java – Guava为什么toStringFunction不是泛型函数?
Guava toStringFunction()具有以下声明:
public static Function<Object,String> toStringFunction() { ... } Object的所有非原始根,因此该函数运行良好. 但是当我尝试用另一个函数组合它时,例如: Function<Integer,Double> f1 = Functions.compose(Functions.forMap(someMap),Functions.toStringFunction()); someMap变量是map< String,Double>,所以我希望toStringFunction将Integer转换为String,然后forMap将String转换为Double. Function<Integer,^ required: Function<Integer,Double> found: Function<Object,Double> 2 errors 我的两个问题是: 1.具体告诉编译器toStringFunction应该是Function<整数,字符串>?一个简单的演员不会起作用,我正在寻找这两个函数的真实组合. Function< Integer,String> g1 = (Function< Integer,String>)Functions.toStringFunction(); // cause error 2.将toStringFunction写成如下: @SuppressWarnings("unchecked") public static <E> Function<E,String> toStringFunction(){ return (Function<E,String>) ToStringFunction.INSTANCE; } // enum singleton pattern private enum ToStringFunction implements Function<Object,String>{ INSTANCE; // @Override public String toString(){ // return "Functions.toStringFunction()"; // } @Override public String apply(Object o){ return o.toString(); } } 我可以指定类型: Function<Integer,Functions.<Integer>toStringFunction()); 这很好用.但番石榴团队现在拥有的版本的动机是什么? 解决方法
经过评论讨论后:
要修复编译错误: Function<Object,Double> f1 = Functions.compose(Functions.forMap(someMap),Functions.toStringFunction()); 你的问题意味着你需要一个函数< Integer,Double>而不是函数< Object,Double>.根据评论中的讨论,并试图考虑其他方案,您想要这个的唯一原因是验证. toStringFunction中的代码不受您的控制,因此该函数中的验证是不可能的.至于forMap函数中的验证,该代码也是您无法控制的.如果要防止IllegalArgumentException,则无论您提供的输入是Object还是Integer,都必须执行此验证.因此,验证也超出了forMap,toStringFunction和compose的范围,因为这些函数都没有提供这种验证,你必须编写自己的代码来执行此操作(捕获异常并处理它或预先验证在调用这个组合函数之前以某种方式). 对于特定的组合,通过将Function的输入参数从Object更改为Integer,你什么也得不到,因为Function只需要Object中的方法,所以这是一个很好的决定,因为它简化了这种情况下的事情并使其更广泛可用.假设您能够将参数类型强制为Integer,您仍然无法获得任何好处,无论是IllegalArgumentException的验证还是您正在尝试的其他内容. 在设计API时,您希望尽可能多的消费者使用它,而不必偏离您的方式,即您应该使用满足您要求的最高级别的类.通过在toStringFunction中使用Object,Guava函数满足了这个原则.这使得该功能更通用并且可以更广泛地使用.这就是选择Object而不是参数化此函数的原因. 如果函数接受了一个参数,它就不会像现在这样做,所以为什么在不需要时使用参数.这种方法大大简化了设计,而不是添加不需要的东西. 原始答案: 每个类都是Object的子类,Function只调用Object类中存在的输入上的toString.因此,在这种情况下,声明一个Function等同于声明Function.通过将Function的输入参数从Object更改为Integer,您将无法获得任何结果,因为它简化了这种情况下的事情. 您应尽可能使用满足您要求的最高级别的课程.这使得该功能更通用并且可以更广泛地使用.这就是选择Object而不是参数化此函数的原因. 修复编译错误:函数f1 = Functions.compose(Functions.forMap(someMap),Functions.toStringFunction()); (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |