레이블이 coding style인 게시물을 표시합니다. 모든 게시물 표시
레이블이 coding style인 게시물을 표시합니다. 모든 게시물 표시

2018-04-01

2018년 13번째 주

 이 포스팅은 그냥 지난 한 주간 읽었던 것들을 정리하는 포스트입니다. 그냥 예전에 봤던 글 중 나중에 필요한데 뭐였는지 기억 안 나는 글들이 있어서 쓰기 시작했습니다.
 보통 하는 일과 관련된 글들이 올라오겠지만 딱히 정해둔 주제는 없고, 그때그때 관심 있었던 것을 읽었기 때문에 지난주에 쓰인 글일 수도 있고 몇 년 전에 쓰인 글일 수도 있습니다.


정규 표현식에서 \d가 의미하는 것이 언어마다 다 다르다고 한다.

언어가 지원하는 문자열이 single byte문자열이면, \d가 [0-9]를 의미하는 것이 맞지만, 유니코드라면 [0-9] 이외의 문자열도 처리할 것을 고려했어야 한다. 그런 의미에서 파이썬 2의 string literal은 유니코드가 아니기 때문에 [0-9]를 처리하는 것이 이상하지 않지만, Java나 JavaScript처럼 유니코드 string literal을 지원하는 언어에서 \d를 [0-9]에만 대응하는 건 조금 안일한 결정이 아니었나 싶다


자바스크립트 디자인 패턴: RORO

RORO는 Receive an Object, Return an Object의 약자로, 이름 그대로 함수에 넘기는 인자와 함수가 넘기는 인자를 object로 하자는 것이다. 함수의 인자로 object를 넘기자는 것은 꽤 옛날부터 있었던 주장이다. 최소한 내가 처음 웹 개발을 했던 2009년경에는 이미 함수의 인자로 객체를 넘기는 패턴이 유행했다. 함수의 인자로 객체를 넘겼을 때의 장점은 두 가지로 정리할 수 있었다.

하나는 default parameter를 구현하기 쉽다는 것이다. EcmaScript 5까지는 default parameter가 없었다. Default parameter를 흉내 내기 위해서 Arguments를 이용해야 했는데, 몇 번째 인자가 무슨 의미를 가지는지 코드에 표현할 방법이 없기에 새 인자를 하나 추가할 때 실수할 확률이 높았다. 이를 object를 이용하면, property 이름이 있기 때문에 Arguments를 이용하는 것보다 읽고 수정하기 쉬운 코드를 만들 수 있었다. 이는 EcmaScript 6에서 default parameter가 추가됐기 때문에 지금은 크게 장점이 아니다.

두 번째 장점은 EcmaScript에 없는 named parameter를 구현할 수 있다는 것이다. EcmaScript에는 named parameter가 없기 때문에 인자 개수 차이에 따라 몇 번째 인자가 무엇을 의미하는지 다르게 해석하는 방법을 많이 사용한다. 하지만 이는 버그를 만들기 쉬운 코드이므로 좋은 방법은 아니다. 이것도 object를 사용하면, 손쉽게 구현할 수 있다.

인자를 객체로 넘기자는 주장은 많이 있었지만, 함수의 리턴 값을 객체로 하자는 주장은 과거에는 그리 흔한 주장이 아니었다. 함수의 종류에 따라 객체를 리턴하는 값이 특정한 객체로 묶기 쉬운 경우도 있었다. 그러나 이 값을 하나의 값이라고 부를지 리턴을 위해 객체로 묶었다고 부를지는 사람마다 다를 것이다.
하지만 EcmaScript 6 이후로는 전혀 관계없는 값을 하나로 묶어서 리턴하는 코드도 자주 보인다. EcmaScript 6에 들어온 destructuring assignment 덕분으로 보인다.


Coding is bad for you

코딩하다 보면 문제가 생길만한 상황이나 너무 사소한 것에 집착하게 되기 때문에 정신 건강에 해롭다는 글.

경험적으로 잘 짠 코드는 예상치 못한 상황에 대비할 수 있도록 짜인 코드였다. 그렇기 때문에 당연히 문제가 생겼을 때를 대비하는 프로그래머가 잘 하는 프로그래머일 것이고, 그들은 사소한 문제가 될만한 상황도 잘 잡아낸다. 이걸 못 하는 사람들은 아무리 빠르게 스펙에 맞게 코드를 짜더라도 절대 잘 한다는 소리를 들을 수 없다.

