用于序列计算的函子
Functor for sequence computation
我正在阅读 underscore.io 的 scala cats 书。它说了以下关于 Monad 和 Functor 的内容:
While monads and functors are the most widely used sequencing data
types..
我可以看到 Monad 正在用于排序数据,但 Functor 根本没有。有人可以展示关于仿函数的排序计算吗?
Seq(1, 2, 3).map(_ * 2).map(_.toString).foreach(println)
此处:您对一系列数据进行了一系列操作。
每个 monad 实际上都是一个仿函数,因为您可以 implement map with flatMap 和 unit/pure/whatever 您的实现调用它。因此,如果您同意 monad 是 "sequencing data types",那么您应该同意仿函数也是它们。
如果断章取意,这个说法就不太清楚了。
引用的完整版本是:
While monads and functors are the most widely used sequencing data types
[...], semigroupals and applicatives are the most general.
此声明的目的不是消除 "sequencing" 的函子和单子概念之间的差异,而是将它们与 Semigroupal
提供的明显 non-sequential 操作进行对比。
Functor
和 Monad
都支持(不同的)类型 "sequencing"。
给定一个 x
类型 F[X]
的值 F
和一些类型 X
,我们可以 "sequence" pure 函数
f: X => Y
g: Y => Z
像这样:
x map f map g
你可以叫这个"sequencing",至少"elementwise"。关键是 g
必须等到 f
产生至少一个 y
类型的 Y
才能做任何有用的事情。然而,这并不意味着 f
的所有调用必须在 g
首次调用之前完成,例如如果 x
是一个长列表,则可以并行处理每个元素 - 这就是我将其命名为 "elementwise".
的原因
对于表示单子效果的单子,通常会更认真地对待 "sequencing" 的概念。例如,如果您正在使用 M[X] = Writer[Vector[String], X]
类型的值 x
,并且您有两个具有 "writing"-effect
的函数
f: X => M[Y]
g: Y => M[Z]
然后像这样对它们进行排序:
x flatMap f flatMap g
您确实希望 f
完全完成,直到 g
开始将任何内容写入 Vector[String]
类型的日志。所以在这里,这实际上只是 "sequencing",没有任何 fine-print.
现在,将其与 Semigroupal
进行对比。
假设F
是半群的,即我们总是可以从F[A]
和F[B]
组成一个F[(A,B)]
。给定两个函数
f: X => F[A]
g: X => F[B]
我们可以构建一个函数
(x: X) => product(f(x), g(x))
returns 结果类型 F[(A, B)]
。请注意,现在 f
和 g
可以完全独立地处理 x
:不管它是什么,它肯定是 不排序 。
类似地,对于 Applicative
F
和函数
f: A => X
g: B => Y
c: (X, Y) => Z
和两个独立的值a: F[A]
、b: F[B]
,你可以用f
和g
完全独立地处理a
和b
,然后将最后的结果与 c
组合成一个 F[Z]
:
map2(a, b){ (a, b) => c(f(a), g(b)) }
同样:f
和 g
对彼此的输入和输出一无所知,他们完全独立地工作,直到最后一步 c
,所以这又不是"sequencing".
我希望它能在一定程度上澄清区别。
我正在阅读 underscore.io 的 scala cats 书。它说了以下关于 Monad 和 Functor 的内容:
While monads and functors are the most widely used sequencing data types..
我可以看到 Monad 正在用于排序数据,但 Functor 根本没有。有人可以展示关于仿函数的排序计算吗?
Seq(1, 2, 3).map(_ * 2).map(_.toString).foreach(println)
此处:您对一系列数据进行了一系列操作。
每个 monad 实际上都是一个仿函数,因为您可以 implement map with flatMap 和 unit/pure/whatever 您的实现调用它。因此,如果您同意 monad 是 "sequencing data types",那么您应该同意仿函数也是它们。
如果断章取意,这个说法就不太清楚了。
引用的完整版本是:
While monads and functors are the most widely used sequencing data types [...], semigroupals and applicatives are the most general.
此声明的目的不是消除 "sequencing" 的函子和单子概念之间的差异,而是将它们与 Semigroupal
提供的明显 non-sequential 操作进行对比。
Functor
和 Monad
都支持(不同的)类型 "sequencing"。
给定一个 x
类型 F[X]
的值 F
和一些类型 X
,我们可以 "sequence" pure 函数
f: X => Y
g: Y => Z
像这样:
x map f map g
你可以叫这个"sequencing",至少"elementwise"。关键是 g
必须等到 f
产生至少一个 y
类型的 Y
才能做任何有用的事情。然而,这并不意味着 f
的所有调用必须在 g
首次调用之前完成,例如如果 x
是一个长列表,则可以并行处理每个元素 - 这就是我将其命名为 "elementwise".
对于表示单子效果的单子,通常会更认真地对待 "sequencing" 的概念。例如,如果您正在使用 M[X] = Writer[Vector[String], X]
类型的值 x
,并且您有两个具有 "writing"-effect
f: X => M[Y]
g: Y => M[Z]
然后像这样对它们进行排序:
x flatMap f flatMap g
您确实希望 f
完全完成,直到 g
开始将任何内容写入 Vector[String]
类型的日志。所以在这里,这实际上只是 "sequencing",没有任何 fine-print.
现在,将其与 Semigroupal
进行对比。
假设F
是半群的,即我们总是可以从F[A]
和F[B]
组成一个F[(A,B)]
。给定两个函数
f: X => F[A]
g: X => F[B]
我们可以构建一个函数
(x: X) => product(f(x), g(x))
returns 结果类型 F[(A, B)]
。请注意,现在 f
和 g
可以完全独立地处理 x
:不管它是什么,它肯定是 不排序 。
类似地,对于 Applicative
F
和函数
f: A => X
g: B => Y
c: (X, Y) => Z
和两个独立的值a: F[A]
、b: F[B]
,你可以用f
和g
完全独立地处理a
和b
,然后将最后的结果与 c
组合成一个 F[Z]
:
map2(a, b){ (a, b) => c(f(a), g(b)) }
同样:f
和 g
对彼此的输入和输出一无所知,他们完全独立地工作,直到最后一步 c
,所以这又不是"sequencing".
我希望它能在一定程度上澄清区别。