Tyv*_*ain 5 java generics java-10
这个类显示信息:
// display line numbers from a file
display(getLineNumber(myFile));
// display users from DB
display(getUsersName(myDBRepository));
Run Code Online (Sandbox Code Playgroud)
等等...
我想制作一个通用接口,这样我就可以将显示信息的代码具体化。
然后我可以做这样的事情:
myInformationElements.stream().forEach(e -> display(e.getValue());
Run Code Online (Sandbox Code Playgroud)
这是我到目前为止所拥有的(不工作):
public interface InformationElement {
public <T> String getValue (T param);
}
public class NbFileLineInformationElement implements InformationElement{
@Override
public <File> String getValue(File param) {
return *same code as in getLineNumber(myFile)*;
}
}
public class UserInformationElement implements InformationElement{
@Override
public <UserRepository> String getValue(UserRepository param) {
return *same code as in getUsersName(myDBRepository)*;
}
}
Run Code Online (Sandbox Code Playgroud)
您已经定义了类型参数File,并且UserRepository正在隐藏类名称File和UserRepository. 这是与现有类相同的命名类型参数的惊喜之一。类型参数不代表类,并且它们没有界限,因此编译器只能假设它们具有Object方法。
这不是最佳实践。实现泛型方法时,这些方法必须保持泛型,并且至少在边界方面是开放的。为了能够稍后限制类型参数的含义,请在类/接口上定义它,并让子类使用类型参数提供该特定实现的含义。
这里最好的解决方案是将InformationElement的类型参数移动到类中,并在子类中提供类型参数。这些方法不再是通用的,但它们确实使用接口/类上定义的类型参数。
interface InformationElement<T> {
public String getValue (T param);
}
class NbFileLineInformationElement implements InformationElement<File>{
@Override
public String getValue(File param) {
return /*same code as in getLineNumber(myFile)*/;
}
}
class UserInformationElement implements InformationElement<UserRepository>{
@Override
public String getValue(UserRepository param) {
return /*same code as in getUsersName(myDBRepository)*/;
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1108 次 |
| 最近记录: |