如何声明和实例化一个新的通用数组?

时间:2013-02-21 01:29:10

标签: java arrays generics data-structures generic-programming

我正在研究我的数据结构技巧。我在网上找到了一本很棒的免费书籍Open Data Structures in Java.在阅读之后,我试图用所提供的代码创建所有声明的数据结构,这样我就可以将它们灌输到我的记忆中。

我遇到了“错误”,在我的生活中我无法弄明白:在resize()的{​​{1}}方法(第2.1.2节)中,有代码行 - ArrayStack。关键在于包含元素的数组既不太小也不太大。如果我使用这行代码,我会从Eclipse获得以下错误消息:

T[] b = newArray(Math.max(n*2,1));

所以,我认为它一定是“拼写错误”,其意思是“新数组”。但是修复它会让我看到Eclipse的以下错误消息:

The method newArray(int) is undefined for the type ArrayStack<T>.

我不明白我错过了什么或做错了什么。 总结一下我的问题,如何声明和实例化一个新的通用数组,特别是在固定大小的情况下?

3 个答案:

答案 0 :(得分:2)

鉴于T的等级,我们称之为klass ...

对于长度为n的一维数组:

T[] arr = (T[]) Array.newInstance(klass, n)

对于长度为n x m的二维数组:

T[][] 2dArr = (T[][]) Array.newInstance(klass, n, m)

以上实际上是两个不同的函数,一个采用int参数,第二个采用int...参数,您也可以将其作为数组传递。两者都返回Object,你需要一个未经检查的演员。

如果你想要一个长度为n的锯齿状数组,第二维未定,你必须得到T[]的类,让我们称它为klass2,然后再做

T[][] 2dArr2 = (T[][]) Array.newInstance(klass2, n)

这就是为什么你还需要将一个类型传递给collection.toArray(T[] arr),否则你会得到一个Object[]的vanilla toArray()方法,因为它不知道类型。

答案 1 :(得分:1)

您想要的是:

void resize() {
    T[] b = new T[Math.max(n*2,1)];
    for (int i = 0; i < n; i++) {
        b[i] = a[i];
    }
    a = b;
}

但这不起作用,因为T在运行时实际上并不知道,而且必须如此。但是,这可以使用通用安全构造函数编写。

void resize() {
    T[] b = (T[]) Array.newInstance( a.getClass().getComponentType(),
                                     Math.max(n*2,1) );
    for (int i = 0; i < n; i++) {
        b[i] = a[i];
    }
    a = b;
}

似乎作者意味着在该类中有一个方法newArray:

void T[] newArray(int size) {
    return (T[]) Array.newInstance( a.getClass().getComponentType(), size);
}

答案 2 :(得分:0)

Java并不是一件容易的事。由于type erasure T的类在运行时不可用(当您需要确定要创建的数组类型时)。

但是,由于您已经有一个数组(a),因此您可以使用反射来创建该类型的新数组。

看起来像这样:

import java.lang.reflect.Array;

public class Test {

        public static void main(String args[]) throws Exception {
                Object array[] = new Object[5];

                array = resizeArray(array, 10);

                for (Object o : array) {
                        System.out.println(o);
                }
        }

        public static <T>
        T[] resizeArray(T[] a, int newSize) throws Exception {
                T[] b = (T[]) Array.newInstance(a.getClass().getComponentType(),
                                                newSize);

                for (int i = 0; i < a.length; i++) {
                        b[i] = a[i];
                }

                return b;
        }
}