Spec-Zone .ru
спецификации, руководства, описания, API
След: API Reflection
Урок: Массивы и Перечислимые типы
Раздел: Массивы
Создание Новых Массивов
Домашняя страница > API Reflection > Массивы и Перечислимые типы

Создание Новых Массивов

Так же, как в неотражающем коде, отражение поддерживает возможность динамически создать массивы произвольного типа и размерностей через java.lang.reflect.Array.newInstance(). Рассмотреть ArrayCreator, основной интерпретатор, способный к динамичному созданию массивов. Синтаксис, который будет проанализирован, следующие:

fully_qualified_class_name variable_name[] = 
     { val1, val2, val3, ... }

Предположите что fully_qualified_class_name представляет class, у которого есть конструктор с синглом String параметр. Размерности массива определяются числом обеспеченных значений. Следующий пример создаст экземпляр массива fully_qualified_class_name и заполните его значения с примерами, приведенными val1, val2, и т.д. (Этот пример принимает знакомство с Class.getConstructor() и java.lang.reflect.Constructor.newInstance(). Для обсуждения API Reflection для Constructor см. Создающий Новый раздел Экземпляров Класса этого следа.)


import java.lang.reflect.Array;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.regex.Pattern;
import java.util.regex.Matcher;
import java.util.Arrays;
import static java.lang.System.out;

public class ArrayCreator {
    private static String s = "java.math.BigInteger bi[] = { 123, 234, 345 }";
    private static Pattern p = Pattern.compile("^\\s*(\\S+)\\s*\\w+\\[\\].*\\{\\s*([^}]+)\\s*\\}");

    public static void main(String... args) {
        Matcher m = p.matcher(s);

        if (m.find()) {
            String cName = m.group(1);
            String[] cVals = m.group(2).split("[\\s,]+");
            int n = cVals.length;

            try {
                Class<?> c = Class.forName(cName);
                Object o = Array.newInstance(c, n);
                for (int i = 0; i < n; i++) {
                    String v = cVals[i];
                    Constructor ctor = c.getConstructor(String.class);
                    Object val = ctor.newInstance(v);
                    Array.set(o, i, val);
                }

                Object[] oo = (Object[])o;
                out.format("%s[] = %s%n", cName, Arrays.toString(oo));

            // production code should handle these exceptions more gracefully
            } catch (ClassNotFoundException x) {
                x.printStackTrace();
            } catch (NoSuchMethodException x) {
                x.printStackTrace();
            } catch (IllegalAccessException x) {
                x.printStackTrace();
            } catch (InstantiationException x) {
                x.printStackTrace();
            } catch (InvocationTargetException x) {
                x.printStackTrace();
            }
        }
    }
}
$ java ArrayCreator
java.math.BigInteger [] = [123, 234, 345]

Вышеупомянутый пример показывает один случай, где это может быть требуемым, чтобы создать массив через отражение; а именно, если компонентный тип не известен до времени выполнения. В этом случае, использование кода Class.forName() получить class для требуемого компонентного типа и затем вызывает определенного конструктора, чтобы инициализировать каждый компонент массива прежде, чем установить соответствующее значение массива.


Проблемы с примерами? Попытайтесь Компилировать и Выполнить Примеры: FAQ.
Жалобы? Поздравление? Предложения? Дайте нам свою обратную связь.

Предыдущая страница: Идентификация Типов Массива
Следующая страница: Получение и Установка Массивов и Их Компонентов