문제 분해는 큰 문제를 더 간단하고 관리 가능한 하위 문제나 함수로 나누는 것입니다. 역사적으로 문제 분해는 모듈 프로그래밍의 핵심 원칙으로 등장했습니다: 이는 복잡성 관리, 테스트 가능성 및 코드 재사용을 용이하게 합니다.
문제: 문제 분해 없이는 코드가 "모놀리식"이 되어 읽기 어렵고 유지 보수하기 힘들며, 테스트를 작성하고 프로그램의 일부를 재사용하기가 더 어렵습니다.
해결책: 파이썬에서 문제 분해는 논리를 함수, 클래스, 모듈로 나누고; 명확한 이름을 사용하고; 구성 및 추상을 활용하여 구현됩니다. 이는 읽기 쉽고 확장 가능한 코드를 작성할 수 있게 합니다.
코드 예제:
# 비압축 모놀리식 코드 numbers = [1, 2, 3, 4] squares = [] for n in numbers: if n % 2 == 0: squares.append(n**2) print(squares) # 분해된 버전 def is_even(n): return n % 2 == 0 def square(n): return n ** 2 def filter_and_apply(numbers, predicate, func): return [func(n) for n in numbers if predicate(n)] numbers = [1, 2, 3, 4] result = filter_and_apply(numbers, is_even, square) print(result)
주요 특징:
작은 비즈니스 로직을 한 함수로 구현할 수 있나요?
종종 작은 작업은 "100줄 함수"를 작성할 수 있다고 생각합니다. 이는 안티 패턴입니다: 작은 작업이라도 작은 변경을 할 경우 복잡해질 수 있으며, 마이크로 함수는 테스트 및 유지보수가 훨씬더 쉽습니다.
같은 로직의 함수가 서로 다른 이름을 가진 경우 분해로 간주될 수 있나요?
아니요, 코드 중복은 나쁜 분해입니다. 반복되는 코드는 하위 문제의 경계가 잘못 설정된 것을 나타냅니다. 항상 반복되는 기능을 보조 함수로 분리해야 합니다.
예:
def add_user(): pass # 로직 def add_admin(): pass # 위와 같은 로직!
보조 작업을 분해할 필요가 있나요, 단 한 번만 사용된다면?
네, 종종 그러한 함수는 단일 사용 시에도 코드를 더 간단하게 만드는 데 도움이 됩니다 (예: 조건이나 필터링을 별도의 함수로 분리).
데이터 처리를 위한 프로젝트가 300줄의 큰 함수로 제출되었습니다. 각 버그는 패닉을 일으켰습니다: 무엇이 어떻게 일어났는지 빠르게 이해할 수 없고, 테스트가 거의 불가능했습니다.
장점:
단점:
같은 프로젝트, 리팩토링 - 코드가 기본 로직 (읽기, 검증, 처리, 데이터 기록)에 따라 작은 함수 및 클래스로 분리되었습니다.
장점:
단점: