Defer를 이용한 코딩 패턴 - Deferred closure
페이스북의 GOLang 커뮤니티에서 아래의 글이 링크되었다.
해당 글은 defer에 대해 매우 쉽게 잘 설명해주고 있다.
내용중에 인상적인 부분은 Deferred closure 이다.
최근 텍스트파일을 읽어서 데이터 분석을 했었다.
분석시 해당 데이터 전체의 시작과 끝점을 기록할 필요가 있었다.
문제는 끝점이 정확히 검색이 되는 경우이지만 그렇지 않은 경우 여러 조건절을 통해 끝점을 찾아야 한다.
나쁜 경우는 내용전체를 돌면서 최종 기록을 끊임없이 반복하여 기존 변수에 할당해야 하는 것이다.
for err != io.EOF {
if xxxx { ...... ......
(CarsInfo[lID][dDate][rNo]).endTime = "20" + string(lines[11:23])
beforeSpeed = nowSpeed
}
n, err = rc.Read(lines) } // 마지막 라인 if xxx { (CarsInfo[lID][dDate][rNo]).endTime = "20" + string(lines[11:23]) }
이런 경우 deferred closure를 사용하면 성능을 좋게하면서 코드를 깔끔하게 할 수 있다.
위의 링크의 예제코드이다.
defer func() 내에서 조건문을 사용하여 작업을 할수도 있고 정해진 구조라면 마지막의 일부 데이터만 추출하여 사용할 수 있다.
만약 for 루프가 10000번 실행된다면 10000번의 할당작업의 성능을 아낄수 있다.
defer func () {
(CarsInfo[lID][dDate][rNo]).endTime = "20" + string(lines[11:23])
}()
for err != io.EOF {
if xxxx {
......
......
beforeSpeed = nowSpeed
}
n, err = rc.Read(lines)
}
현재 개인적으로 개발한 분석 코드에서의 수정 결과를 체크해보자.
할당에 대한 CPU 타임은 크지 않으므로 아주 큰 효과는 없으리라 본다.
테스트 환경 / 결과
12코어(TOP 표기상 24코어)중 절반 사용
평소 100% idle (완벽히 노는 서버)
worker 20개로 버퍼채널 이용
20398개의 ZIP 파일을 zip package를 이용해서 압축을 풀면서 분석
캐쉬 상황을 고려하여 번갈아가며 3회 반복(압축을 풀면서 작업하기에 캐쉬관련 이슈는 없지 싶지만서도...)
평균 15초 이상 줄어든다
기존 코드 결과
job ends. execute time: 3m14.353966626s
job ends. execute time: 3m16.453676824s
job ends. execute time: 3m15.367271724s
deferred closure 사용 결과
job ends. execute time: 3m0.899630867s
job ends. execute time: 2m59.410079684s
job ends. execute time: 2m52.597714407s
결론
꽤 괜찮다. 적극적으로 사용할만한 패턴이라 생각된다.
'프로그래밍??? > Go Lang' 카테고리의 다른 글
JetBrains의 GoLand EAP 2017.03 업버전시 발생한 이슈 (0) | 2017.11.24 |
---|---|
필드 이름 없이 선언하는 것을 막아주는 방법 (0) | 2017.10.11 |
GOLANG 첫번째 프로젝트 완료! (0) | 2017.02.06 |
read binary data from binary file and copy to struct (0) | 2017.02.01 |
인터페이스와 메서드 집합 그리고 포인터 (0) | 2017.01.12 |