or
로 묶는 것 고려)interface SomeService {
fun process(data: String): String
}
class SomeServiceImpl: SomeService {
override fun process(data: String): String {
// 매우 복잡한 로직 ...
return processedData
}
}
// wrapping
class WrappedSomeService(val someService: SomeService): SomeService {
override fun process(data: String): String {
// do something before process...
val ret = someService.process(data)
// do something after process...
return ret
}
}
// mocking
class MockSomeService: SomeService {
override fun process(data: String): String {
return "MockedData"
}
}
//
fun fun1(){
fun2()
fun3()
}
private fun fun2(){}
private fun fun3(){}
decoupling 비용 + 변경비용 < coupling 비용 + 변경비용
인 경우 결합도 제거Point(
긴 표현식...,
다른 긴 표현식...
)
vs
x = 긴 표현식...,
y = 다른 긴 표현식...
Point(x,y)
object EntityFixture {
fun createProduct(
key: String = DefaultValues.DEFAULT_PRODUCT_KEY, // 기존: "test-key"
name: String = DefaultValues.DEFAULT_PRODUCT_NAME, // 기존: "test-name"
number: Long = DefaultValues.DEFAULT_PRODUCT_NUMBER, // 기존: 10
): Product {
return Product(key, name, number)
}
}
// CreatePostRequest.kt
data class CreatePostRequest(
val memberId: Long,
val title: String,
val content: String,
val someValue: String,
val somdData: Data,
) {
fun toMemberKey(): Long {
return memberId
}
fun toPostContent(): PostContent { // 도메인 객체(또는 dto)
return PostContent(
title = title,
content = content,
)
}
}
// Controller.kt
@PostMapping
fun createPost(@RequestBody request: PostRequest): ResponseEntity<Void> {
val postId = postService.createPost(request.toMemberKey(), request.toPostContent()) // 필요한 값만 전달
...
}
fun calculateTotalPrice(item: Item){
return item.price * item.count
}
vs
fun calculateTotalPrice(price: Int, count: Int){
return price * count
}
print("\n====== vpc 생성 ======")
vpc_id = create_vpc(ec2, '10.0.0.0/16')
igw_id = create_and_attach_igw(ec2, vpc_id)
allocation_id = create_eip(ec2)
print("\n====== 서브넷 생성 (public, private) ======")
public_subnet_id = create_subnet(ec2, vpc_id, '10.0.1.0/24', igw_id=igw_id)
private_subnet_id = create_subnet(ec2, vpc_id, '10.0.2.0/24')
print("\n====== EC2 생성 (2개) ======")
ec2_instances = [
create_ec2_instance(ec2, public_subnet_id, allocation_id),
create_ec2_instance(ec2, private_subnet_id),
]
fun helper(){
...변경하고자 하는 코드...
}
fun function(){
...그대로...
...변경하고자 하는 코드... // <- 이 부분을 helper()로 대체
...그대로...
}
fun createAndRun(){
create()
run()
}
private fun create(){}
private fun run(){}
fun processOrder(order: Order) {
if (order.items.isEmpty()) {
throw IllegalArgumentException("Empty order")
}
// ... 복잡한 로직 ...
println("Processing order: $order")
// ... 복잡한 로직 ...
// ... 복잡한 로직 ...
println("Order completed")
// ... 복잡한 로직 ...
}
vs
fun processOrder(order: Order) {
validateOrder(order)
handleOrderProcessing(order)
completeOrder()
}
fun validateOrder(order: Order) {
if (order.items.isEmpty()) {
throw IllegalArgumentException("Empty order")
}
}
fun handleOrderProcessing(order: Order) {
// ... 복잡한 로직 ...
println("Processing order: $order")
// ... 복잡한 로직 ...
}
fun completeOrder() {
println("Order completed")
// ... 복잡한 로직 ...
}
코드가 지나치게 많은 함수로 나뉘어져 있을 때는 코드를 하나의 더미(
One Pile
)처럼 느껴질 떄 까지 모아라. 그리고 다시 정리하라.
코드를 만드는 데, 가장 큰 비용이 들어가는 일은 작성이 아니라 읽고 이해하는데 드는 비용이다.
코드를 모음으로써 응집도를 높일 수 있지만, 실무적으로는 가독성을 증가시킬 수 있다.
메서드 분리의 목적은 가독성의 증가도 있다. 명확성을 찾으려면 코드를 모으는 것을 고려해보아라.
아래의 증상이 느껴진다면 코드를 모으는 것을 검토해보아라.
"작은 함수 속에 코드를 이해하고자 갖은 애를 쓰다가 문득, 자신의 능력을 의심하는 데까지 이르기도 한다. 하지만, 이때 코드를 한곳으로 모으면 모든것이 이해되기 시작한다."