标签: pointfree

在Haskell中将多个函数应用于相同的值无点样式

有一天我很无聊,想锻炼我的大脑,所以我决定做99个Haskell问题但是限制自己以无点的方式做这些.当我以无点样式执行操作时,似乎出现了很多问题:如何将多个函数应用于相同的值,同时将每个结果保持为独立实体?使用尖头符号:

foobar x = [id x, reverse x]
Run Code Online (Sandbox Code Playgroud)

到目前为止我用无点符号得出了什么:

foobar' = `map` [id, reverse] ($ x)
Run Code Online (Sandbox Code Playgroud)

我似乎无法x在那里结束.

haskell pointfree

27
推荐指数
4
解决办法
3264
查看次数

点免费代码更有效率,还是只是更简洁?

我编写了以下代码,它使用光泽库获取了一堆点并在屏幕上绘制它们.

let s = blocks pes
    pts = map (map mkPt) s  {- stitches to points-}
    lines = map Line pts    {-points to lines -}
    pict = Pictures lines   {- lines to a picture -}
  in do  displayInWindow "My Window" (200, 200) (10, 10) white pict
Run Code Online (Sandbox Code Playgroud)

它工作正常,但我发现有一个重复的模式:一个函数调用链,每个函数调用的结果进入下一个参数的最后一个参数.所以我通过删除中间变量,反转顺序并使用函数组合(".")链接函数来重构,如下所示:

let pict = Pictures . (map Line) . (map $ map $ mkPt) . blocks $ pes
                in do  displayInWindow "My Window" (200, 200) (10, 10) white pict
Run Code Online (Sandbox Code Playgroud)

令人高兴的是,这也很好.但是我想知道我是否会降低可读性,或者我是不是习惯于阅读和编写点免费样式代码.另外,我如何推理这段代码?第二个版本更有效率,还是仅仅更高效?有什么我可以风格化的做法让它更清晰吗?

refactoring haskell coding-style pointfree

25
推荐指数
1
解决办法
1245
查看次数

如何将两个参数的Haskell函数重写为无点样式

我在Haskell中有以下功能

agreeLen :: (Eq a) => [a] -> [a] -> Int
agreeLen x y = length $ takeWhile (\(a,b) -> a == b)  (zip x y)
Run Code Online (Sandbox Code Playgroud)

我正在努力学习如何编写'惯用'Haskell,它似乎更喜欢使用.$不是括号,并且在可能的情况下更喜欢无点代码.我似乎无法摆脱提及xy明确.有任何想法吗?

我认为我对点两个参数的任何函数都有同样的问题.

顺便说一下,这只是为了编写好的代码; 不是一些"使用任何必要的东西来使其无意义"的家庭作业.

谢谢.


(添加评论)感谢您的回答.你已经说服我这个功能不会从pointfree中受益.而且你也给了我一些很好的例子来练习转换表达式.这对我来说仍然很困难,而且它们似乎与Haskell一样重要,因为它指向C.

haskell pointfree

25
推荐指数
2
解决办法
5189
查看次数

组成功能组合:(.).(.)如何工作?

(.)采用两个函数,它们接受一个值并返回一个值:

(.) :: (b -> c) -> (a -> b) -> a -> c
Run Code Online (Sandbox Code Playgroud)

既然(.)两个参数,我觉得(.).(.)应该是无效的,但它完全没问题:

(.).(.) :: (b -> c) -> (a -> a1 -> b) -> a -> a1 -> c
Run Code Online (Sandbox Code Playgroud)

这里发生了什么?我意识到这个问题措辞严厉......所有的功能都只是因为讨论而采取了一个论点.也许更好的方式来说它是类型不匹配.

haskell currying pointfree

25
推荐指数
4
解决办法
1934
查看次数

减法的等价于(+1),因为(-1)被视为负数?

可能重复:
Currying减法

我开始了第一个不是来自教程的haskell项目,当然我偶然发现了最简单的东西.

我有以下代码:

moveUp y = modifyMVar_ y $ return . (+1)
moveDn y = modifyMVar_ y $ return . (-1)
Run Code Online (Sandbox Code Playgroud)

我花了一些时间来理解为什么我的代码不能编译:我曾经使用过(-1)这被认为是负面的.将减号括起来并没有帮助,因为它为它添加前缀并使其成为第一个参数.

简而言之,这点的免费版本是什么?

dec :: Num a => a -> a
dec x = x - 1
Run Code Online (Sandbox Code Playgroud)

haskell pointfree

23
推荐指数
2
解决办法
3569
查看次数

Scala中无点样式的情况

对于这里的FP认知来说,这看起来真的很明显,但Scala中的点自由风格有什么用呢?在这个主题上真正卖给我的是一个插图,它显示了点自由风格在某些方面(例如性能,优雅,可扩展性,可维护性)如何在非点自由风格中解决相同问题的代码.

functional-programming scala pointfree

22
推荐指数
2
解决办法
2506
查看次数

在Haskell中"重用"参数的伎俩?

我不时偶然发现我想要表达的问题"请使用两次最后一个参数",例如为了编写无点样式或避免使用lambda.例如

sqr x = x * x
Run Code Online (Sandbox Code Playgroud)

可写成

sqr = doubleArgs (*) where
   doubleArgs f x = f x x
Run Code Online (Sandbox Code Playgroud)

或者考虑这个稍微复杂的功能(取自这个问题):

ins x xs = zipWith (\ a b -> a ++ (x:b)) (inits xs) (tails xs)
Run Code Online (Sandbox Code Playgroud)

如果有这样的函数,我可以写这个代码pointfree:

ins x = dup (zipWith (\ a b -> a ++ (x:b))) inits tails where
     dup f f1 f2 x = f (f1 x) (f2 x)
Run Code Online (Sandbox Code Playgroud)

但是因为我在Hoogle中找不到像doubleArgs或dup这样的东西,所以我猜我可能会错过这里的伎俩或成语.

haskell coding-style pointfree

21
推荐指数
3
解决办法
2189
查看次数

21
推荐指数
2
解决办法
474
查看次数

Haskell地图/邮编Vs. 列表理解

您最有可能写下以下哪项?

r = zip xs $ map sqrt xs
Run Code Online (Sandbox Code Playgroud)

要么

r = [(x, sqrt x) | x <- xs]
Run Code Online (Sandbox Code Playgroud)

互联网上的示例代码似乎表明前者更为丰富且是首选方式.

zip haskell list-comprehension combinators pointfree

19
推荐指数
7
解决办法
6584
查看次数

在Haskell中没有点

我有这个代码,我想做点无关;

(\k t -> chr $ a + flip mod 26 (ord k + ord t -2*a))

我怎么做?

除了"想想这个和某些东西"之外,还有一些关于点自由风格的一般规则吗?

haskell coding-style pointfree

17
推荐指数
2
解决办法
4151
查看次数