함수형 프로그래밍이 소개된건 이미 오래 지났는데 최근에는 함수형 없이는 제대로된 개발을 할 수 없을정도로 주요 개발도구들의 언어에서 도입하여 사용하게 해주고 있는 형편이다. 이제 함수형을 사용하지 않고는 프로그래밍이나 개발을 한다고 말할수 없게 될지도 모른다.
함수형 프로그래밍은 이전의 값 중심에 비해 이해하기가 어려운데 체계적인 설명도 부족하고 일일이 수집해서 왜 이렇게 설명하는가 맥을 짚어가면서 이해해야 하는 어려운 점이 많다. 게다가 최악은 진도가 늦다는 이유로 빨리 설명하고 넘어가거나 쉽게 설명해준다는 명분으로 함수형을 건드리는 것을 회피하는 성향마저 있는 실정이다.
결국 함수형의 특징과 장점을 이해하기 위해서는 많은 단서를 수집해서 최대한의 이해력으로 접근할 수밖에 없는데 많은 학생들이 프로그래밍 개발 코딩을 접한후로 포기하게 되는 주된 요인일 것이다.
이미지를 걸지 않으면 블로그 홈에서 이미지가 없다는 표시를 내는 이미지를 따로 주기때문에 이미지를 하나 넣고 본론을 이야기하겠다.
haskell 홈페이지. 이런데 흥미를 가지게 된다면 한가지를 깨닫게 된다. 아름다움을 추구함에는 고통이 반드시 따른다.
http://www.haskell.org
리스프에는 스키마 클로저 커먼리스프, 이맥스리스프와 같은 사투리가 다수 있다. 대신 규격이 통일된 하스켈로 했다. 리스프는 haskell에 비하면 훨씬 쉽게 배울수 있으나 둘다 어느정도 안다는 전제하에서나 쉽다는 말이 나오지 함수형을 모르고서는 둘다 어렵기는 마찬가지다.
함수형은 함수를 값처럼 사용할 수 있게 한다. 함수는 일급객체인데 할당될 수 있고 인자로 사용할 수 있으며 반환될 수 있다. 따라서 보통 값처럼 보이거나 값이 입력될 영역에 함수가 들어가 있다면 함수형이 적용되어 있는것이다.
함수를 값처럼 넘기면 전역변수 등 외부에서 함수 내부로 끌어들이지 않게 하고 콜백함수를 이용한 연쇄적인 처리가 가능하다. 이는 커링(curring)과 연관이 있는데, 값을 반환하면 그자리에서 값이 확정되어 버리기 때문에 매개변수가 맞지 않거나 할때 에러를 야기시키기도 하고 유연한 처리를 하는데 한계를 보이는 것을 함수형으로 넘겨 값이 확정되지 않더라도 에러 없이 처리할 수 있게 하는 것이다. (예전 자바스크립트에서는 바인드와 콜백을 이용하기도 했다)
함수는 외부에서 내부를 알 수 없다. 이를 이용하여 지연처리(Lazy evaluation)할 수 있고 나중에 연쇄된 함수에서 비로소 값을 취하게 될때 그제서야 연산을 시작하여 일일이 다 계산하는 시스템 낭비를 절감시켜 주는 것이다. 함수의 연쇄 이부분도 함수형의 주요 특징이나 개발자 대부분은 아무렇지도 않게 쓰고 있다.
함수를 반환한다는 것은 처음부터 모든 프로그래밍 언어가 도입한 것이 아니고 좀더 유연한 기법을 활용하기 위해 람다(lambda)식을 활용해왔다. 람다함수는 함수를 반환하는데 이를 이용해서 값 반환으로 끝날 함수를 위와같은 처리를 할수 있도록 해준다.
이런 처리과정에서 복잡하거나 반복되는 흐름을 디자인 패턴으로 극복하는 것 중에서 모나드(monad)가 있는데 모나드로 복잡한 코드를 연산자 수준으로 정리할 수 있게 해주는데 (이 과정에서 코드가 절차적 코드가 일절 분리되어 순수한 함수의 연계만 남게되는 아름다운? 코드를 탄생시킨다) 그런 모나드의 기능을 그냥 일반적인 코드로 작성하게 된다면 많은 중복코드와 에러처리로 곤란한 과정에 처할수도 있다. 모나드를 통해 모나드는 하스켈(haskell)을 통해 처음으로 널리 알려졌고 자바스크립트에서 지원하는 Promise 객체가 모나드의 일종이다.
리스프 매크로나 하스켈 모나드를 들여다보고 있으면 마치 자신이 매크로나 모나드가 된것같은 기분이 든다.
함수형 프로그래밍에서 어려운점을 이렇게 공개하는건 다른 주제들을 다루기 위해 미리 기록해 두는것이다. 수시로 함수형 관련된 주제를 devnote에서 소개할 계획으로 다른 글에서는 부분적으로 다루겠지만 이 설명을 각 주제마다 일일이 해주지는 않을것이다.