【问题标题】:Why doesn't Eff have an arrow for the last return value为什么Eff没有最后一个返回值的箭头
【发布时间】:2016-12-01 00:03:50
【问题描述】:

优秀的PureScript book 解释说

fullName :: forall r. Record (firstName :: String, lastName :: String | r) -> String
fullName person = person.firstName <> " " <> person.lastName

然后比较Eff monad

import Prelude

import Control.Monad.Eff.Random (random)
import Control.Monad.Eff.Console (logShow)

main :: forall eff. Eff (console :: CONSOLE, random :: RANDOM | eff) Unit
main = do
  n <- random
  logShow n

我的问题是: 为什么main的签名在Unit之前没有-&gt;,即

main :: forall eff. Eff (console :: CONSOLE, random :: RANDOM | eff) -> Unit

这将使它类似于-&gt; String 的签名,就像fullName 的签名一样

同一章节的摘录(强调我的):

main 是一个有副作用的计算,它可以在任何 支持随机数生成和控制台 IO 的环境, 和任何其他类型的副作用,并且返回类型的值 单位

.

【问题讨论】:

  • 你明白Eff# ! -&gt; * -&gt; *是什么意思吗?
  • 一点。我重读了它,它确实告诉了我的理解。谢谢

标签: purescript


【解决方案1】:

两个函数之间的一个区别是fullName 有一个参数(在-&gt; 之前)。函数签名声明它需要一些记录并返回一个字符串。

main 不带任何参数,因为它是应用程序的“入口点”,它返回Eff。所以main 只返回 one 类型。该类型恰好有两个类型参数

函数参数和类型参数看起来很相似,但它们处于不同的层次。带参数的类型有一个构造函数,并应用它们的参数来生成实际类型。它看起来像函数应用程序,但在类型级别!类型的“签名”称为 kind...您可以了解更多信息,但可以将其视为“类型的类型”。

现在Eff 是一种结合了一些效果和一些“实际结果”的类型。它的构造函数应用效果行作为第一个参数,结果类型作为第二个参数。对于main,它所做的只是副作用,所以“实际结果”是Unit,基本上什么都没有。

如果main的签名是:

main :: forall eff. Eff (console :: CONSOLE, random :: RANDOM | eff) -> Unit

这意味着

  • Eff 只接受一些效果行作为类型参数(与Eff 的定义不匹配)
  • mainEff 作为参数(但它会来自哪里?)
  • main 只返回 Unit

【讨论】:

    猜你喜欢
    • 2018-01-27
    • 2016-05-07
    • 2020-09-30
    • 2020-02-07
    • 1970-01-01
    相关资源
    最近更新 更多