所以我想创建一个util方法,它返回一个包含ConstraintValidator
s错误的List。我有这个方法:
public static List<String> getViolationsToList(Set<ConstraintViolation<?>> violations) {
List<String> errors = new ArrayList<>();
for(ConstraintViolation<?> violation: violations) {
errors.add(violation.getMessage());
}
return errors;
}
但是当我打电话时,
RestUtil.getViolationsToList(violations);
它无法编译。违规类型为:
Set<ConstraintViolation<UserDto>> violations;
任何想法? Eclipse建议使用UserDto删除通配符或创建新方法,但我想使用泛型。
答案 0 :(得分:2)
使用
Set<<ConstraintViolation<T>>
然后:
public static <T> List<String> getViolationsToList(Set<ConstraintViolation<T>> violations) {
答案 1 :(得分:2)
泛型是不变的。 Set<ConstraintViolation<UserDto>>
不是Set<ConstraintViolation<?>>
的子类型,即使ConstraintViolation<UserDto>
是ConstraintViolation<?>
的子类型。这就像List<String>
不是List<Object>
的子类型一样,即使String
是Object
的子类型。
您需要在顶层使用通配符才能获得类型参数的多态性:
List<String> getViolationsToList(Set<? extends ConstraintViolation<?>> violations) {
答案 2 :(得分:1)
进一步挖掘,
OP没有提及它,但请注意,由于更好的类型推断,代码在Java 8中工作。在java 8中,您可以执行以下操作:
return violations.stream().map(Violation::getMessage).collect(Collectors.toList());
更优雅
答案 3 :(得分:0)
可能是你想做这样的事情:
public static <T> List<String> getViolationsToList(Set<ConstraintViolation<T>> violations) {
List<String> errors = new ArrayList<>();
for(ConstraintViolation<T> violation: violations) {
errors.add(violation.getMessage());
}
return errors;
}