java中的方法求和_在Java中模拟求和类型的巧妙解决方法
java中的方法求和
在继续阅读实际文章之前,我想感谢令人敬畏的Javaslang库的作者Daniel Dietrich ,他在我面前有了这个主意:
@lukaseder尝试使用静态方法<T,T1扩展T,... Tn扩展T> Seq <T> toSeq(T1 t1,…,Tn tn){…}(从我的手机中……)
— Daniel Dietrich(@danieldietrich) 2016年2月16日
逆变通用界
这一切都始于一条推文:
您是否不想用Java编写<T super T1&T2&…&TN>?
— Lukas Eder(@lukaseder) 2016年2月16日
我想做一些事情,像模式匹配一组类型的一个普通的超级类型,方法如下:
<T super T1 | T2 | ... | TN>
请注意,我真正想要的是对联合类型的支持,而不是我最初声称的交集类型。
我为什么要这样做? 因为它将很好地添加到jOOλ库中 ,该库具有Java的类型安全元组 :
class Tuple3<T1, T2, T3> {final T1 v1;final T2 v2;final T3 v3;// Lots of useful stuff here
}
在元组中最好的是迭代所有属性的forEach()
方法:
tuple(1, "a", null).forEach(System.out::println);
上面将简单地产生:
1
"a"
null
现在,此forEach()
方法的参数类型是什么? 它看起来像这样:
class Tuple3<T1, T2, T3> {void forEach(Consumer<? super T1 | T2 | T3> c) {}
}
消费者将收到类型为T1 或 T2 或 T3的对象。 但是接受前面三种类型的普通超级类型的消费者也可以。 例如,如果我们有:
Tuple2<Integer, Long> tuple = tuple(1, 2L);
tuple.forEach(v->System.out.println(v.doubleValue()));
上面的代码可以编译,因为Number
是Integer
和Long
的常见超类型,并且它包含doubleValue()
方法。
不幸的是,这在Java中是不可能的
Java当前仅对异常捕获块支持联合/求和类型( 另请参见代数数据类型 ),您可以在其中编写以下内容:
class X extends RuntimeException {void print() {}
}
class X1 extends X {}
class X2 extends X {}// With the above
try {...
}
catch (X1 | X2 e) {// This compiles for the same reasons!e.print();
}
但是不幸的是,catch块是Java中唯一允许使用求和类型的地方。
这是Daniel巧妙而狡猾的解决方法发挥作用的地方。 我们可以编写一个静态方法来使用泛型执行某种“模式匹配”(如果您斜视),反之亦然:
static <T, T1 extends T, T2 extends T, T3 extends T
>
void forEach(Tuple3<T1, T2, T3> tuple, Consumer<? super T> consumer
) {consumer.accept(tuple.v1);consumer.accept(tuple.v2);consumer.accept(tuple.v3);
}
现在可以安全地使用以上方法来推断T1,T2和T3的公共超级类型:
Tuple2<Integer, Long> t = tuple(1, 2L);
forEach(t, c -> {System.out.println(c.doubleValue());
});
符合预期:
1.0
2.0
这是有道理的,因为泛型类型约束是简单地“相反地”指定的,即当T1 extends T
强制T1 extends T
,强制是T super T1
…
如果你真的很quin眼;-)
据说Daniel在Javaslang即将推出的模式匹配API中使用了此技术。 我们期待看到这一结果!
翻译自: https://www.javacodegeeks.com/2016/02/ingenious-workaround-emulate-sum-types-java.html
java中的方法求和
java中的方法求和_在Java中模拟求和类型的巧妙解决方法相关推荐
- 在Java中模拟求和类型的巧妙解决方法
在继续阅读实际文章之前,我想感谢令人敬畏的Javaslang库的作者Daniel Dietrich ,他在我面前有了这个主意: @lukaseder尝试使用静态方法<T,T1扩展T,... Tn ...
- 【源码+图片素材】Java王者荣耀游戏开发_开发Java游戏项目【王者荣耀】1天搞定!!!腾讯游戏_Java课程设计_Java实战项目_Java初级项目
王者荣耀是当下热门手游之一,小伙伴们是否想过如何制作一款属于自己的王者荣耀游戏呢? 本课程讲解了一个王者荣耀游戏的详细编写流程,即使你是刚入门Java的新手,只要你简单掌握了该游戏所需要的JavaSE ...
- vue 父刷新子_父组件中vuex方法更新state子组件不能及时更新并渲染的完美解决方法...
场景: 我实际用到的是这样的,我父组件引用子组件related,父组件调用获取页面详情的方法,更新了state值related,子组件根据该related来渲染相关新闻内容,但是页面打开的时候总是先加 ...
- confluence中org.apache.tomcat.util.net.NioEndpoint$Acceptor.run Socket accept failed的解决方法
confluence中org.apache.tomcat.util.net.NioEndpoint$Acceptor.run Socket accept failed的解决方法 参考文章: (1)co ...
- oracle xe 乱码_关于Linux操作系统下终端乱码的完美解决方法
初入linux的程序员们,经常会受到乱码的问候.可谓"始乱终弃".因为乱码,并且最终放弃了linux的不在少数.好吧,言归正传,先看看各类乱码是怎么形成的. 中文字符乱码 这种情况 ...
- JavaScript中的window.close在FireFox和Chrome上不能正常动作的解决方法
原文:JavaScript中的window.close在FireFox和Chrome上不能正常动作的解决方法 JS中关闭窗口的方法window.close()在IE上能够正常动作,而在FireFox和 ...
- Easyui中使用jquery或js动态添加元素时出现的样式失效的解决方法
Easyui中使用jquery或js动态添加元素时出现的样式失效的解决方法 在添加完之后,可以使用 $.parser.parse();这个方法进行处理: (1) 对整个页面重新渲染: $.parser ...
- Cent OS 6/7 中通过yum安装软件时提示cannot find a valid baseurl...的解决方法
Cent OS 6/7 中通过yum安装软件时提示cannot find a valid baseurl...的解决方法 参考文章: (1)Cent OS 6/7 中通过yum安装软件时提示canno ...
- 在xp中不能查看或更改文件夹的“只读”属性或“系统”属性解决方法
在xp中不能查看或更改文件夹的"只读"属性或"系统"属性解决方法 症状 您可能会遇到下列任一症状: • 不能使用文件夹的"属性"对话框查看 ...
最新文章
- Yii2 的小贴士用法
- linux printf 刷新,linux下printf中\n刷新缓冲区的疑问(已解决)
- our reuse project in HCP
- PL/SQL包(Package)
- 无法解析的外部符号 __imp__glewinit
- java基础代码实例_全网都在找的Python简单基础小程序的实例代码
- OpenAI API 案例
- 美赛论文格式基本要求
- 安装Linux无盘工作站
- android edittext删除文本框,Android EditText 文本框实现搜索和清空效果
- openharmony容器组件之Panel
- 寒霜朋克计算机丢失,寒霜朋克无法进入游戏解决方法 寒霜朋克无法进入游戏怎么办...
- 房地产公司网站建设需要多少钱
- Python网页编程(CGI)
- 勿喷:thinkphp项目怎么跑起来
- 网上教学系统mysql课程设计_基于学生信息管理系统的数据库系统课程设计(MySQL)...
- 阿里云服务器的ECS和RDS和OSS和SLB是什么意思?
- HBase批量写入数据
- 解决 Windows中丢失d3dx9_39.dll
- 软考架构设计师知识点