英文:
Is it possible to chain predicates with `and` using different type parameter?
问题
我正在学习Java 8的lambda表达式。我可以使用Predicate接口中的"and"方法来合并两个具有不同类型参数的谓词吗?
以下是我的代码:
Predicate<Integer> pc = (iv) -> iv > 20;
Predicate<String> pL = (is) -> is.length() > 5;
System.out.println("pc的谓词结果是:" + pc.test(25));
System.out.println("===========");
System.out.println("同时满足两个条件的谓词结果是:" + pc.and(pL).test("abcd"));
英文:
I am learning Java 8 lambdas. Can I join two predicates, with different type parameter, using and method in Predicate interface?
This is my code:
Predicate<Integer> pc = (iv) -> iv > 20;
Predicate<String> pL = (is) -> is.length() > 5;
System.out.println("The predicate result for pc is: " + pc.test(25));
System.out.println("===========");
System.out.println("The predicate result with both condition true: " + pc.and(pL.test("abcd")));
答案1
得分: 2
不可以,您不能链接不同类型的谓词,除非链接的 谓词 也接受原始谓词的类型。
从签名上看,您可以很容易地看到:
and(Predicate<? super T> other)
or(Predicate<? super T> other)
您可以链接谓词:
Predicate<Person> isMale = p -> p.isMale();
Predicate<Person> isAdult = p -> p.age() >= AGE_OF_MATURITY;
Predicate<Person> isAdultMale = isAdult.and(isMale);
您只能链接那些至少接受与原始谓词相同类型的谓词(这就是 ? super T
的意思):
Predicate<Object> hasWeirdHashCode = o -> o.hashCode() == 0;
Predicate<Person> nonsense = isMale.and(hasWeirdHashCode);
如果要测试不同的类型(A
,B
),您需要分别提供它们:
Predicate<A> propertyOfA = [...];
Predicate<B> propertyOfB = [...];
BiPredicate<A, B> propertyOfAnB = (a, b) ->
propertyOfA.test(a) && propertyOfB.test(b);
如果您需要超过两种不同类型,您需要自己编写自定义的 TriPredicate
、QuadPredicate
等功能接口,实现起来应该很简单。
英文:
No, you can not chain predicates of different types, unless the chained predicate also accepts the type of the original predicate.
Looking at the signature, you can easily see that:
and(Predicate<? super T> other)
or(Predicate<? super T> other)
You can chain predicates:
Predicate<Person> isMale = p -> p.isMale();
Predicate<Person> isAdult = p -> p.age() >= AGE_OF_MATURITY;
Predicate<Person> isAdultMale = isAdult.and(isMale);
You can only chain predicates that accept at least (thats what the ? super T
says) the same type as the original predicate:
Predicate<Object> hasWeirdHashCode = o -> o.hashCode() == 0;
Predicate<Person> nonsense = isMale.and(hasWeirdHashCode);
If you want to test different types (A
, B
), you need to provide them separately:
Predicate<A> propertyOfA = [...];
Predicate<B> propertyOfB = [...];
BiPredicate<A,B> propertyOfAnB = (a, b) ->
propertyOfA.test(a) && propertyOfB.test(b);
If you need more than two different types, you need to roll your own, custom TriPredicate
, QuadPredicate
and so on functional interfaces, which should be straight-forward to implement.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论