Q: Will the assignment of value in a Java Boolean object cause re-allocation in memory I have the following piece of code 
Boolean flag = new Boolean(false);
flag = true;

Will the second line (assignment) cause a recreation of the initial object (basically a call to new()) in the JVM? I am asking because I am using a Boolean object to synchronize multiple threads, and I am afraid that if a re-initialization takes places, the waiting threads will not see the change in value.
In my application, there are multiple threads that are given a reference to the previous Boolean object. Only one thread changes the objects value to true, and the rest wait until the object's value becomes true. So, if T1 is the thread that changes the value, its code is like:
synchronized(flag) {
    flag = true;
    flag.notifyAll();
}

and the rest of the threads (T2) will have code like:
synchronized(flag) {
    while(flag == false)
        wait();
    if(flag == true) {
        //do something
    }
}

Therefore, the question is that after the assignment of true to flag, will the other threads (T2) still have access to the original object?
Thanks,
Nick

A: The assignment flag = false is a boxing conversion. It will get compiled as flag=Boolean.valueOf(false) which will end up returning the constant Boolean.FALSE.
So the answer is, it will not create a new object but it will change the variable flag as it assigns an instance distinct from your previous result of new Boolean(false).
It's not quite clear what you are actually doing but in general, synchronizing on a mutable variable is broken design.

The problem is that you are mixing the value that makes up your condition and the object to synchronize on. The simplest implementation of your updated intention is to use a simple boolean flag and synchronize on the instance that contains the flag:
class WithFlag {
  private boolean flag;

  public synchronized void setToTrue() {
    if(!flag) {
      flag=true;
      notifyAll();
    }
  }
  public synchronized void waitForTrue() throws InterruptedException {
    while(!flag) wait();
  }
}

Note that declaring an instance method synchronized is similar to wrap its code with synchronized(this) { … }

A: If you want to use a boolean to synchronize threads, you should consider using AtomicBoolean, which is specifically designed for this purpose.

A: The other answers have already explained that when you say flag=false, it is a boxing conversion which will return the constant Boolean.FALSE. One important point that the other answers have covered but not emphasized on is that when you obtain a lock on two Boolean objects that were assigned the same value through a boxing conversion, it is as good as obtaining a lock on one Boolean object. 
My answer attempts to give an example to explain this. Consider the following code that creates two threads that obtain a lock on a Boolean. 
public class BooleanTest {

    public static void main(String[] args) {
        BooleanTest test = new BooleanTest();
        test.booleanTest();

    }

    private void booleanTest() {
        BooleanLockTester booleanLock1 = new BooleanLockTester();
        booleanLock1.setBooleanLock(true);
        BooleanLockTester booleanLock2 = new BooleanLockTester();
        booleanLock2.setBooleanLock(true);
        BooleanLocker booleanLocker1 = new BooleanLocker(booleanLock1);
        BooleanLocker booleanLocker2 = new BooleanLocker(booleanLock2);

        Thread threadOne = new Thread(booleanLocker1);
        Thread threadTwo = new Thread(booleanLocker2);

        threadOne.start();
        threadTwo.start();
    }

    private class BooleanLocker implements Runnable {

        private BooleanLockTester booleanLockObj;

        public BooleanLocker(BooleanLockTester booleanLockObj) {
            this.booleanLockObj = booleanLockObj;
        }

        @Override
        public void run() {
            booleanLockObj.testLockOnBoolean();
        }

    }

    private class BooleanLockTester {

        private Boolean booleanLock = false;

        public synchronized void testLockOnBoolean() {
            synchronized (booleanLock) {
                for (int i = 0; i<1000000000; ++i) {
                    System.out.println(Thread.currentThread().getName());
                }
            }
        }

        public void setBooleanLock(Boolean booleanLock) {
            this.booleanLock = booleanLock;
        }

    }
}

In the above example, the two threads will never be able to enter the for loop together. When you run the program, you will see that the thread that starts first will start printing on the console and only when it is finished, the next thread will start printing to the console.
Let's make a small change in the above code :
Change the following line in the code : 
booleanLock2.setBooleanLock(true);

To this :
booleanLock2.setBooleanLock(false);

You will now see that the threads stop behaving and print to the console in a random order. This is because the threads now obtain a lock on two different objects.