근데 이게 코딩을 하다 보면 사람이 그렇게 생각하게 되는지 원래 그런 사람들이 코딩을 잘하는 건지는 잘 모르겠다.


Avoid else early return

억지로 single point return을 만들기 위해 if/else를 쓰지 말고, early return이 가능한 지점에서는 최대한 빠르게 return 하자는 글이다. 경험상 single point return이 early return보다 장점을 가지는 경우는 C를 사용할 때밖에 없었다.
Early return이 문제가 되는 경우는 결국 함수 종료 시 특정 로직을 실행해야 하는데, return 문이 많이 있어서 실수로 로직을 빼먹는 경우다. 하지만 요즘 나오는 언어는 대부분 RAII가 되거나, finally block을 지원한다. 따라서 요즘 나온 언어를 사용하면 early return을 사용할 때의 문제점을 언어 차원에서 해결책을 제공하는 것이다.

아쉽게도 C에는 아직 RAII나 finally block에 해당하는 기능이 존재하지 않는다. 그래서 함수가 끝날 때 특정 코드를 실행시킬 방법이 없고, 이런 문제로 C에서는 single point return을 쓰는 게 더 안전할 수 있다. 그래서 지금도 리눅스 커널에서는 예외 처리나 리소스 해제 등을 위해 goto를 이용하여 single point return을 만드는 방법이 권장된다.

하지만 이는 C를 쓸 때의 예외적인 상황이고 대부분의 경우에는 early return이 더 좋다.


LG launches open source version of webOS

LG 스마트 워치나 스마트 티비에 들어가는 webOS의 오픈 소스 버전이 공개됐다는 소식.
webOS는 원래 Palm에서 만든 OS로 리눅스 커널 기반이라는 점에서 안드로이드나 iOS보다 잘 되기를 바랐지만 망한 OS다.
한 5년쯤 전에 LG가 인수했다는 말은 들었는데 LG가 이것저것에 사용해본 듯한데 결과적으로 점유율이 0%인 것을 보면 확실하게 망한 듯하다. 이제 와서 오픈 소스 버전을 공개한다고 하는데 딱히 기대는 안 된다. 오픈 소스라는 게 단순히 소스를 공개한다고 끝나는 것이 아니라 사용자로부터 꾸준한 피드백을 받으며 이루어지는 커뮤니티가 핵심인데, webOS에 피드백을 줄 사용자가 있을지, LG가 그런 커뮤니티를 운영할 능력이 있을지도 의문이다. 솔직히 webOS를 사는데 든 돈이 아까워서 손절하지 못 하고 있는 게 아닐까 싶다.


Key words for use in RFCs to Indicate Requirement Levels

영어를 못 해서 스펙 문서를 작성할 때 어떤 조동사를 써야 할지 헷갈릴 때가 있는데, 그때를 위해 Network Working Group에서 규정한 가이드라인이다.

  • MUST, SHELL, REQUIRED - 반드시 해야 하는 경우
  • MUST NOT, SHELL NOT - 절대 하면 안 되는 경우
  • SHOULD, RECOMMENDED - 근거가 있으면 안 해도 되는 경우
  • SHOULD NOT, NOT RECOMMENDED - 근거가 있으면 해도 되는 경우
  • MAY, OPTIONAL - 하든 안 하든 전체 동작에 문제가 없어야 하는 경우

2015-04-24

한줄짜리 코드에도 반드시 괄호를 써야한다.


