0

I have odd behavior with a Java List<> class, which is overriding all values with the last one added.

Take for example the following code ...

import java.io.*;
import java.sql.*;
import java.lang.*;
import java.util.*;

public class alist
{
    //   
    public static class item 
    {    
        public static String name;
        public static long   type;

        item() {}

        item( String n, long t )
        {
            name = n; 
            type = t; 
        }

        public String toString()
        {
            return "name: " + name +
                 ", type: " + String.valueOf( type );
        }
    }    

    public static void main(String [] args)
    {
        List<item> lst = new ArrayList<item>();

        lst.add( new item( "abc", 0 ) );
        lst.add( new item( "xyz", 1 ) );

        for ( item i : lst )
            System.out.println( i.toString() );
    }
}

I would have expected this to output the following ...

name: abc, type: 0
name: xyz, type: 1

... but instead it prints ...

name: xyz, type: 1
name: xyz, type: 1

... ideas?

I'm sure it's something silly, where I simply cannot see the forest because of the trees. .

nvanwyen
  • 49
  • 5

4 Answers4

7

You are declaring your Item class attributes static and thus, they are shared by all Item instances. Static attributes are class attributes, there is only one value of each associated to the class itself and not to each single object.

http://docs.oracle.com/javase/tutorial/java/javaOO/classvars.html

The second invocation to Item constructor is changing the values and that is why you are getting the same String.

Change:

    public static String name;
    public static long   type;

For:

    public String name;
    public long   type;
  • 1
    You should - given that you don't seem to need to change those values after constructing `item` - make the fields `final` too, e.g: `public final String name` / `public final long type`. Also it should be `Item` and `AList` not `item` and `alist` (the Java convention is caps-case for classes). – Paul Jun 09 '14 at 16:05
  • You might (depending on what you are really doing) want to use an `Enum` instead of a `long` for `type`. (Or even have different subclasses of `Item` for different 'types'.) – Paul Jun 09 '14 at 16:07
0

Your Item class has static variables, not member variables. Each time you call the constructor you are changing the static value.

Change it to:

public static class item 
{    
    public String name;
    public long   type;

    item() {}

    item( String n, long t )
    {
        name = n; 
        type = t; 
    }

    public String toString()
    {
        return "name: " + name +
             ", type: " + String.valueOf( type );
    }
}  
Brett Okken
  • 6,210
  • 1
  • 19
  • 25
0

Well that is because you have added static while declaring name and type. Static keyword only makes a single instannce of the object so whenever you update the value, it all values get the same. Just remove static and try.

Mayank Agarwal
  • 376
  • 2
  • 9
0

The reason is that the fields type and name are static, and therefore the same for all instances.

Andres
  • 10,561
  • 4
  • 45
  • 63