함수형 프로그래밍에 대해 알아보다보면 모나드 얘기가 참 많이 나옵니다. 함수형 프로그래밍에서 모나드가 어떤 개념을 말하는지 알아보도록 하겠습니다.
수학적 대상
수학적인 구조를 말합니다. 정수, 자연수, 행렬, 집합, 군, 환 체, 카테고리 등등 입니다.
범주(카테고리)
위키백과를 보고 정리 해봤습니다. 범주는 아래의 내용으로 구성된다고 합니다.
- 수학적 대상의 모임
- 범주 안의 대상 A, B에 대하여 A를 정의역으로, B를 공역으로 하는 사상(morphism)의 모임
- 프로그래밍 입장에서 사상은 꼭 범주 안의 대상 A, B를 정의역, 공역으로 할 필요는 없습니다.
- 사상은 합성 가능합니다. (해당 사상을 수행하는 모든 집합의 곱집합)
- 항등 사상이 존재 합니다.
- 결합법칙을 만족 합니다.
- 항등원이 존재 합니다.
입니다.
사상(morphism)은 뭘까?
정의역에서 공역으로 연결하는 것을 사상 이라고 한다. f: 자연수 -> 자연수 는 자연수에서 자연수로 연결하는 사상 이라고 말합니다. 프로그래밍적으로 생각해본다면 아래 morphism 함수는 string -> number로 연결하는 사상이겠네요
function morphism(text: string): number {
return string.length;
}
text가 뭐가 들어올진 모르지만 좌우지간 숫자로 바뀝니다. 이게 사상 입니다.
함자(functor)
위키백과를 보고 정리 해보았습니다.
C와 D가 범주라 할때 C와 D사이의 함자 F: C->D는 아래의 내용으로 구성되어 있다.
- C의 임의의 대상 X에 대응되는 D의 대상 F(X)
- C의 임의의 사상 f: X->Y에 대해 대응되는 D의 사상 F(f): F(X)->F(Y)
- 항등사상의 보존
- 사상합성의 보존
입니다.
이해한대로 풀어 써보면
- 함자는 사상(함수)를 인자로 받습니다.
- 함자는 범주 C의 임의의 대상을 D의 대상이 존재 합니다.
- 함자는 범주 C의 임의의 사상을 D의 사상이 존재 합니다.
이것도 와닿지 않습니다. 프로그래밍 입장에서 살펴보겠습니다.
const arr = [1, 2, 3, 4];
const morphism = (e) => e + 1
const identity = (e) => e // 항등사상
const result = arr.map(morphism) // [2, 3, 4, 5]
map 함수는 무엇일까요? map 함수가 바로 함자 입니다.
map 함수의 정의인 'map 함수를 통해 받은 함수의 파라미터로 어떤 배열의 모든 값을 하나씩 넣어 실행하고 그 결과들을 새로운 배열에 담아 리턴한다' 만으로 우리는 map 함자를 갖고있는 어떤 범주에 대해 유추할 수 있습니다. 네 맞습니다. 그 범주는 배열 입니다. 자연히 arr과 result가 하나씩 대응된다는 것도 map 함수의 정의에 따라 알 수 있습니다.
우리가 사실 공부 할때는 'Array prototype에 map 함수가 있다' 고 배우지만, 수학적인 의미로는 'Array prototype의 map 함자의 정의에 따라 배열에서 배열로 대응하는 함수다.' 가 더 자연스럽습니다.
따라서 함자로부터 범주를 유추하고 범주의 성질도 알 수 있습니다(우리 입장에서는 length, forEach 등등의 속성과 메서드 입니다)
드디어 모나드, 모나드는 자기함자(endofunctor)입니다.
위의 코드를 재탕하겠습니다. map 함자는 배열 범주에서 배열범주로 대응 한다고 하였습니다.
const arr = [1, 2, 3, 4];
const morphism = (e) => e + 1
const result = arr.map(morphism) // [2, 3, 4, 5]
위와 같이 같은 범주로 대응하는 것을 모나드라고 합니다. 정의역과 공역이 같은 함자 입니다.
사실 배열 말고도 여러가지 모나드가 더 있습니다. 아래 코드를 보면
Promise.then(()=>{ ... }).then(()=>{ ... }).then(()=>{ ... }))
Promise도 역시 then을 함자로 갖고있는 모나드 입니다.
주어진 모나드 말고 우리가 직접 만들수도 있습니다. 앞으로 함수의 합성과 몇 가지 유명한 모나드들의 코드와 설명을 올려보도록 하겠습니다.
이 내용을 몰라도 함수형 프로그래밍을 하는 것과 상관은 없습니다.
하지만 우리가 무심코 쓰는 것들이 어떤 의미를 갖는지 생각해보는 것은 의미가 있다고 생각 합니다.
(이 글은 제 과거 블로그 글을 다시 정리하여 쓴 글입니다. 지식이 일천하여 틀린곳이 있을 수 있습니다.)
'프로그래밍' 카테고리의 다른 글
#4 부수효과 (0) | 2022.04.08 |
---|---|
#3 maybe 모나드와 either 모나드 (0) | 2022.04.08 |
#2 함수의 합성 (0) | 2022.04.07 |
CSS 적용 우선순위 (0) | 2022.04.06 |
typescript - enum 값에 따라 함수 타입 설정하기 (0) | 2022.04.05 |