http://www.reddit.com/r/ProgrammerHumor/comments/1rfstw/there_are_two_types_of_people/
 위의 meem에서 알 수 있듯이 프로그래머는 괄호를 같은 라인에 붙여 쓰는가 띄어 쓰는가 하는 별 중요하지 않은 것으로 끊임없이 논쟁을 벌이고 있다. 여기에  조건문뿐 아니라 함수의 선언에 괄호를 어디에 붙이는가 까지 해서 4가지 조합을 가지고 끊임없이 싸운다.


 뭐 나는 개인적으로 함수의 선언이나 조건문에 붙는 괄호를 한 라인에 붙여 쓰는 걸 선호하지만, 그에 대해서 딱히 내 의견을 강요하지 않는다. 그냥 프로젝트에서 기존에 쓰이던 것이나, 다른 팀원들이 원하는 스타일을 따른다.

 하지만 괄호에 관해서 절대 양보 못 하는 것이 하나 있다. 한 줄짜리 statement를 위해서 괄호를 사용할 것인가 말 것인가 하는 것이다. 이유를 알 수 없지만, 조건문이나 for 문에 한 줄짜리 statement가 들어갈 일이 있으면, 괄호를 생략하고 쓰는 사람들이 많다.


 괄호를 생략하는 사람들은 이것저것 이상한 주장을 한다. 쓸데없이 바이트를 낭비한다거나, 오히려 한 줄짜리 코드라는 것을 명시해주어야 한다거나, 이유 없이 타이핑할 이유가 없다거나, 뭐 이것저것 이유를 대는데 전부 20세기라면 의미 있을지도 모르지만, 지금이라면 전혀 의미 없는 이유다. 21세기에는 괄호를 생략할 이유가 전혀 없다. 오히려 괄호를 생략해서는 안되는 절대적인 이유가 있다.

 코딩할 때 언제나 버젼 컨트롤 시스템을 사용하기 때문이다. git을 사용하든 머큐리얼을 사용하든 심지어 subversion을 사용하든 상관없지만 어찌 됐든 코딩할 때는 언제나 버젼 컨트롤 시스템과 함께하며 소스의 변경을 추적한다. 이때, 괄호를 생략했던 한 문장의 코드가 여러 줄로 나누어지면 괄호를  해서 불필요한 변경사항이 두 코드의 diff에 나오게 된다. 이러한 불필요한 변경 이력이 코드에 나오는 것을 막기 위해서 한 줄의 코드에도 반드시 괄호를 써야 한다.

2014-10-31

[Scala] 함수 선언과 호출에서의 괄호 생략


 위에서 보듯이 Scala에서는 인자가 0개인 함수를 선언하거나 호출할 때 괄호를 생략할 수 있다.1) 컴파일 타임에 괄호 생략에 대해 아무런 제약도 하지 않고, 컴파일된 byte code에도 차이가 없다. 그렇다고 아무 괄호나 생략해도 되는 것은 아니다. 언어적으로는 괄호 생략에 관해 아무 제약을 하지 않지만, side-effect가 없을 때만 괄호를 생략하여야 한다.2)

 side-effect가 없는 함수에 대해서만 괄호를 생략하는 것은 함수가 선언된 모양만으로 그 함수가 하는 일을 추측할 수 있기 때문에 코드의 가독성을 높이는 데 도움이 된다. 그렇다면 어째서 컴파일 타임에 side-effect가 없는 함수에 대해서만 괄호를 생략할 수 있도록 강제하지 않을까?
 이유는 간단하다. 컴파일러가 함수가 side-effect가 있는지 없는지 구분할 수 없기 때문이다. Haskelmonad같은 개념을 도입하여 side-effect를 분리해 낼 수 있을지도 모르지만, Scala는 그런 개념을 도입하지 않고, 사용자에게 책임을 넘겼다.

 side-effect는 functional 프로그래밍에서 매우 중요한 부분이기 때문에 이것에 대한 책임을 프로그래머에게 넘겼다는 점에서, Scala의 안 좋은 부분이라고 평하는 사람도 있다. 하지만 나는 이 정도 자유는 프로그래머에게 넘기는 것이 적당하다고 생각한다.

 예를 들어, 무언가 side-effect가 없는 일을 하는 함수가 있을 때 그 함수가 호출되면 logging을 하도록 수정하였다고 생각해보자. 이 함수는 side-effect가 있는 함수라고 봐야 할까? side-effect가 없는 함수라고 봐야 할까? 엄밀한 의미에서 따져본다면 side-effect가 있는 함수라고 분류해야겠지만, 실제 돌아가는 logic을 생각해보면 이 함수를 side-effect가 있다고 구분하는 것은 뭔가 억울(?)하다.

1) http://docs.scala-lang.org/style/method-invocation.html#arity-0
2) http://docs.scala-lang.org/style/naming-conventions.html#parentheses