简体   繁体   中英

Why i am able to read/write arraylist at same time?

i am using multiple threads here .. one thread is fetching the list and other is adding a name to the list and both these threads are using a shared resource ie ArrayList object it should give concurrentModification something like that which it is not giving or maybe i am not able to use the threads correctly in my code

code is as follows :

import java.util.*;
import java.util.logging.Level;
import java.util.logging.Logger;

public class threadprac  
 {
  public static void main(String args[]){

        ArrayList<String> shared;
         shared = new ArrayList<>(); 
         String[] arr=new String[]{"amol","robin","shanu","saaru","mohit"};
         for(String n:arr)
           shared.add(n);  
         Thread tf = new Thread(new fetch(shared));
         Thread tm = new Thread(new manipulate(shared));
         tm.setName("thread-M"); tf.setName("thread-F");
         tf.start();
         tm.start();
         try {
         Thread.currentThread().sleep(2000); 
    } catch (InterruptedException ex) {
        Logger.getLogger(threadprac.class.getName()).log(Level.SEVERE, null, ex);
    }
         for(String n:shared)
           System.out.print(n+" ");  

 }    
}

class fetch implements Runnable
{
 ArrayList<String> f;
 fetch(ArrayList shared){
   this.f=shared;
   }
 @Override
 public void run(){
  displayList(); 
  }
void displayList(){
   Iterator<String> itr=f.iterator();
   while(itr.hasNext()){
      String name = itr.next();
      System.out.print(name+" ");
   }
   System.out.println();
  } 
}

class manipulate implements Runnable
{
ArrayList<String> m;
manipulate(ArrayList shared){
    this.m=shared;
}
@Override
public void run(){
    addName();
 }
void addName(){
  m.add("rohit"); 
 } 
}

Each of the two threads takes so little time (probably less than 1 microsecond on a modern CPU) that the chance of them actually executing at the same time is extremely low. You would have to do significant work in both threads to ensure they were active simultaneously.

Thread.start() takes some time. It's very likely that the first thread has completed before the second begins to use its Iterator -- or vice versa, there's no way to predict which.

One of the problems with concurrency is that we have to use phrases like 'very likely' because we can't predict the order in which things will happen, so the behaviour of some programs becomes inconsistent.

Try putting some Thread.sleep() statements inside the loops, so that you can be more sure that the ArrayList get() s execute while the Iterator is open.

Note that while adding sleeps is a quick and easy way to "fiddle" the timings into long enough periods that you can witness certain conditions occurring, they are almost never the right way to solve thread synchronization issues in real code.

As @Slim mentioned its due to the delay in threads while displaying and adding. Modify your code as below by adding Sleep, it would result in concurrentModificationException.

void displayList() throws InterruptedException {
        Iterator<String> itr = f.iterator();
        while (itr.hasNext()) {
            String name = itr.next();
            Thread.sleep(100);
            System.out.print(name + " ");
        }
        System.out.println();
    }

 ...

    void addName() throws InterruptedException {
    Thread.sleep(100);
    m.add("rohit");
}

Exception:

amol Exception in thread "thread-F" java.util.ConcurrentModificationException
    at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:901)
    at java.util.ArrayList$Itr.next(ArrayList.java:851)
    at fetch.displayList(TestClass.java:43)
    at fetch.run(TestClass.java:33)
    at java.lang.Thread.run(Thread.java:745)

ArrayList is not threadsafe. You should probably be looking at something like ConcurrentLinkedDeque

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM