键入与非键入的ArrayList

时间:2015-04-13 07:49:05

标签: java arraylist

在Java中使用类型化与非类型化ArrayList之间的区别是什么?

例如,使用ArrayList CustomObject

类型的:

ArrayList<CustomObject> typedArray = new ArrayList<>();
typedArray.add(new CustomObject);

或非打字:

ArrayList<> nonTypedArray = new ArrayList<>();
nonTypedArray.add(new CustomObject);

是否有首选后者?当ArrayList持有不同的数据类型时有什么不同,例如一个StringInt等的ArrayList?

7 个答案:

答案 0 :(得分:4)

在第二种方法中,不必仅在第一种方法中添加CustomObject,否则您将收到编译错误。

ArrayList<CustomObject> typedArray = new ArrayList<>();
typedArray.add(new CustomObject);

这种方法通常是优选的,因为没有机会出现类别施放异常,但在第二种方法中有很高的可能性!

JavaDocs解释得很漂亮:Why to prefer Generics

  1. 在编译时进行更强大的类型检查。
  2. 消除演员。
  3. 使程序员能够实现通用算法。

答案 1 :(得分:3)

使用后一种选择永远不会优先。我认为这甚至不可能。我想你的意思是:

 ArrayList nonTypedArray = new ArrayList();

此语法在Java 1.4及更早版本中保留。它仍然为了向后兼容性而编译。

在Java 1.5中引入了泛型,它允许您指定有角度括号之间的类型。

最好使用泛型,因为它更安全。

也就是说,如果你指定

ArrayList<String> typedArray = new ArrayList<String>();

然后你不能不小心将一个整数添加到这个数组列表中;如果你试图添加一个整数,程序将无法编译。

当然,Generics在编译时确保类型安全。在运行时ArrayList<String> typedArray = new ArrayList<String>();变为ArrayList typedArray = new ArrayList();。这是为了保持向后兼容性。

答案 2 :(得分:1)

  

使用typed与非typedArrayList之间的区别是什么?   爪哇?

Typed / Generic ArrayList是一个对象的集合,其中对象的“类型”在有角度的括号中定义。 Java 5中引入了泛型来创建类型安全的集合。 在Generics之前,该集合被称为Untyped / Raw Type Collection,因为无法为编译器指定正在创建的集合的类型。 两者之间的区别是在编译时检测类型安全操作。

在两种情况下,您都要将“CustomObject”类型的对象添加到ArrayList中。在列表中添加元素时没有问题,因为两个列表都将其视为对象。

<强>类型的:

ArrayList<CustomObject> typedArray = new ArrayList<>();
typedArray.add(new CustomObject);

<强>无类型:

ArrayList<> nonTypedArray = new ArrayList<>();
nonTypedArray.add(new CustomObject);
  

是否有首选后者?

我不这么认为。建议在创建列表时使用泛型,以确保类型安全操作。

  

当ArrayList保持不同时有什么不同   datat-ypes,例如String,Int等的ArrayList?

当然,有一个合理的区别。对于无类型列表,您需要在从列表中获取元素时添加类型转换。因为,由于不同类型的元素,编译器有可能在运行时抛出ClassCastException。

答案 3 :(得分:0)

在运行时,绝对没有区别,但是在编译时,使用类型参数可以避免过多的错误,因此最好正确使用泛型。

合理使用原始类型的唯一情况是遗留应用程序,但即使在这种情况下,如果可以,也会尝试使用类型化参数。

答案 4 :(得分:0)

使用类型简化了编码,无需进行投射,也可以有效地存储数据 https://docs.oracle.com/javase/tutorial/java/generics/why.html

答案 5 :(得分:0)

是的,我知道这是一个老帖子。但我想分享一个实例,其中无类型的ArrayList是有用的:当你编写一个应该作用于任意元素类型的函数时。例如,假设您想要创建一个知道如何对数组进行混洗的通用shuffle函数。像这样:

ArrayList<Die> diceRolls = getGetPossibleDiceRolls();
ArrayList<Card> cardDeck = getPossibleCards();
ArrayList<GirlToDate> blackbook = getBlackbook();
shuffle(diceRolls);
shuffle(cardDeck);
shuffle(blackbook);

.
.
void shuffle(ArrayList array) {
    int size = array.size();
    for (int i=0; i<size; ++i) {
        int r = random.nextInt(size - i) + i;

        // Swap
        Object t = array.get(i);
        array.set(i, array.get(r));
        array.set(r, t);
    }    
}

有些人可能会说“是的,但是正确的方法是创建一个类似Shuffleable类型的接口或子类......”但是真的吗?

答案 6 :(得分:0)

在Java 1.7及更高版本中,您通常应该使用如下构造函数:

ArrayList<MyObject> list = new ArrayList<>();

或更普遍的List对象:

List<MyObject> list = new ArrayList<>();

注意您只指定类型<MyObject>一次,而不是两次。这使您的代码更易于维护。 <>使构造函数返回一个ArrayList,它已经被键入以匹配它所分配的字段/变量 - 因此调用代码中不需要强制转换。

不要使用new ArrayList()作为构造函数。这将返回无类型 ArrayList,然后必须将其转换为类型以匹配分配给它的字段/变量。这意味着不必要的类型检查和转换,因此通常会降低性能。