java - 是否可以用 Java 实现 `Functor<T>`?

标签 java haskell functor

我今天偶然发现了一个小问题。考虑一个小包装类:

class Event<T> {
   T value;
   Class<T> type;
   // other fields, getters and setters omitted for brevity
}

现在我想转换 Event<Long>进入 Event<String>同时保留其他字段并更新 type成员(member)。

最终我得到了最简单的“解决方案”:

Event<String> new = new Event(old.getValue().toString(), String.class, other, fields);

然而,在我的宠物项目中使用 Haskell,我自然渴望像 fmap :: Functor f => (a -> b) -> f a -> f b 这样的函数。 (阅读:给定一个从 a 到 b 的函数和一个包含 a 类型的东西的仿函数给我一个包含 b 的结果)并且在发现没有标准实现之后我开始自己写一个:

interface Functor<T> {
  Functor<S> fmap( Func1<T,S> f );
}

// ... in Event<T>:

Functor<S> fmap( Func1<T,S> f ) { 
  S newValue = f.call(this.value);
  return new Event( newValue, newValue.getClass(), other, fields);
}

现在这个解决方案有一个问题:在 Java 中调用 fmap 之后,我剩下一个类型为 Functor<String> 的实例。而 Haskell 中的相同函数将返回 Event<String> .

有没有办法得到我的Event返回(没有不安全地转换它)?

最佳答案

不,这是不可能的。为此,我们需要对界面中的 Functor 进行抽象,例如

interface Functor<T> as F<T> {
    F<S> map(f : Function<T, S>);
}

但 Java 不允许您抽象类型构造函数,只是类型。这称为高级类型 (HKT)。只有少数(非依赖)语言有 HKT,Scala 和 Haskell 是我能想到的仅有的两种。

其实HKTs是表达很多抽象的必要条件,

  1. Control.Monad
  2. 控制.应用
  3. Data.Traversable
  4. Data.Foldable
  5. Control.Monad.Trans
  6. 任何 monad 转换器,句号
  7. 免费单子(monad)
  8. 透镜/棱镜
  9. 流媒体库(它们是 monad 转换器)
  10. category-extras 中的几乎所有内容

所有这些都涉及对类型构造函数的抽象,而不仅仅是具体类型。

关于java - 是否可以用 Java 实现 `Functor<T>`?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22944661/

相关文章:

java - 有没有办法为 RESTful 堆栈生成样板代码?

java - log4j 1 到 log4j 2 属性文件

java - 为什么消息卡在安慰服务器上?

c++ - 将未实例化的模板名称传递到函数模板扩展中

java - 为什么ContextLoaderListener要在Log4jConfigListener之后注册

scala - promise 的反义词是什么?

haskell - 如何在 Haskell 中定义一个包含现有类型的枚举类型

haskell - 内函数作为幺半群

haskell - 在实践中使用单子(monad)、幺半群、仿函数和箭头

lambda - lisp 中的 bool 仿函数