Ошибка нулевого указателя в Java? - PullRequest
0 голосов
/ 11 октября 2011

Я довольно новичок в этом форуме.Я всегда был очень обеспокоен размещением сообщений на форумах, но после двух недель, когда я ломал голову над своим кодом, пытаясь заставить его работать, я наконец-то сдался. Код ниже является важной частью какого-то более крупного кода, но я думаю, что «Мы точно определили проблемный раздел.У меня есть 2D-массив объектов, которые должны быть инициализированы по умолчанию, как только он будет создан.Однако этого, похоже, не происходит, и значение остается нулевым.Может ли это быть результатом того, что Java не может передавать по ссылке?Если так, то почему примитивные двумерные массивы создаются идеально?Заранее спасибо, Лас.

    class ObjectThing
    {
        int someInt;
        double someDouble;

        public ObjectThing()
        {
            someInt = 0;
            someDouble = 0;
        }

        synchronized private void someIntIncrement ()
        {
           someInt++;
        }

        synchronized public void addSomeDouble (double sd)
        {
            someDouble += sd;
            someIntIncrement ();
        }

        synchronized public String toString ()
        {
            return someInt + "," + someDouble;
        }
  }


  class AnotherObject
  {
          String name;
          ObjectThing [][] someObjectMAtrix;
          double [][] someDoubleMAtrix01;
          double [][] someDoubleMAtrix02;   

          public AnotherObject()
          {
          }

          private void initDouble (double [][] mat)
          {
             for (double [] i: mat)
                for (double j: i)
                   j = 0;
          }

          private void initObject (ObjectThing [][] so)
          {
              for (ObjectThing [] i: so)
                 for (ObjectThing j: i)
                    j = new ObjectThing ();
          }         

          public void init (int r, int c)
          {
              someObjectMAtrix =  new ObjectThing [r][c];
              someDoubleMAtrix01 = new double [r][c];
              someDoubleMAtrix01 = new double [r][c];         
          initObject (someObjectMAtrix);
              initDouble (someDoubleMAtrix01);
              initDouble (someDoubleMAtrix02);
          }
   }

   class Driver
   {
       public static void main (String [] args)
       {
            initializeMethod();
       }

       public void initializeMethod ()
       {
            AnotherObject [] anotherObjectArray = new AnotherObject [1];
            for (AnotherObject i: anotherObjectArray)
            {
                i.init(72,72);
            }
       }
   } 

Ответы [ 4 ]

2 голосов
/ 11 октября 2011

Проблема в вашем initializeMethod:

        AnotherObject [] anotherObjectArray = new AnotherObject [1];
        for (AnotherObject i: anotherObjectArray)
        {
            i.init(72,72);
        }

Going Object[] myArray = new Object[1] только выделяет место для массива. На самом деле он не создает эти объекты. Ваш кодовый блок должен быть

        AnotherObject [] anotherObjectArray = new AnotherObject [1];
        anotherObjectArray[0] = new AnotherObject();
        for (AnotherObject i: anotherObjectArray)
        {
            i.init(72,72);
        }

Это немного неуклюже. Я предполагаю, что у вас есть необходимость поместить AnotherObject в массивы, а вы просто не показываете его Если вам нужен только один из этих объектов, просто создайте его напрямую. Вам, вероятно, стоит взглянуть на Списки

0 голосов
/ 11 октября 2011

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

Однако при инициализации массива будет создан массив нужного размера, для каждого элемента будет установлено значение по умолчанию.Для примитивов это что-то вроде 0 для числовых типов, false для логических значений.Для ссылочных типов по умолчанию используется null.Это источник вашей проблемы.

Вы правильно инициализируете массив, но не заполняете его допустимыми значениями.Таким образом, это не связано с передачей по ссылке, а с правильной инициализацией массива и знанием значений по умолчанию для вновь инициализированного массива.

В частности, вы используете конструкцию for-each для зацикливаниямассив.Эта конструкция выполняет операцию над каждым объектом в коллекции / массиве.

Следовательно, этот код:

AnotherObject [] anotherObjectArray = new AnotherObject [1];
for (AnotherObject i: anotherObjectArray){
    i.init(72,72);
}

эквивалентен этому коду:

AnotherObject [] anotherObjectArray = new AnotherObject [1];
for(int count=0; count <  anotherObjectArray ; count++){
    AnotherObject tempObj = anotherObjectArray[i]; // This is null, because anotherObjectArray[i] hasn't been initialised yet
    tempObj.init(72,72); // This is where we get the NullPointerException :(
}

Вы видите проблему?Вы пытаетесь выполнить операцию с нулем, следовательно, NullPointerException

Я полагаю, что вы на самом деле намеревались это:

AnotherObject [] anotherObjectArray = new AnotherObject [1];
for(int count=0; count <  anotherObjectArray ; count++){
    AnotherObject tempObj = new AnotherObject(); // Here we create the new object
    tempObj.init(72,72); // Initialise the newly created object
    anotherObjectArray[i] = tempObj; // Now we store in the array :)
}

Я надеюсь, что объяснил это достаточно ясно, но, пожалуйста, спроситедля уточнения, если у меня нет :) 1028 *

0 голосов
/ 11 октября 2011

Вы только что инициализировали массив объектов AnotherObject ... но в первом поле массива нет AnotherObject ... Он пуст, как только вы его получили, потому что вы его не инициализировали. В initializeMethod вы должны сделать следующее:

AnotherObject [] anotherObjectArray = new AnotherObject [1];
 for (AnotherObject i: anotherObjectArray)
    {
        i = new AnotherObject();
        i.init(72,72);
    }

ура! * * 1004

0 голосов
/ 11 октября 2011

Я полагаю, что это по замыслу.Примитив будет размещен в стеке и всегда будет иметь какое-то значение по умолчанию.Объект размещается в куче и передается по ссылке.Эти ссылки по умолчанию ничего не будут указывать, пока вы их не инициализируете.

...