I got a null pointer exception when accessing a static array from a static member method.
The exception is thrown when i call setData(x, y, z) from a thread. When I debugged it I found out data[0] is null when i try to write to it. I just don't understand how it can be null
public class dataContainer
{
private static final short nrOfDataElements = ids.total_ids;
private static regularDataElement[] data = new regularDataElement[nrOfDataElements];
public static synchronized void getData(final short i, regularDataElement r)
{
if ( (i >= 0) && (i < nrOfDataElements) )
r.set(data[i].getTimestamp(), data[i].getValue());
}
public static synchronized void setData(short i, double ts, long val)
{
if ( (i >= 0) && (i < nrOfDataElements) )
data[i].set(ts, val); //<<-------null pointer exception, debugging showed data[i] == null, (with i = 0 and nrOfDataElements = 12)
}
}
and
public class regularDataElement
{
regularDataElement()
{
set(0, 0);
}
public void set(double _ts, long _val)
{
System.out.println(this.ts + " " + _ts + " " + this.val + " " + _val); System.out.flush();
this.ts = _ts;
this.val = _val;
}
public double getTimestamp()
{
return this.ts;
}
public long getValue()
{
return this.val;
}
private double ts;
private long val;
}
The statement private static regularDataElement[] data = new regularDataElement[nrOfDataElements];
initializes data
with an array the size of nrOfDataElements
. It does not initialize each element in this array. I.e., all the elements are null.
If you wish to initialize the elements, you should do so yourself. E.g., you could add a static block to handle this:
static regularDataElement[] data = new regularDataElement[nrOfDataElements];
static {
for (int i = 0; i < nrOfDataElements; ++i) {
data[i] = new regularDataElement();
}
}
Did you ever initialize the data
array?
private static regularDataElement[] data =
new regularDataElement[nrOfDataElements];
will create an array full of null
objects of size nrOfDataElements
. It won't actually initialize any elements in the array.
You don't appear to be allocating memory for data[i]
, which is why you're getting the NPE.
Allocating memory for the array itself is not enough. You need to allocate memory for each element:
for (int i = 0; i < nrOfDataElements; ++i) {
data[i] = new regularDataElement(...);
}
(Replace ...
with the actual arguments.)
You never actually create any objects. You must add somewhere:
for (int i = 0; i < data.length; i++) {
data[i] = new regularDataElement();
}
When you initialize an Object
array in Java
, like data
in your code, all elements are by default set to null
.
So, you need to populate the data
array first, before being able to call any methods against its elements.
Assuming that the regularDataElement
class has a no-args (i.e., no parameters) constructor, you could do
static regularDataElement[] data = new regularDataElement[nrOfDataElements];
static
{
for (int i=0; i<nrOfDataElements; i++)
{
data[i] = new regularDataElement();
}
}
Of course, you could have a separate method to initialize the array, e.g.
static regularDataElement[] initialize(int nrOfDataElements)
{
regularDataElement[] elements = new regularDataElement[nrOfDataElements];
for (int i=0; i<nrOfDataElements; i++)
{
elements[i] = new regularDataElement();
}
return elements;
}
and then call that method to create and initialize the data array, replacing the statement
static regularDataElement[] data = new regularDataElement[nrOfDataElements];
with
static regularDataElement[] data = initialize(nrOfDataElements);
Also, as a matter of following established coding conventions, you should name your classes starting with a capital letter, i.e. use RegularDataElement
instead of regularDataElement
.