[英]Implementing a filter with Predicate<T> in Java8
為了掌握Java8,我試圖實現一個簡單的Repo來存儲不同對象的列表。
我的出發點是:
public class MyRepo {
Map<Class, List<?>> repo =new HashMap<>();
public List<?> get(Class c){
List<?> result= repo.get(c);
return (result==null)?new ArrayList<>():(List<?>) result;
}
public void put(Class c,List<?> l){
repo.put(c, l);
}
}
所以我能夠插入列表並檢索列表。
我的下一步是實現一個通用的過濾方法:
public List<?> find(Class c, Predicate<?> predicate){
List<?> result= repo.get(c);
return (result==null)?new ArrayList<>():(List<?>)result.stream().filter(predicate);
}
結果
java: incompatible types: java.util.function.Predicate<capture#1 of ?> cannot be converted to java.util.function.Predicate<? super capture#2 of ?>
如何實現通用的查找方法?
我不得不承認,我不確定,設計與
Map<Class, List<?>> repo =new HashMap<>();
是個不錯的選擇。 也許有更好的解決方案。
首先,您應該使您的方法通用,這將讓編譯器決定您傳遞哪個Predicate
,並相應地推斷出特定類型。 此外, result.stream().filter(predicate)
將為您提供Stream
而不是List
。 您需要在List
收集流。
此外,由於您已經有了get(Class<T>)
方法,因此可以使用它而不是在find()
方法中執行repo.get(c)
find()
方法。 你也可以在這里使用java.util.Optional
類:
Map<Class, List<?>> repo =new HashMap<>();
public <T> List<T> get(Class<T> c){
return Optional.ofNullable((List<T>)repo.get(c)).orElse(new ArrayList<>());
}
public <T> void put(Class<T> c,List<T> l){
repo.put(c, l);
}
public <T> List<T> find(Class<T> c, Predicate<T> predicate){
return get(c).stream().filter(predicate).collect(Collectors.toList());
}
您需要修復方法簽名。 通用通配符類型本質上是獨立的 - Java編譯器沒有理由相信它?
類型與另一種類型有什么關系?
類型。
嘗試:
public <T> List<T> get(Class<T> c)
public <T> void put(Class<T> c, List<T> list)
public <T> List<T> find(Class<T> c, Predicate<T> predicate)
這個可配置的<T>
參數允許調用者指定他們想要的任何類型,但也讓編譯器知道“嘿,這個List<T>
和Predicate<T>
?那是相同的T
,所以你可以完全做過濾”
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.