• Save
Responding to change
Upcoming SlideShare
Loading in...5
×
 

Responding to change

on

  • 2,429 views

변화에 대처하기

변화에 대처하기

Statistics

Views

Total Views
2,429
Views on SlideShare
2,225
Embed Views
204

Actions

Likes
0
Downloads
0
Comments
0

4 Embeds 204

http://mypage.sarang.net 183
http://www.hanrss.com 14
http://www.slideshare.net 6
http://whatthehell.pe.kr 1

Accessibility

Categories

Upload Details

Uploaded via as Microsoft PowerPoint

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

Responding to change Responding to change Presentation Transcript

  • 변화에 대처하기 (Responding to change) 남기룡 마이에트 엔터테인먼트
  • 변하지 않는 것은 없다
    • 변하지 않는 유일한 진리 = 변하지 않는 것은 없다
      • 요구사항은 끊임없이 변한다 .
      • 만들어봐야 재미있는지 안다 .
  • 변화에 대한 대처법
    • 많은 의사소통
    • 유연한 설계
    • 테스트
    • 지속적인 통합
    • 피드백
  • 설계
  • 설계의 악취
    • 경직성 (Rigidity) - 설계를 변경하기 어려움
    • 취약성 (Fragility) - 설계가 망가지기 쉬움
    • 부동성 (Immobility) - 설계를 재사용하기 어려움
    • 점착성 (Viscosity) - 제대로 동작하기 어려움
    • 불필요한 복잡성 (Needless Complexity) - 과도한 설계
    • 불필요한 반복 (Needless Repetition) - 마우스 남용
    • 불투명성 (Opacity) - 혼란스러운 표현
  • 설계 원칙
    • SRP – 단일 책임 원칙 (Single Responsibility Principle)
    • OCP - 개방 - 폐쇄 원칙 (Open-Closed Principle)
    • LSP - 리스코프 교체 원칙 (Liskov Substitution Principle)
    • DIP - 의존 관계 역전 원칙 (Dependency Inversion Principle)
    • ISP - 인터페이스 격리 원칙 (Interface Segregation Principle)
  • SRP(Single Responsibility Principle)
    • 단일 책임 원칙
    • 객체는 하나의 책임만을 맡아야 한다 .
    • 책임 = 변화의 축 ( 산탄총 수술 )
  • SRP 예시
    • 국제적 은행의 계좌 관리 케이스
  • SRP 예시
  • OCP(Open Closed Principle)
    • 개방-폐쇄 원칙
    • 소프트웨어 개체 ( 클래스 , 모듈 , 함수 등등 ) 는 확장에는 열려 있어야 하고 , 변경에는 닫혀 있어야 한다 .
  • OCP
  • OCP
  • OCP
    • 상속을 통한 다형성을 이용한 호출
  • Command Pattern
  • LSP(Liskov Substitution Principle)
    • 리스코프 치환 원칙
    • 기반 클래스는 서브 클래스로 대체 가능해야 한다 .
    • Is-A 관계
  • 잘못된 상속 관계
  • DIP(Dependency Inversion Principle)
    • 의존 관계 역전의 법칙
    • 클라이언트는 구체 클래스가 아닌 인터페이스나 추상 클래스에 의존해야 한다 .
    • Don’t call us, we’ll call you
  • Template Method Pattern
  • ISP(Interface Segregation Principle)
    • 인터페이스 분리의 원칙
    • 클라이언트에게 특화된 여러 개의 인터페이스가 하나의 범용 인터페이스보다 낫다.
  • ISP 적용 전
  • ISP 적용 후
  • 테스트
  • 테스트 유형 스토리 테스트 비즈니스 의도 (제품 설계) 사용성 테스팅 탐색적 테스팅 단위 테스트 개발자 의도 (코드 설계) 특성 테스팅 보안 테스팅 부하 테스팅 조합 테스팅 … 자동 자동 수동 도구
  • Test Example (단위 테스트) TEST(TestCapsuleIntersectRay) { // test1 vec3 t = vec3(0.0f, 2000.0f, 100.0f); vec3 b = vec3(0.0f, 2000.0f, 0.0f); float fDistance = 0.0f; MCapsule tCapsule(b, t, 50.0f); vec3 vRayOrigin = vec3(0.0f, 0.0f, 0.0f); vec3 vRayDir = vec3(0.0f, -1.0f, 0.0f); bool bPick = tCapsule.IntersectRay(vRayOrigin, vRayDir, fDistance); CHECK(bPick == false); CHECK(fDistance > 0.0f); // test2 t = vec3(0.0f, 2000.0f, 100.0f); b = vec3(0.0f, 2000.0f, 0.0f); MCapsule tCapsule2(b, t, 50.0f); vRayOrigin = vec3(0.0f, 0.0f, 0.0f); vRayDir = vec3(0.0f, 1.0f, 0.0f); bPick = tCapsule2.IntersectRay(vRayOrigin, vRayDir, fDistance); CHECK(bPick == true); CHECK_CLOSE(fDistance, 1950.0f, 0.01f); // test3 t = vec3(0.0f, 2000.0f, 100.0f); b = vec3(0.0f, 2000.0f, 0.0f); MCapsule tCapsule3(b, t, 100.0f); vRayOrigin = vec3(0.0f, 0.0f, 0.0f); vRayDir = vec3(101.0f, 2000.0f, 0.0f).Normalize(); bPick = tCapsule3.IntersectRay(vRayOrigin, vRayDir, fDistance); CHECK(bPick == false); CHECK(fDistance < 1.0f); }
  • Test Example(스토리 테스트) TEST(PlayerJumpTest) { const vec3 player_pos = vec3(1000,1000,0); World world; world.Create(); Player player; player.Create(world, player_pos); player.Jump(); player.Update(0.1f); CHECK(player.GetPosition().z > 0); CHECK(player.GetAni() == ANI_JUMP); } TEST(ShieldCanBeDamaged) { Player player; player.SetHealth(1000); Shield shield; shield.SetHealth(100); player.Equip(shield); player.Damage(200); CHECK(shield.GetHealth() == 0); CHECK(player.GetHealth() == 900); }
  • TDD(Test Driven Development)
    • TDD != Test
    • 장점
      • 단순함과 모듈화
      • 안전망
      • 즉각적인 피드백
      • 문서화
    • 과정
      • 재빨리 테스트를 하나 추가한다 .
      • 테스트를 실행시켜 새로 추가한 녀석이 실패하는 걸 확인한다 .
      • 코드를 약간 수정한다 .
      • 테스트를 실행시켜 모두 성공하는지 확인한다 .
      • 중복을 제거하기 위해 리팩터링한다 .
  • 불과 몇 분밖에 걸리지 않는다 . 체크 인 체크 인 TDD 의 순환 과정 TEST (ShieldLevelStartsFull) { Shield shield; CHECK_EQUAL (Shield::kMaxLevel, shield.GetLevel()); } Shield::Shield() : m_level (Shield::kMaxLevel) { } 테스트 작성 코드 작성 리팩토링 테스트 실패 테스트 통과 테스트 통과
  • TDD 시연
  • Tips
    • Mock Object
      • Device, Socket, DB
    • 김밥 썰기와 해체 하기
    • 처음부터 많은 것을 테스트하려 하지말고 , 현실적으로 가능한 것부터 하라 .
    • 처음에는 과도할 정도로 클래스를 나눠라 .
    • MVC(Model-view-controller) 패턴을 활용하라 .
    • 초반에는 개발 속도가 떨어지지만 , 익숙해지면 개발 속도가 빨라진다 .
  • Legacy Code
    • 세상에 존재하는 두 종류의 코드
      • 변화 허용 코드
      • 레거시 코드
    • 변화 허용 코드 : 쉽게 비즈니스나 기술의 변화에 적용하는 코드
    • Legacy Code : 의존성 (Dependency) 이 높고 , 테스트로 보호되지 않은 코드
  • Legacy Code에 대한 접근 방법
    • 다시 짜고 내다 버리기 (Rewrite and throw away)
    • 리팩토링으로 굴복시키기 (Refactor into submission)
      • 의존 관계 깨뜨리기
      • 독립적인 코드 주변에 테스트를 추가
      • 단위 테스트보다는 스토리 테스트 위주 작성
    • 질식시키기 (Strangle)
      • 포도 덩굴로 무화과 나무 질식시키기
      • 레거시 코드 일부분이라도 건드릴 기회가 있을 때마다 질식시키는 코드를 추가
  • 리팩토링을 습관화하라 . CODE
  • 정리
    • 변화 에 기민하게 대응하자 .
    • 알고 있는 것은 중요하지 않다 . 실천하는 것이 중요하다 !
    • 습관적으로 설계하고 테스트하고 리팩토링해야 한다 .