Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/316.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在java中创建泛型方法_Java_Generics - Fatal编程技术网

在java中创建泛型方法

在java中创建泛型方法,java,generics,Java,Generics,如果我将(Inventory)更改为(T)它将无法识别getId() public static T getSelectedRow(表){ T selectedItems=(T)table.getValue(); 如果(selectedItems!=null){ System.out.println(“getSelectedRow id:+((库存)selectedItems.getId()); 返回selectedItems; } 如何使其作为((T)selectedItems.getId(

如果我将
(Inventory)
更改为
(T)
它将无法识别
getId()

public static T getSelectedRow(表){
T selectedItems=(T)table.getValue();
如果(selectedItems!=null){
System.out.println(“getSelectedRow id:+((库存)selectedItems.getId());
返回selectedItems;
}
如何使其作为
((T)selectedItems.getId()
表是vaadin7,我使用Java8


我不想使用
Inventory
,它应该是泛型的,这样我就可以使用不同的对象。
Inventory
只是其中的一个,有些有
getId()
有些没有!

因为
T
是类型的占位符,就编译器而言
T
没有
getId()
或不属于
对象的任何其他方法。您不能这样做


但是,如果确实需要
getId
,可以将
T
约束为

public interface HasId {
    long getId();
}

public class Inventory implements HasId {

    @Override
    public long getId() { return id; }
}

public static <T extends HasId> T getSelectedRow(Table table) {
    T selectedItems = (T) table.getValue();
    if (selectedItems != null) {
        System.out.println("getSelectedRow id:"+ selectedItems.getId());
        return selectedItems;
    }
...

如果您使用了
我不想使用Inventory,那么它应该是泛型的,这样我就可以使用不同的对象。Inventory只是其中的一个,有些有getId(),有些没有!那么是什么阻止了您实现
,并且在
Inventory.class
中重写了一个方法
getId();
()
接口有一个称为
default
方法的概念。请注意,在您的第一个示例中,使用
HasId
接口的示例中,类型参数
T
不向方法添加任何内容,我的意思是它不添加类型安全性。它们可以直接转换为
HasId
,并具有相同的效果。您的第二个示例MPE比第一个更灵活。所以第二个示例可以工作,因为我不想使用清单,所以它应该是通用的,这样我就可以使用不同的对象。清单只是其中的一个,有些有getId()有些不是?而且不仅仅是getId,还有不同的方法。@andrej听起来你在试图创建一个可以处理任何情况的方法。要么所有类型都需要实现一个公共接口,要么需要不同的方法。我建议第二个选项,以避免一个方法做得太多。无论如何,请记住Java泛型中的ber被删除。换句话说,泛型是一种只在编译时使用的机制。这就是为什么,例如,在Joop的第一个示例中,类型参数
T
是多余的。在这种情况下,转换为
T
与转换为
HasId
完全相同,这是由于上限。关于
T
:可以由于类型擦除,因此需要使用
Table
或参数
Class type
,执行
T=type.cast(Table.getValue())
@andrej我的意思是它是多余的、不需要的、基本上没有意义的。这只适用于第一个示例。无论您使用什么类型的参数,对于方法来说,它总是一个
HasId
。由于
T
没有用作返回类型或一个或多个参数类型,因此
T
没有添加任何内容第二个例子,因为
T
是由
tolong函数使用的
T
有意义。当然,您仍然有一个未检查的强制转换问题;这就是使用
Class
可能会派上用场的地方,正如Joop的评论所示。我不想使用Inventory,它应该是泛型的,这样我就可以使用不同的对象了。Inventory只是其中之一,有些人有getId()有些人没有!
public interface HasId {
    long getId();
}

public class Inventory implements HasId {

    @Override
    public long getId() { return id; }
}

public static <T extends HasId> T getSelectedRow(Table table) {
    T selectedItems = (T) table.getValue();
    if (selectedItems != null) {
        System.out.println("getSelectedRow id:"+ selectedItems.getId());
        return selectedItems;
    }
...
public static <T> T getSelectedRow(Table table, ToLongFunction<T> idGetter) {
    T selectedItems = (T) table.getValue();
    if (selectedItems != null) {
        System.out.println("getSelectedRow id:"+ idGettter.apply(selectedItems));
        return selectedItems;
    }
...

Inventory inventory = getSelectedRow(table, Inventory::getId);