Skip to content
This repository was archived by the owner on Dec 30, 2021. It is now read-only.

Chapter 04. Comments

sponge edited this page Aug 9, 2021 · 6 revisions

2021.08.07 (SAT) 10:20-12:00 (100mins)
🚀 Lead by. 'KiHoon Kang'

4장. 주석

나쁜 코드에 주석을 달지마라. 새로 짜라!

  • 브라이언 W. 커니핸, P.J. 플라우거

잘 달린 주석은 유용하지만, 경솔하고 근거없는 주석은 코드를 이해하기 어렵게 만든다. 주석은 사실상 '필요악' 이다.
2장 의미있는 이름을 잘 활용한다면 주석을 쓸 필요가 없다. 원하는바를 표현하지 못해 실패를 만회하기 위해 주석을 사용한다.

코드로 의도표현에 성공했을때 +1 칭찬

주석을 달았을 경우 +1 자책

주석은 고의는 아니지만 거짓말을 자주하고, 오래될수록 관리가 힘들어 코드의 변화를 따라가지 못한다.
잘 정리된 주석은 보기에 좋아 보일 수 있지만, 애초에 주석이 필요 없는 방향을 추구하는게 더욱 옳다.

부정확한 주석은 독자를 현혹하고 오도한다.
코드만이 정확한 정보를 제공하는 진실되고 유일한 출처이므로, (간혹 필요하지만) 주석을 줄이도록 노력해야한다.

  • 주석은 나쁜 코드를 보완하지 못한다

주석이 추가되는 일반적 이유는 코드 품질이 나쁘기 때문이다.
지저분한 모듈이란 것을 알아차렸을때 ~~주석달자!~~ 대신 코드를 정리하자!를 실천하자.

  • 코드로 의견을 표현하라! 코드 >> 주석

코드만으로 의도를 설명하기가 쉽지 않을 수 있다. 하지만 주석 달 시간동안 고민하면 더 좋은 코드가 될 수 있다.

//직원에게 복지 혜택을 받을 자격이 있는지 검사한다.
// case1.
if ((employee.flags & HOURLY_FLAG ) &&
    (employee.age > 65))

// case2.
if (employee.isEligibleForFullBenefits())

좋은 주석과 나쁜 주석

좋은 주석

