Как правильно указать тип элемента регулируемого вектора

Исключение нулевого указателя - это индикатор того, что вы используете объект, не инициализируя его.

Например, ниже - класс ученика, который будет использовать его в нашем коде.

public class Student {

    private int id;

    public int getId() {
        return this.id;
    }

    public setId(int newId) {
        this.id = newId;
    }
}

Приведенный ниже код дает вам исключение с нулевым указателем.

public class School {

    Student obj_Student;

    public School() {
        try {
            obj_Student.getId();
        }
        catch(Exception e) {
            System.out.println("Null Pointer ");
        }
    }
}

Поскольку вы используете Obj_Student, но вы забыли инициализировать его, как в правильном коде, показанном ниже:

public class School {

    Student obj_Student;

    public School() {
        try {
            obj_Student = new Student();
            obj_Student.setId(12);
            obj_Student.getId();
        }
        catch(Exception e) {
            System.out.println("Null Pointer ");
        }
    }
}
2
задан davypough 4 April 2019 в 23:09
поделиться

2 ответа

Почему нет ошибки типа

Тип проверяется в соответствии с array-element-type массива:

(defparameter w (create-jvector :element-type 'fixnum))

(array-element-type (jvector-vector v))
=> T

(array-element-type (jvector-vector w))
=> FIXNUM

Нажатие символа на W приводит к ошибке. Как сказал jkiiski, тип используется главным образом, чтобы помочь компилятору иметь возможность использовать специализированные представления для массивов (битвекторы, строки, ...).

integer может быть bignum, поэтому тип обновленного элемента: T:

(upgraded-array-element-type 'integer)
=> T

Как решить вашу проблему

Это решение подсказано jkiiski, а именно добавить тип в структуру; здесь я также переопределяю конструктор непосредственно из структуры:

(defstruct (j2vector
             (:constructor make-jvector
                           (element-type
                            &aux
                            (start 0)
                            (vector (make-array 0
                                                :adjustable t
                                                :fill-pointer 0
                                                :element-type element-type)))))
  element-type
  vector
  (start 0 :type (integer 0)))

Затем вы явно проверяете тип:

(defun push-jvector (elt jvec)
  (assert (typep elt (j2vector-element-type jvec)) ())
  (vector-push-extend elt (j2vector-vector jvec)))
0
ответ дан coredump 4 April 2019 в 23:09
поделиться

Если вы укажете MAKE-ARRAY тип элемента, он попытается выделить массив с эффективным использованием пространства. Реализации имеют несколько поддерживаемых вариантов:

Примеры:

CL-USER 13 > (mapcar #'upgraded-array-element-type
                     '(bit fixnum character))
((UNSIGNED-BYTE 1) (SIGNED-BYTE 64) CHARACTER)

Но для многих типов нет пространственно-эффективных массивов:

CL-USER 14 > (mapcar #'upgraded-array-element-type
                     '(integer string standard-object))
(T T T)

Вы запросили целое число массив и получил общий массив: см. тип T, возвращаемый upgraded-array-element-type.

Речь идет не о проверке типов, а о том, чтобы запросить во время выполнения, возможно, получить оптимизированный для пространства массив.

0
ответ дан Rainer Joswig 4 April 2019 в 23:09
поделиться
Другие вопросы по тегам:

Похожие вопросы: