我试图以递归方式定义ghci中的map.到目前为止我想出的是以下内容:
let mymap f (x:xs) = if null xs then [] else f x : map f xs
Run Code Online (Sandbox Code Playgroud)
我现在要做的是简化它并对代码中的列表进行硬编码,即编写一个map函数,该函数将函数作为参数并执行真实映射所做的但仅限于特定列表,例如[ 1,2,3,4,5].这样的事情可能吗?
首先,你的地图功能并不完全正确.如果我要输入mymap (+1) [1],我会期望[2]回来,但我会得到[].如果我尝试过mymap (+1) [],我的程序会因模式匹配失败而崩溃,因为您尚未定义该情况.相反,请考虑将您定义mymap为
mymap :: (a -> b) -> [a] -> [b]
mymap f [] = []
mymap f (x:xs) = f x : mymap f xs
Run Code Online (Sandbox Code Playgroud)
如果你想用if语句内联,那么你必须这样做
mymap f xs = if null xs then [] else f (head xs) : mymap f (tail xs)
Run Code Online (Sandbox Code Playgroud)
这些基本上是相同的,但在我看来,第一个更容易阅读.
如果你想用来mymap定义一个只映射到特定列表的函数,你可以很容易地做到这一点
mapOnMyList :: (Int -> b) -> [b]
mapOnMyList f = mymap f [1, 2, 3, 4, 5]
Run Code Online (Sandbox Code Playgroud)
或者以无点形式
mapOnMyList = (`mymap` [1, 2, 3, 4, 5])
Run Code Online (Sandbox Code Playgroud)
使用mymap作为中缀运算符.这相当于flip mymap [1, 2, 3, 4, 5],但操作符表单通常是首选,因为flip不一定可以自由执行.
您也可以使用列表推导来执行此操作:
mymap f xs = [f x | x <- xs]
Run Code Online (Sandbox Code Playgroud)
或者,如果您想对列表进行硬编码
mapOnMyList f = [f x | x <- [1, 2, 3, 4, 5]]
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1023 次 |
| 最近记录: |