Q: How to Construct a unduplicate list? I want to construct a unduplicated List using below code ,but something is wrong ,somebody says it's thread unsafe but  I don't get it ,so please give me some examples to prove it ,Thanks 
class BadListHelper <E> {  
    public List<E> list = Collections.synchronizedList(new ArrayList<E>());  
    public synchronized boolean putIfAbsent(E x) {  
        boolean absent = !list.contains(x);  
        if (absent)  
            list.add(x);  
        return absent;  
    }  
} 


A: One problem with your code is that operations on your (exposed) list object, and the putIfAbsent method are synchronizing on different objects.  That means that putIfAbsent has a race-condition with respect to direct operations on list.
For example if you have two threads:


*

*thread A calls helper.list.add(e)

*thread B calls helper.putIfAbsent(e)
then you could end up with e in the list twice ... depending on the timing. 
public synchronized boolean putIfAbsent(E x) {  
    boolean absent = !list.contains(x);  
    // <<--- the Thread A call could happen here.
    if (absent)  {
        list.add(x);  
    }
    return absent;  
}

Now admittedly, you would get the same effect if threads A and B both called helper.list.add directly.  However, the implied semantic of putIfAbsent is that it won't add an element that is already there ... and that is what it would do in the case above.
In fact, the implementation of Collections.synchronizedList returns a List object that synchronizes on itself.  So one fix is to change putIfAbsent to this:
public boolean putIfAbsent(E x) {  
    synchronized (list) {
        boolean absent = !list.contains(x);  
        if (absent) { 
            list.add(x);  
        }
        return absent;
    }
}

