在镜头中观看和使用有什么区别?
What's the difference between view and use in lens?
有什么区别
view :: MonadReader s m => Getting a s a -> m a
和
use :: MonadState s m => Getting a s a -> m a
看一下类型签名,view
取一个 MonadReader
(比如 ReaderT
),use
取一个 MonadState
(比如StateT
)。现在,view
和 use
都具有相同的 objective:从我们正在查看的事物中提取合理的值。
MonadReader
表示只读状态。我们可以使用 ask
. MonadState
represents read-write state, which can be retrieved with get
访问值。所以 view
和 use
都查询给定 monad 的内部状态,但是 view
调用 ask
而 use
调用 get
。一般来说,只有一个会适用于你的情况。
查看这两个函数的源代码并不是特别有启发性,除非您已经了解镜头是如何实现的(如果您了解了,那么您可能会理解 view
和 [=13= 之间的区别) ]), 所以这是一个很好的例子,说明类型签名比代码本身更有启发性。
A lens getter 给了我们一个从源到目标的函数:
(^.) :: s -> Getting a s a -> a
flip (^.) :: Getting a s a -> s -> a
任何函数都可以做成MonadReader
计算,函数的参数类型作为环境类型:
asks :: MonadReader s m => (s -> a) -> m a
既然如此,(^.)
可以推广到 MonadReader
到 asks
之间的任何一个,从而产生 view
:
view :: MonadReader s m => Getting a s a -> m a
view g = asks (\s -> s ^. g)
(我在这里使用的定义与您在 the Control.Lens.Getter
source 中找到的字面意思不同,但就结果而言它们是等价的。)
同理,任何函数都可以做成MonadState
状态不变的计算,函数的参数类型为状态类型:
gets :: MonadState s m => (s -> a) -> m a
因此,(^.)
也可以推广到 MonadState
到 gets
,结果是 use
:
use :: MonadReader s m => Getting a s a -> m a
use g = gets (\s -> s ^. g)
从另一个角度看,view
和use
分别可以看作是asks
和gets
的变体,以getter为参数,而不是直接一个函数。
关于 view
的最后一点说明,函数本身是 MonadReader
的实例。既然如此,view
可以用作 (^.)
.
的 prefix/non-operator 版本
有什么区别
view :: MonadReader s m => Getting a s a -> m a
和
use :: MonadState s m => Getting a s a -> m a
看一下类型签名,view
取一个 MonadReader
(比如 ReaderT
),use
取一个 MonadState
(比如StateT
)。现在,view
和 use
都具有相同的 objective:从我们正在查看的事物中提取合理的值。
MonadReader
表示只读状态。我们可以使用 ask
. MonadState
represents read-write state, which can be retrieved with get
访问值。所以 view
和 use
都查询给定 monad 的内部状态,但是 view
调用 ask
而 use
调用 get
。一般来说,只有一个会适用于你的情况。
查看这两个函数的源代码并不是特别有启发性,除非您已经了解镜头是如何实现的(如果您了解了,那么您可能会理解 view
和 [=13= 之间的区别) ]), 所以这是一个很好的例子,说明类型签名比代码本身更有启发性。
A lens getter 给了我们一个从源到目标的函数:
(^.) :: s -> Getting a s a -> a
flip (^.) :: Getting a s a -> s -> a
任何函数都可以做成MonadReader
计算,函数的参数类型作为环境类型:
asks :: MonadReader s m => (s -> a) -> m a
既然如此,(^.)
可以推广到 MonadReader
到 asks
之间的任何一个,从而产生 view
:
view :: MonadReader s m => Getting a s a -> m a
view g = asks (\s -> s ^. g)
(我在这里使用的定义与您在 the Control.Lens.Getter
source 中找到的字面意思不同,但就结果而言它们是等价的。)
同理,任何函数都可以做成MonadState
状态不变的计算,函数的参数类型为状态类型:
gets :: MonadState s m => (s -> a) -> m a
因此,(^.)
也可以推广到 MonadState
到 gets
,结果是 use
:
use :: MonadReader s m => Getting a s a -> m a
use g = gets (\s -> s ^. g)
从另一个角度看,view
和use
分别可以看作是asks
和gets
的变体,以getter为参数,而不是直接一个函数。
关于 view
的最后一点说明,函数本身是 MonadReader
的实例。既然如此,view
可以用作 (^.)
.