消除Haskell透镜中的“翻转”
我在试着掌握镜头的窍门。有没有更惯用的方法来写下面的内容?(前面带有下划线的占位符)消除Haskell透镜中的“翻转”,haskell,idioms,haskell-lens,lenses,Haskell,Idioms,Haskell Lens,Lenses,我在试着掌握镜头的窍门。有没有更惯用的方法来写下面的内容?(前面带有下划线的占位符) 翻转(设置镜头)\u a。fmap\u f 对我来说,flip的使用似乎暗示了非惯用代码。在这种情况下,有没有更好的组合器可以避免翻转?在“ fMAP?>P>”中,是否有更多类似镜头的方式,在这种情况下,您可能需要考虑编写指向“”的方法。 \x->\u a&\u镜头~fmap\u f x 这让我觉得更习惯 如果您确实希望它不带翻转,而是无点的,您可以将上述内容转换为无点: (_a&)。设置镜头。fmap\u
翻转(设置镜头)\u a。fmap\u f
对我来说,
flip
的使用似乎暗示了非惯用代码。在这种情况下,有没有更好的组合器可以避免翻转
?在“<代码> fMAP?>P>”中,是否有更多类似镜头的方式,在这种情况下,您可能需要考虑编写指向“”的方法。
\x->\u a&\u镜头~fmap\u f x
这让我觉得更习惯
如果您确实希望它不带翻转
,而是无点的,您可以将上述内容转换为无点:
(_a&)。设置镜头。fmap\u f
(虽然从技术上讲,由于
&
相当于翻转($)
,您实际上只是隐藏了翻转
)我认为@DDub已经涵盖了您问题的前半部分。至于集成fmap
的更“像镜头”的方式,这似乎是一个更普遍问题的特例。如果我有一个二传手:
> (1,"a") & _1 .~ True
(True,"a")
然后我想应该有一个组合器让我可以写:
> (1,"a") & _1 . applying not .~ True
(False,"a")
此组合符似乎不存在于镜头中(除非其他人可以发现),但您可以将其定义为:
applying :: Functor f => (a -> b) -> (c -> f a) -> (c -> f b)
applying f = (fmap f .)
或者使用(>)r
的Functor
实例:
applying :: Functor f => (a -> b) -> (c -> f a) -> (c -> f b)
applying = fmap . fmap
这就引出了一个有趣的事实:二传手:
_lens . (fmap . fmap . fmap) _f
将\u lens
与fmap\u f
的应用相结合,从而产生等效的结果:
ex1 = (flip (set _1) ("a","b") . fmap not) $ Just True
ex2 = ("a","b") & _1 . applying (fmap not) .~ Just True
ex3 = ("a","b") & _1 . (fmap . fmap . fmap) not .~ Just True
-- all the above yield: (Just False,"b")
你一定会让你的朋友感到惊讶。如果你扩展/完成这个例子,回答起来会更容易。我的收获是,我没有遗漏什么严重的东西。我想我的朋友会说,那不是英语,而且有很多标点符号…:->