1

Hey guys I just have a quick question about initializing an arraylist

This is just a small piece of code I'm doing

public class OrderManager {
    ArrayList<Order>orders = new ArrayList<Order>();
    public OrderManager() {

    }

    public OrderManager(ArrayList<Order> orders) {
        orders = new ArrayList<Order>();
    }

using a variable orders, and then declaring orders = new correct? Or is this going to be two different instances and when I try to add things to it its not going to work?

Or since OrderManager is going to take an arraylist does it even make sense?

I haven't tested it yet, I just started writing this code and have ran into this problem before where I couldn't add to the list properly and believe it was because of a error similar to this just checking to try and get it right to start with.

4
  • You are reassigning it in the constructor, so it makes no difference (unless it's in multithreaded code). Also, see below comment. Commented Sep 18, 2013 at 18:37
  • 6
    You probably should use this.orders = orders in your second constructor if you want OrderManager to store passed list of orders. Commented Sep 18, 2013 at 18:37
  • Ok, so when I put an addOrder method in this same code would it be better to use this.orders.add, or would that not make sense? Commented Sep 18, 2013 at 18:39
  • Don't forget to accept an answer if one has answered your question. Commented Sep 19, 2013 at 9:49

3 Answers 3

3
public class OrderManager {
    private ArrayList<Order>orders;
    public OrderManager() {
      this(new ArrayList<>());//call constructor
    }

    public OrderManager(ArrayList<Order> orders) {
        this.orders = orders;
    }
  .
  .
   //more methods here for example getters and/or setters for orders
}

This is the proper way. Also consider using List rather than ArrayList cause in future if you want not to be ArrayList and for example be LinkedList you don't have to modify this class. Programming to an interface concept.

So your class would look like:

    public class OrderManager {
        private final List<Order>orders;

        public OrderManager() {
          this(new ArrayList<>());//call constructor or doing nothing is another option
        }

        public OrderManager(List<Order> orders) {
            this.orders = orders;
        }


       public List<Order> getOrders(){
           return orders;
       }    

       public void addOrder(Order order){
            orders.add(order);
       }
  }
Sign up to request clarification or add additional context in comments.

Comments

2

What you are currently doing is assigning a new, empty ArrayList instead of taking the one given.

You should either do this:

public class OrderManager {
    private final List<Order> orders;

    public OrderManager() {
        orders = new ArrayList<Order>();
    }

    public OrderManager(final List<Order> orders) {
        this.orders = orders;
    }

Which will take the reference to the List passed into the constructor. Changes to the List from outside the class will affect the List inside the class.

A more common way is to make a "defensive copy" using the copy constructor

public class OrderManager {
    private final List<Order>orders;

    public OrderManager() {
        orders = new ArrayList<Order>();
    }

    public OrderManager(final List<Order> orders) {
        this.orders = new ArrayList<Order>(orders);
    }

Now the class has a copy of the List passed in so it will be independent of the original List.

5 Comments

i don't get the point.. to store the variable as a List if you are always creating statically as an ArrayList
From my experience, it is usually better to declare a pre-condition in the constructor, such as orders is a fresh instance / no outside references are kept, than bothering to clone / copy the given arguments defensively.
@nachokk Because if I decide to change that I only need to change the assignment. If you used an ArrayList then you would need to change that everywhere.
@afsantos That doesn't provide any guarantees against stupidity whereas a defensive copy does. There is much stupidity in the world...
@BoristheSpider Agreed. That's just an approach to solve the problem. Another would be to let stupidity meet the bugs it creates. Generally, defensive copies would work best on public / API level, whereas private / package-private levels assume that you know what you're doing. In the end, it's little more than a matter of habits and style.
0

Your second constructor is wrong.

It should be:

public OrderManager(ArrayList<Order> orders) {
        this.orders = orders;
    }

Constructor is what used to create a new object and initialize its class variables.

When you use new you are calling a class constructor.

There are cases when one constructor can be called from another. It's done when the calling constructor initializes a larger set of variables and uses other constructor to initialize a sub-set (so not to repeat the same code). At such cases you use this with a proper signature.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.