```
Clean Code에 대한 김 씨의 생각
```
이번 글을 통해 배워갈 내용
- Clean Code에 대한 김씨의 생각
Clean 코드의 정의
클린 코드는 쉽게 이해하고 쉽게 유지 보수할 수 있는 코드입니다.
(Wickionary를 의역)
KimC가 회사생활을 하면서
여러 코드를 보고 여러 사람들을 경험해본 결과
많은 개발자들은
많은 시간을
다른 개발자들이 작성한 코드를
읽고 이해하는데 쓴다는 것을 깨달았습니다.
따라서 코드를 작성하는 개발자는
다른 사람들이 읽고 이해하는데
불편함이 없도록 배려를 해야 합니다.
(물론 코드를 읽는 개발자도
코드를 작성하는 개발자에게 질문을 하기 전에
기본적인 내용은 숙지하고 요약을 해서 불필요한 질문을 줄이고
검색해서 해결이 가능한 간단한 것들은 직접 해결하고
전에 물어본 것을 다시 물어보지 않게 해서 불필요한 반복을 줄여야 합니다
그리고 문제가 발생할만한 것들은 무조건 물어봐야 하고..............
여기서 끝도 없으니 사심이 가득한 사설은 멈추겠습니다.)
따라서 김 씨는 상황에 따라서
주니어 개발자가 어려워하는 함수를 작성할 때는
주석을 달면서 설명하거나 그것도 힘들 때는 최대한 단순 명료하게 작성하였으나
해답은 없다는 것을 깨달았습니다.
하지만
상황에 따라서 최적화된 길을 존재한다고 믿습니다.
클린 코드는 이름이 명확하고
코드 구조가 복잡하거나
코드 블록이 크지 않고
짧고 인지하기 쉬우며
읽기 쉬워야 한다고 많은 개발자들이 동의합니다.
아래는 김 씨가 생각해낸 한 가지 예시입니다.
정답은 아니니 참조만 해주시면 감사하겠습니다.
package com.bj;
import java.util.HashMap;
import java.util.Map;
import java.util.stream.IntStream;
public class Main {
public static void main(String[] args) {
System.out.println(example01(true));
System.out.println(getHelloByIsHappy(true));
}
//////////////////////////////////////////////
// 예시
//////////////////////////////////////////////
// dirty code
private static String example01(boolean h) {
if (h){
// 출력합니다.
System.out.println("hello1");
// 출력합니다.
System.out.println("hello2");
System.out.println("hello3");
System.out.println("hello4");
System.out.println("hello5");
System.out.println("hello6");
System.out.println("hello7");
System.out.println("hello8");
return "smile";
}
// 반환 합니다.
String faceStringToShowFacialResponseofSomething= "fringe";
// Map<String, String> faceList = new HashMap<>();
return faceStringToShowFacialResponseofSomething;
}
// cleaner code
// if arg is happy then return smile string and 8 consecutive hello with postfix number
// if not then return fringe string
private static String getHelloByIsHappy(boolean isHappy) {
final String HELLO = "hello";
final String SMILE = "smile";
final String FRINGE = "fringe";
StringBuilder sb = new StringBuilder();
if (isHappy) {
IntStream.rangeClosed(1, 8).forEach(num -> sb.append(HELLO).append(num).append("\n"));
sb.append(SMILE);
} else {
sb.append(FRINGE);
}
return sb.toString();
}
}
먼저 example 01 함수를 보면
1.
인자로 들어오는 값에 h의 이름이 명확하지 않습니다.
해당하는 값이 무엇을 의미하는지 아무도 모릅니다.
자매품으로 변수명을 data 혹은 val이라고 짓는 경우도 있습니다.
2.
example01이라는 함수명이 대체 무엇을 하는 함수인지 아무도 모릅니다.
자매품으로 함수명을 그냥 handle 이라고 짓거나 process라고 지으면
아무도 이게 무엇을 하는 함수인지 모릅니다.
3.
불필요하게 출력이 여러 번 반복됩니다.
4.
리턴이 두 개입니다.
5.
스트링 변수가 어떻게 돼있는지 조금만 길어도 파악하기 힘들어집니다.
6.
하나의 함수가 여러 가지 역할을 합니다.
7.
불필요한 주석이 코드 중간에 덕지덕지 붙어있습니다.
8.
반환되는 곳에 스트링을 출력하나 함수 내부에서도 불필요하게 출력합니다.
9.
기본적인 줄 맞춤이 돼있지 않습니다.
IDE가 자동으로 저장할 때 해주게 설정하거나
저장 시 단축키를 누르는 배려가 기본으로 돼있어야 합니다.
10.
faceStringToShowFacialResponseofSomething 은 너무 길고
불필요한 정보는 필요없습니다.
바로 리턴에 쓰이는 변수라 필요 없지만 만약 이름을 쓴다면 faceEmotion 이상의 길이는 필요 없을 것 같습니다.
필요에 따라서 긴 변수보다 이해하기 쉬운 경우 짧은 변수를 쓰는 것도 좋습니다.
11.
Map 은 map이고 List는 list입니다. faceList는 리스트가 아닙니다.
(특히 자바스크립트에서 이런 경우를 많이 봤습니다)
(자바스크립트하니까 떠오르는데 retrieve, get, fetch 등을 prefix로 혼용해서 쓰는 것보다 프로젝트 내에서 하나 정해서 쓰는 게 정신 건강에 더 좋습니다. 저는 get을 씁니다 물론 axios 나 타 라이브러리 메서드는 예외입니다.)
12.
깃을 쓰는 경우 쓰이지 않는 주석 코드는 지우는 게 원칙입니다.
13.
//////////////////////////////////////////////
// 예시
//////////////////////////////////////////////
라고 돼있는 코드를 나누는 부분은 필요가 없습니다.
불필요한 정보이고 코드명으로 충분하게 나눌 수 있는 내용입니다.
불필요하게 코드가 길어서 나누었다면
이건 코드가 많아서 그런 것이기 때문에
코드를 여러 파일로 나누어주는 게 정신건강과 깃 충돌을 막는데 더 이득입니다.
반면 getHelloByIsHappy 함수를 보면
1.
인자로 isHappy 가 들어와서
해당되는 인자가 행복에 관련된 Boolean이라는 게 명확합니다.
isLoggedin, isError 등도 많이 씁니다.
2.
함수 명칭이 getHelloByIsHappy이며
해피로 헬로를 조회한다는 느낌이 옵니다.
물론 하나의 함수는 하나의 역할만 해야 된다는 제 원칙에 위배되나
예시로 봐주시면 감사하겠습니다.
실무에서는 isHappy() 함수와 getHelloByHappy(), getFaceStrByHappy()
이런 식으로 짤 것 같다는 생각도 합니다.
3.
StringBuilder, StringBuffer 등을 사용해서 Immutable 한 스트링을 Concat 해주고
반복문을 사용해서 불필요하고 반복되는 코드를 줄였으며 IntStream으로 불필요한 for문을 줄였습니다.
4.
리턴을 하나로 만들어서 불필요한 리턴을 줄였습니다.
5.
해당 메서드의 길이가 한 페이지 이내이며 필요한 스트링들을 위에 써서 파악하기 쉽게 하였습니다. 필요시 Static처리도 좋을 것 같습니다.
6.
주석이 영어로 메서드 위에 깔끔하게 붙어서 글로벌합니다
1줄 요약
클린 코드는 읽고 이해하기 쉽고 유지보수가 편하나 더러운 코드는 그렇지 않습니다.
(김씨의 개인적 생각이기 때문에 의견은 환영합니다)
참조
Clean Code
Book by Robert Cecil Martin
읽어주셔서 감사합니다
무엇인가 얻어가셨기를 바라며
오늘도 즐거운 코딩 하시길 바랍니다 ~ :)
'Java > Java 기타' 카테고리의 다른 글
Keytool 사용법: RFC 형식으로 인증서를 keystore.pem으로 내보내는 한가지 방법 (1) | 2023.09.24 |
---|---|
JAVA로 점을 가진 문자열 나누는 방법 (0) | 2022.08.23 |
자바에서 @SafeVarargs사용하는 한 가지 방법 (0) | 2022.05.21 |
자바에서 @FunctionalInterface 사용하는 한 가지 방법 (0) | 2022.05.21 |
자바에서 @SupressWarnings 사용하는 한 가지 방법 (0) | 2022.05.21 |