# Comprehension 表示

February 2, 2022

## map 與 filter

List Comprehension 能做到 `map` 函式的功能，例如 `map (+ 3) [1, 2, 3, 4, 5]`，也可以使用 `[x + 3 | x <- [1, 2, 3, 4, 5]]`，也能使用 List Comprehension 來實作 `map'` 函式：

``````map' :: (a -> a) -> [a] -> [a]
map' mapper lt = [mapper elem | elem <- lt]
``````

``````filter' :: (a -> Bool) -> [a] -> [a]
filter' predicate lt = [elem | elem <- lt, predicate elem]
``````

## 更多 List Comprehension

``````leng :: [a] -> Int
leng lt = sum [1 | _ <- lt]
``````

``````[[a, b, c] |
a <- [1..10], b <- [1..10], c <- [1..10],
a <= b, b <= c]
``````

List Comprehension 可以列舉多個 list，只要以 `,` 做區隔，接下來加上直角三角型定義：

``````[[a, b, c] |
a <- [1..10], b <- [1..10], c <- [1..10],
a <= b, b <= c,
a ^2 + b ^ 2 == c ^ 2]
``````

## 命令式？宣告式？

``````var tris = new ArrayList<List<Integer>>();
range(1, 11).forEach(a -> {
range(1, 11).forEach(b -> {
range(1, 11).forEach(c -> {
if(a <= b && b <= c && a * a + b * b == c * c) {
}
});
});
});
``````

``````[x * 100 + y * 10 + z|
x <- [1..9], y <- [0..9], z <- [0..9]]
``````

``````[x * 100 + y * 10 + z|
x <- [1..9], y <- [0..9], z <- [0..9],
x ^ 3 + y ^ 3 + z ^ 3 == x * 100 + y * 10 + z]
``````

List Comprehension 中可以使用 `let`，例如，可以令 `x * 100 + y * 10 + z``number`，這樣就不用重複計算這個算式了：

``````[number|
x <- [1..9], y <- [0..9], z <- [0..9],
let number = x * 100 + y * 10 + z,
x ^ 3 + y ^ 3 + z ^ 3 == number]
``````

``````var numbers = new ArrayList<Integer>();
range(1, 10).forEach(x -> {
range(0, 10).forEach(y -> {
range(0, 10).forEach(z -> {
var number = x * 100 + y * 10 + z;
if(x * x * x + y * y * y + z * z * z == number) {