필요하거나 유의미한 주석이 존재한다. 하지만 가장 좋은 주석은, 주석을 달지 않을 방법을 찾아낸 주석!

  1. 법적인 주석

    저작권 정보소유권 정보는 필요하고도 타당하다.

    // ex1. FitNess 소스파일 첫머리 표준 주석헤더
    
    //Copyright (C) 2003, 2004, 2005 by Object Mentor, Inc. All rights reserved
    //GNU General Public License 버전 2 이상을 따르는 조건으로 배포한다.
  2. 정보를 제공하는 주석

    // ex1. 추상메서드가 반환할 값을 설명
    //테스트 중인 Responder 인스턴스를 반환한다.
    protected abstract Responder responderInstance();
    -> redponderBeingTested()  형태였다면 주석이 필요없다.
    
    // ex2. 정규표현식 표현 안내
    //kk:mm:ss EEE, MMM dd, yyyy형식이다.
    Pattern timeMatcher = Pattern.compile("\\d*:\\d*:\\d* \\w*, \\w* \\d*, \\d*");
    // -> SimpleDateFormat.format 함수가 반환하는 시각과 날짜를 뜻한다.
    // -> HH:mm:ss / kk:mm:ss 차이 ? '0시 0분' 표현
    // => 00:00:00 / 24:00:00

    [Java] 자바 정규 표현식 (Pattern, Matcher) 사용법 & 예제

    자바 정규 표현식 참고자료

  3. 의도를 설명하는 주석

    public int compareTo(Object o)
    {
      if(o instanceof WikiPagePath) //o가 WikiPagePath 형태인가?
      {
        WikiPagePath p = (WikiPagePath) o;
        //StringUtil.join은 앞의 인자들을 뒷 인자의 형태로 연결해준다. 
        String compressedName = StringUtil.join(names, "");
        String compressedArguementName = StringUtil.join(p.names, "");
        return compressedName.compareTo(compressedArgumentName);
        // compressedName과 compressedArgumentName을 비교해 숫자로 반환해 나타낸다
        // return > 0 : compressedName > compressedArgumentName
        // return = 0 : compressedName == compressedArgumentName
        // return < 0 : compressedName < compressedArgumentName
      }
      return 1; //오른쪽 유형이므로 정렬 순위가 더 높다.
    }
    public void testConcurrentAddWidgets() throws Exception{
      WidgetBuilder widgetBuilder = new WidgetBuilder(new Class[]{BoldWidget.class});
      String text = "'''bold text'''";
      ParentWidget parent = new BoldWidget( newMockWidgetRoot(), "'''bold text'''");
      AtomicBoolean failFlag = new AtomicBoolean();
      failFlag.set(false);
       	
      //스레드를 대량 생성하는 방법으로 어떻게든 경쟁 조건을 만들려 시도한다.
      for (int i = 0; i < 25000; i++){
      	 WidgetBuilderThread widgetBuilderThread = new WidgetBuilderThread(widgetBuilder, text, parent, failFlag);
        Thread thread = new Thread(widgetBuilderThread);
        thread.start();
      }
      assertEquals(false, failFlag.get());
    }
  4. 의미를 명료하게 밝히는 주석

    모호한 인수나 반환값을 읽기 좋게 표현하면 좋으나 변경할 수 없는 코드라면 의미를 명료하게 주석을 달 수 있다. 하지만 주석이 올바른지 검증하기 쉽지않기 때문에 위험할 수 있다.

    public void testCompareTo() throws Exception
    {
      WikiPagePath a  = PathParser.parse("PageA");
      WikiPagePath ab = PathParser.parse("PageA.PageB");
      WikiPagePath b = PathParser.parse("PageB");
      WikiPagePath aa = PathParser.parse("PageA.PageA");
      WikiPagePath bb = PathParser.parse("PageB.PageB");
      WikiPagePath ba = PathParser.parse("PageB.PageA");
    
      assertTrue(a.compareTo(a) == 0 );    // a==a
      assertTrue(a.compareTo(b) != 0 );    // a!=b
      assertTrue(ab.compareTo(ab) == 0 );  // ab==ab
      assertTrue(a.compareTo(b) == -1 );   // a<b
      assertTrue(aa.compareTo(ab) == -1 ); // aa<ab
      assertTrue(ba.compareTo(bb) == -1 ); // ba<bb
      assertTrue(b.compareTo(a) == 1 );    // b>a
      assertTrue(ab.compareTo(aa) == 1 );  // ab>aa
      assertTrue(bb.compareTo(ba) == 1 );  // bb>ba
    }
  5. 결과를 경고하는 주석

    결과를 경고할 목적으로 사용하기도 한다. !!WARNING!!

    //여유시간이 충분하지 않다면 실행하지 마십시오
    public void _testWithReallyBigFile()
    {
      writeLinesToFile(10000000);
    
      response.setBody(testFile);
      response.readyToSend(this);
      String responseString = output.toString();
      assertSubString("Content-Length: 1000000000", responseString);
      assertTrue(bytesSent > 1000000000);
    }
    public static SimpleDateFormat makeStandardHttpDateFormat()
    {
      //SimpleDateFormat은 스레드에 안전하지 못하다.
      //따라서 각 인스턴스를 독립적으로 생성해야 한다.
      SimpleDateFormat df = new SimpleDateFormat("EEE, dd MMM yyyy HH:mm:ss z");
      df.setTimeZone(TimeZone.getTimeZone("GMT"));
      return df;
    }
  6. TODO 주석

    앞으로 할 일을 TODO주석으로 남겨두면 편하다.

    TODO 주석은 필요하지만 당장 구현하기 어려운 업무를 기술한다.
    ex) 필요없는기능 삭제하라, 문제를 알아봐달라, 이름을 추천해달라, 도망쳐라 etc
    하지만 너무 많은 TODO 주석 역시 나쁜코드가 되므로 주의할 것

    //TODO-MdM 현재 필요하지 않다.
    //체크아웃 모델을 도입하면 함수가 필요 없다.
    protected VersionInfo makeVersion() throws Exception
      {
        return null;
      }
  7. 중요성을 강조하는 주석

    놓칠 수 있는 부분의 강조!

    String listItemContent = match.group(3).trim();
    //여기서 trim은 정말 중요하다. trim 함수는 문자열에서 시작 공백을 제거한다.
    //문자열에 시작 공백이 있으면 다른 문자열로 인식되기 때문이다.
    new ListItemWidget(this, listItemContent, this.level+1);
    return buildList(text.substring(match.end()));
  8. 공개 API에서 Javadocs

    설명이 잘 된 공개 API는 유용하고, 그 좋은 예가 Javadocs이다.
    공개 API를 구현하게 된다면 반드시 훌륭한 Javadocs를 작성할것이며 없으면 프로그램을 짜기 힘들것.

    • Javadoc란? .class 파일 등에 들어가보면 많이 보인다!
      Javadoc는 JDK에 기본으로 포함되어 있는 프로그램으로 소스 코드에 포함된 클래스나
      메소드의 주석(comment)으로 부터 자동으로 명세서를 작성 해주는 편리한 도구이다.

    • 주석에대해서, Javadoc에 대해 알아보자

      한줄주석
      //주석내용
      
      블록주석
      /*
       주석내용
       주석 주석
       */
      
      javadoc 주석
      /**
       */
      
      /** 여기서 엔터를 치면 자동으로 *가 붙는다 */
      
      /**
       * 주석
       * 주석
       */
      
      /**
       주석
       주석
       */
      
      시작이 /**이고 일반적인 주석의 작성 방법인 /* 비해 * 하나가 많지만, 
      /* 이후 주석으로 * 이어서 작성되고 있는 것과 동일하기에 Java에서의 주석인 것에는 변함이 없다. 
      Java에서의 주석에서 특히 /** 시작하는 것만을 대상으로 한다고 생각하면 된다.
      
      또한 Javadoc에서는 여러 줄의 주석을 작성할 때는   앞에 *
      작성되어 있던 경우는 제외하고  후에 문자열만을 주석의 대상으로 한다. 
      그리고 *이전에 작성된 공백이나 탭도 함께 제외된다. 
      //sample.java 
      
      /** 
       * 이 클래스는 Javadoc 설명용 클래스이다. 
       * 여러 줄로 작성할 수 있다. 
       * @version 2.0 
       * @param string 이름 
       * @param int 연령 
       * 설명문을 태그 섹션 이후에 작성하지 않는다. 
       */
      
      public class Sample01 { 
      
      /** 
       * 폭 
       */ 
       private int w;
      
      /** 
       * 높이 
       */ 
       private int h; 
      
      /** 
       * 디폴트 생성자 클래스 
       */ 
       public Sample01() { w = 0; h = 0; } 
      
      /** 
       * 사이즈 설정
       * @param width 폭 
       * @param height 높이 
       */ 
       public void setSize(int width, int height) { w = width; h = height; } 
      
      /** 
       * 폭 반환
       * @return 폭 
       */ 
       public int getWidth() { return w; } 
      
      /** 
       * 높이 반환
       * @return 높이 
       */ 
      public int getHeight() { return h; } }
      $ javadoc -private -d doc Sample01.java 
      
      # Like this...
      # Loading source file Sample01.java... 
      # Constructing Javadoc information... 
      # Creating destination directory: "doc/" 
      # Standard Doclet version 1.8.0_161 
      # Building tree for all the packages and classes... 
      # Generating doc/Sample01.html... 
      # Generating doc/package-frame.html... 
      # Generating doc/package-summary.html... 
      # Generating doc/package-tree.html... 
      # Generating doc/constant-values.html... 
      # Building index for all the packages and classes... 
      # Generating doc/overview-tree.html... 
      # Generating doc/index-all.html... 
      # Generating doc/deprecated-list.html... 
      # Building index for all classes... 
      # Generating doc/allclasses-frame.html... 
      # Generating doc/allclasses-noframe.html... 
      # Generating doc/index.html... 
      # Generating doc/help-doc.html...
      $ ls -al
      
      # Like this
      # total 176 
      # drwxr-xr-x 17 kimkc staff 578 10 8 23:49 . 
      # drwxr-xr-x 4 kimkc staff 136 10 8 23:49 .. 
      # -rw-r--r-- 1 kimkc staff 10937 10 8 23:49 Sample01.html 
      # -rw-r--r-- 1 kimkc staff 633 10 8 23:49 allclasses-frame.html 
      # -rw-r--r-- 1 kimkc staff 613 10 8 23:49 allclasses-noframe.html 
      # -rw-r--r-- 1 kimkc staff 3507 10 8 23:49 constant-values.html 
      # -rw-r--r-- 1 kimkc staff 3457 10 8 23:49 deprecated-list.html 
      # -rw-r--r-- 1 kimkc staff 7892 10 8 23:49 help-doc.html 
      # -rw-r--r-- 1 kimkc staff 5448 10 8 23:49 index-all.html 
      # -rw-r--r-- 1 kimkc staff 2744 10 8 23:49 index.html 
      # -rw-r--r-- 1 kimkc staff 3684 10 8 23:49 overview-tree.html 
      # -rw-r--r-- 1 kimkc staff 740 10 8 23:49 package-frame.html 
      # -rw-r--r-- 1 kimkc staff 1 10 8 23:49 package-list 
      # -rw-r--r-- 1 kimkc staff 3906 10 8 23:49 package-summary.html 
      # -rw-r--r-- 1 kimkc staff 3693 10 8 23:49 package-tree.html 
      # -rw-r--r-- 1 kimkc staff 827 10 8 23:49 script.js 
      # -rw-r--r-- 1 kimkc staff 12842 10 8 23:49 stylesheet.css

