【问题标题】:How is `arr fst` a natural transformation?`arr fst` 是如何自然转换的?
【发布时间】:2020-08-28 18:43:24
【问题描述】:

我刚才问this question。这是关于以下箭头定律:

arr fst . first f = f . arr fst -- (.) :: Category k => k b c -> k a b -> k a c

Asad Saeeduddin 帖子下的 cmets 中以 自然变换 的方式对其进行了解释。我想检查一下我的解释是否正确,并与Bartosz Milewski's article on natural transformations进行比较。

所以,自然变换的定义如下:

我们有两个类别CD 和仿函数F, G : C ~> D。自然变换αD 中的一组箭头,这样:

  1. 这些箭头从F 的结果指向G 的结果。也就是说,对于C 中的每个对象a,都存在一个箭头(在a 处称为α组件α_a :: F a ~> G a
  2. 对于每个f :: a ~> bab 作为C 中的对象,保持:Gf . α_a = α_b . Ff。这就是自然。

基本上,我们需要弄清楚在我们的例子中是哪四个变量:CDFG

据我所知:

  • CD 是同一类别的任意类型,k a b 是其中的箭头,其中k 是我们正在使用的Arrow 实例。因此,FG 是内函子。

  • F(, c)GIdentity。换句话说,如果我们不再使用类型,我们将 F 映射到 first 并将 G 映射到 id考虑类型可能会更容易,因为 CategoryArrow 类帮助我们构造类别的箭头,而不是对象

这样对吗?

另外,Bartosz Milewski wrote those ideas down 是这样的:

fmap f . alpha = alpha . fmap f

据我所知,我们需要一个更通用的形式,因为这里alpha :: forall a. F a -> G a 只处理 Hask 作为它使用的类别。还是我错了?这张图fmap在哪个地方?

【问题讨论】:

  • 我认为你的 G 和 F 是错误的,但除此之外你是对的(包括关于“fmap”的更一般形式的东西)。 arr fst 的类型为 k (x, c) x,而不是 k x (x, c)
  • @AsadSaeeduddin 你是对的 - 谢谢。我编辑了帖子。
  • 看起来你现在的答案只是用不同的方式来表达你以前的,所以对我来说仍然是正确的。当你指定一个范畴时,你通常用它的态射来表征它,因为通常态射的规范最终决定了对象。如果我们说C 是一个“箭头类别”(就像你之前所做的那样),其中从对象ab 的态射是箭头类型k a b 的成员,我们隐含地结束了指定对象是任意类型 a, b, ...
  • 类似的经验法则适用于函子:函子的态射映射最终也指定了对象映射,因为你不能在没有定义后者的情况下编写前者。因此,除了出于美学原因之外,没有任何规定我们必须根据类型构造函数而不是它们的“fmap”操作(就像你之前所做的那样)在箭头类别上定义我们的 endofunctors。
  • 为了完整起见添加答案。即使在 cmets 和编辑之间,我怀疑您现在已经基本弄清楚了。

标签: haskell functor category-theory arrows


【解决方案1】:

据我所知:

  • CD 是同一类别的任意类型,k a b 是其中的箭头,其中k 是我们正在使用的Arrow 实例。 因此,FG 是内函子。

  • F(, c)GIdentity。换句话说,如果我们不再使用类型,我们将F 映射到first,将G 映射到id。 [...]

是的,就是这样。 arr fst :: k (b, c) b 中的kc 的每一个选择都为我们提供了(, c) 内函子和k 类别中的恒等函子之间的自然转换。执行特化为我们提供了一个看起来更像自然转换的签名:

arr @K (fst @_ @C) :: forall b. K (b, C) b

此外,Bartosz Milewski wrote those ideas down 像这样:

fmap f . alpha = alpha . fmap f

据我所知,我们需要一个更通用的形式来实现我们的目的 这里alpha :: forall a. F a -> G a 只处理 Hask 作为 它适用的类别。还是我错了? fmap在哪个地方 这张照片?

也正确。 fmap 必须被所涉及的函子的任何适当的态射映射替换。在您的示例中,它们恰好是 firstid,正如您之前注意到的那样,这使我们回到了我们一开始的箭头定律。

(至于替换fmapFunctor的方法从特定的函子态射映射中抽象出来,通过一个更一般的类比,这需要进行适当的安排,以便我们可以表达涉及非Hask的函子 Haskell 代码中的类别。您可能想看看constrained-categoriesdata-category 是如何处理的。)

【讨论】:

  • 感谢您的回答。什么是arr-category(1st 提取)?你的意思是k-category,k 是手头的Arrow 实例吗?
  • @ZhiltsoffIgor 没错。 (我的意思是写k-category;arr 有一个错字。)
  • 另外,你确定arr @K (fst @_ @C)的类型签名吗?首先,我看不出应用于一个参数的K 如何单独出现在类型签名中(如K a :: * -> *)。此外,GHCi 告诉我们:arr @K (fst @_ @C) :: K (c, C) c.
  • @ZhiltsoffIgor 那是另一个编辑错误。已修复,谢谢。
  • @ZhiltsoffIgor 虽然我在写答案时没有想到 subhask,但它的类别和仿函数类也是相关示例。至于弃用,我很确定它已被放弃。 subhask(值得注意的是,其范围比仅仅引入更通用的类别抽象要广泛得多)自 2015 年以来没有新版本,而 constrained-categories 是仍然积极维护。
【解决方案2】:

您无需担心额外的类别,因为arr fst 不涉及任意的Arrow,只是它的(,) 实例。

在 Haskell 中,对于某些函子 fc,类型为 f a -> g a 的函数是一种自然转换。在arr fst :: (b -> c) -> (b, c) 的情况下,让f ~ (->) bg ~ (,) b

【讨论】:

  • 这是什么意思“arr fst 不涉及任意的Arrow,只是它的(,) 实例”?
  • arr 在其签名中具有约束类型 Arrow a => a,但 arr fst 返回的函数没有。
  • 说实话,我非常怀疑。此外,当我输入:t arr fst 时,GHCi 告诉我的是:arr fst :: Arrow a => a (c, b) c
  • 顺便说一句,我认为(b -> c) -> (b, c) 类型是无人居住的,因为(B -> C) -> BC 不是重言式(检查B = FalseC = True)。直觉可能是我们无法在一般情况下应用函数参数。
  • 但是我可能只是误解了您的答案(可能是这种情况)。请您补充一点解释好吗?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-04-13
  • 2021-01-02
  • 1970-01-01
  • 2019-12-19
  • 2015-01-04
  • 1970-01-01
  • 2012-02-13
相关资源
最近更新 更多