나쁜 주석

대다수의 주석은 나쁜 주석이다!

  1. 주절거리는 주석

    주석을 달려면 충분한 시간을 들여 최고의 주석을 달아야한다!

    public void loadProperties(){
    	try{
    		String propertiesPath = propertiesLocation + "/" + PROPERTIES_FILE;
    		FileInputStream propertiesStream = new FileInputStream(propertiesPath);
    		loadedProperties.load(propertiesStream);
    	}catch(IOException e){
    		//속성 파일이 없다면 기본값을 모두 메모리로 읽어 들였다는 의미다.
    	}
    }

    저자에게는 의미있지만 다른사람에게는 전해지지않는다.
    누가 언제 어떤 기본값을 읽어들이는지 설명되지 않아 결국은 연결된 모듈을 뒤져야 이해할 수 있는 코드다.

  2. 같은이야기를 중복하는 주석

    헤더의 주석이 코드의 내용과 동일하다. (주석 읽는 시간이 더 걸린다.)

    //this.closed가 true일 때 반환되는 유틸리티 메서드다.
    //타임아웃에 도달하면 예외를 던진다.
    public synchronized void waitForClose(final long timeoutMillis) throws Exception{
    	if(!closed){
    		wait(timeoutMillis);
    		if(!closed)
    			throw new Exception("MockResponseSender could not be closed");
    	}
    }

    tomcat에는 쓸모없는 javadocs가 굉장히 많다.
    필요하다고 생각되는 주석이지만 과해질 수 있다.

    public abstract class ContainerBase implements Container, Lifecycle, Pipeline, MBeanRegistration, Serializable{
    
      /**
       * 이 컴포넌트의 프로세서 지연값
       */
      protected int backgroundProcessorDelay = -1;
    
      /**
       * 이 컴포넌트를 지원하기 위한 생명주기 이벤트
       */
      protected LifecycleSupport lifecycle = new LifecycleSupport(this);
    }
    • 이러한 나쁜 주석이 적용된 예시

      if (error == 0) {
        //송금요청이 되었으니 잠시 후 처리결과 확인 바랍니다. Alert
        create_alert("안내", "송금요청이 정상처리 되었으니 잠시 후 확인해주세요", false, function() {
          stmtSendFormSearch(0)
        });
      } else {
        //송금에 실패하였습니다. 관리자에게 연락주세요. Alert
        create_alert("안내", "송금에 실패하였습니다. 관리자에게 연락주세요.", false, function() {
          stmtSendFormSearch(0)
        });
      }
  3. 오해할 여지가 있는 주석

    this.closed가 true일 때 라는 말에서 오해가 발생할 수 있음

    //this.closed가 true일 때 반환되는 유틸리티 메서드다.
    //타임아웃에 도달하면 예외를 던진다.
    public synchronized void waitForClose(final long timeoutMillis) throws Exception{
      if(!closed){
        wait(timeoutMillis);
     	 if(!closed)
     	   throw new Exception("MockResponseSender could not be closed");
        }
    }
  4. 의무적으로 다는 주석

    아래와 같이 javadocs를 위한 기계적인 주석은 코드만 지저분하게 만들 뿐이다.

    아래 코드는 의무적으로 작성한 주석으로 코드 해석에 전혀 도움을 주지 않는다. 심지어 CopyAndPaste 오류가 발생해 잘못된 정보를 줄 가능성도 있음

    /**
     *
     * @param title CD 제목
     * @param author CD 저자
     * @param tracks CD 트랙 숫자
     * @param durationInMinutes CD 길이(단위:분)
     */
    public void addCD(String title, String author, int tracks, int durationInMinutes) {
      CD cd = new CD();
      cd.title = title;
      cd.author = author;
      cd.tracks = tracks;
      cd.duration = durationInMinutes;
      cdList.add(cd);
    }
  5. 이력을 기록하는 주석

    예전에는 필요하긴 했지만 지금은 소스관리프로그램이 너무나 잘되어있다.

    /**
     * 변경 이력 (11-Oct-2001부터)
     * -------------------------------
     * 11-Oct-2001 : 클래스를 다시 정리하고 새로운 패키지로 옮김
     * 11.Nov-2001 : getDescription() method를 추가
     */
  6. 있으나 마나 한 주석

    너무 당연한 사실을 언급하며 새로운 정보가 없는 주석

    /**
     * 기본 생성자
     */
    protected AnnualDateRule() {
    }
    
    /** 월 중 일자 */
    private int dayOfMonth;
    
    /** 
     * 월 중 일자를 반환한다.
     *
     * @return 월 중 일자
     */
    public int getDayOfMonth() {
      return dayOfMonth;
    }

    혼자하는 헛소리

    혼자하는 코드라면 상관 없지만 함께 관리하는 코드라면 정리해야한다.

    private void startSending(){
      try{
        doSending();
      } catch(SocketException e) {
        //정상. 누군가 요청을 멈췄다.
      } catch(Exception e) {
     	 try{
     	   response.add(ErrorResponder.makeExceptionString(e));
     		 response.closeAll();
     	 } catch(Exception e1) {
     		 //이게뭐야!
     	 }
      }
    }
    • 이러한 나쁜 주석이 적용된 예시

      if ("0".equals(map.get("seq"))) { // 첫 메일발송 임을 나타내는것 같다?
        if ("01".equals(map.get("pmCd"))) { // 신용카드 전용 템플릿
          if ("0".equals(map.get("trxStCd"))) {
  7. 무서운 잡음

    무지성 javadocs는 오히려 독이된다. copy/paste도 주의를 기울이지 않으면 중복이 발생한다.

    /** The name. */
    private String name;
    
    /** The version. */
    private String version;
    
    /** The licenceName. */
    private String licenceName;
    
    /** The version. */ // <= 복사/붙여넣기한 주석이 실제 코드를 따라가지 못하고 있다.
    private String info;
  8. 함수나 변수로 표현할 수 있다면 주석을 달지 마라

    // 나쁜 예
    // 전역 목록 <smodule>에 속하는 모듈이 우리가 속한 하위 시스템에 의존하는가?
    if (smodule.getDependSubsystems().contains(subSysMod.getSubSystem()))
     	
    // 개선한 예
    ArrayList moduleDependees = smodule.getDependSubsystems();
    String ourSubSystem = subSysMod.getSubSystem();
    if (moduleDependees.contains(ourSubSystem))
  9. 위치를 표시하는 주석

    간혹 프로그래머는 특정 위치를 표시하려 주석을 이용한다.
    너무 자주사용하지만 않는다면 득이될 수 있지만 정말 필요할때만 사용하는게 좋다.

    //ACTION!!!!//////////////I'm HERE!!!!/////////////////
    • 이러한 나쁜 주석이 적용된 예시

      //■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■
      //sms 결제기한 추가 > LWH(2020-11-27)
  10. 닫는 괄호에 다는 주석

    중첩이 심하고 장황하다면 의미가 있을수 있지만 잘 정리된 코드라면 필요가 없을것이다.

    import java.io.BufferedReader;
    import java.io.IOException;
    import java.io.InputStreamReader;
    
    public class wc {
      public static void main(String[] args) {
        BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
        String line;
        int lineCount = 0;
        int charCount = 0;
        int wordCount = 0;
        try {
          while ((line = in.readLine()) != null) {
            lineCount++;
            charCount += line.length();
            String words[] = line.split("\\W");
            wordCount += words.length;
          } //while
          System.out.println("wordCount = " + wordCount);
          System.out.println("lineCount = " + lineCount);
          System.out.println("charCount = " + charCount);
        } // try
        catch (IOException e) {
          System.err.println("Error:" + e.getMessage());
        } //catch
      } //main
    }
  11. 공로를 돌리거나 저자를 표시하는 주석

    이런 주석은 시간이 지나며 방치되어 쓸모없는 정보가 되기 쉽다. (누구한테 상줄것도 아니니 이런건 지양하자)

    /* Updated by KKH */
    • 이러한 나쁜 주석이 적용된 예시

      //■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■
      //sms 결제기한 추가 > LWH(2020-11-27)
      
      // ■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■
      // 동록/변경 소스 정리 하나부터 열까지 > LDH (2020-07-20)
  12. 주석으로 처리한 코드(*)

    가장 위험하다고 생각되는 예시!

    주석으로 처리된 코드는 다른사람들이 지우기를 주저한다! ex. "이유가 있겠지.."
    그렇게 점점 쌓여 질나쁜 코드가 되어간다.
    소스 관리 프로그램이 잘 되어있으므로 과감히 지우자!

    InputStreamResponse response = new InputStreamResponse();
    response.setBody(formatter.getResultStream(), formatter.getByteCount());
    //InputStream resultsStream = formatter.getResultStream();
    //StreamReader reader = new StreamReader(resultsStream);
    //response.setContent(reader.read(formatter.getByteCount()));
    • 이러한 나쁜 주석이 적용된 예시

      logger.info(">>> WSocket IP= " + hostname);
      logger.info(">>> WSocket PORT= " + port);
        			
      SocketAddress socketAddress = new InetSocketAddress(hostname, port);
      Socket socket = new Socket();
      socket.setSoTimeout(30000); //응답 타임아웃 
      socket.connect(socketAddress, 5000);//연결 타임아웃
      BufferedWriter bufWriter =new BufferedWriter(new OutputStreamWriter(socket.getOutputStream(), charset));
      bufWriter.write(data);
      bufWriter.newLine();
      bufWriter.flush();
      //BufferedReader bufReader =new BufferedReader(new InputStreamReader(socket.getInputStream(), charset));
      //reciveData = bufReader.readLine();
      //socket.close();
      //bufReader.close();
      //bufWriter.close();
        			
      InputStream is = socket.getInputStream();
      byte [] length = new byte[4];
      is.read(length);
  13. HTML 주석

    /**
     * <p>
     * 적합성 테스트를 수행하기 위한 과업
     * 이 과업은 적합성 테스트를 수행해 결과를 출력한다.
     * <p/>
     * <pre>
     * 용법 : 
     * &lt;taskdef name = &quot;execute-fitnesse-tests&quot;
     * classname = &quot;fitnesse.ant.ExecuteFitnesseTestsTask&quot;
     * ...
     * 그만 알아보자
     */
  14. 전역 정보

    주석을 달아야 한다면 근처에 있는 코드만 기술하라, 추후 코드가 변했을때 주석도 함께 변할 수 있어야 한다. (변할거라는 보장도 없다.)

    /**
     * 적합성 테스트가 동작하는 포트: 기본값은 8082
     *
     * @param fitnessePort
     */
    public void setFitnessePort(int fitnessePort) {
      this.fitnessePort = fitnessePort;
    }

    해당 코드에서 포트의 기본값을 전혀 통제하지 못한다.(기본값이 변했을때 이 주석도 함께 수정되지 않았을 가능성이 존재)

  15. 너무 많은 정보 (TMT, LA.Park)

    너무 장황한 정보는 정보 전체의 집중력을 떨어뜨린다.

    /*
    RFC 2045 - Multypurpost Internet Mail Extensions (MIME)
    1부 : 인터넷 메시지 본체 형식
    6.8절. Base64내용 전송 인코딩(Content-Transfer-Encoding)
    인코딩 과정은 입력 비트 중 24비트 그룹을 인코딩된 4글자로 구성된 출력문자열로 표현한다.
    이렇게 만들어진 허구의 헛소리들은 아무도 쳐다보지 않을 것이다. 각각은 base64 알파벳에서
    단일 자릿수로 해석된다.base64 인코딩으로 비트 스트림을 인코딩 할 때,
    비트 스트림은 MSB 우선으로 정되렬어 있다고 가한정다.
    따라서, 스트림에서 첫 비트는 첫 8비트 바이트에서 최상위 비트가 된다.
    */

    위 주석 예제에서 헛소리와 오타가 들어았다는 사실을 눈치 챘는가?

  16. 모호한 관계

    주석과 주석이 설명하는 코드는 관계가 명백해야한다.

    /*
     * 모든 픽셀을 담을 만큼 충분한 배열로 시작한다(여기에 필터 바이트를 더한다)
     * 그리고 헤더 정보를 위해 200바이트를 더한다
     */
    this.pngBytes = new byte[((this.width + 1) * this.height * 3 ) + 200];

    필터바이트란 무엇일까? +1은 왜 하는걸까, *3은 왜 있을까? 만약 옆에 이 함수 작성자가 있다면 이거 무슨 소리에요?라고 물어볼 것이다.

  17. 함수 헤더

    짧은 함수의 설명은 헤더로 남기기보다 의미있는 이름으로 작성한 함수가 훨씬 좋다.

  18. 비공개 코드에서 사용하는 Javadocs

    공개 API에서는 Javadocs가 유용하지만 그렇지 않다면 꼭 쓸필요는 없다. 코드가 더 산만해질 것이다.

Clone this wiki locally