Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sql-server-2005/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
java 8中通过remove方法返回相同对象的java arraylist_Java_Multithreading_Arraylist_Synchronization - Fatal编程技术网

java 8中通过remove方法返回相同对象的java arraylist

java 8中通过remove方法返回相同对象的java arraylist,java,multithreading,arraylist,synchronization,Java,Multithreading,Arraylist,Synchronization,我有两个线程共享同一个列表,第一个线程在列表中添加新对象,第二个线程在同一个列表上执行删除。在启动两个线程一段时间后,我得到了相同的对象,为什么和如何 JAVA代码: SubmitJob将线程运行类添加到列表中 public class SubmitJob extends Thread{ public SubmitJob(List l){ list = l; } List<ThreadRuning> list; private sta

我有两个线程共享同一个列表,第一个线程在列表中添加新对象,第二个线程在同一个列表上执行删除。在启动两个线程一段时间后,我得到了相同的对象,为什么和如何

JAVA代码: SubmitJob将线程运行类添加到列表中

public class SubmitJob extends Thread{

    public SubmitJob(List l){
        list = l;
    }
    List<ThreadRuning> list;
    private static int counter =0;
    public void run(){

        while(true){
            try {
                Thread.sleep(10);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            ThreadRuning t = new ThreadRuning();
            t.setThreadname("Thread Name "+counter);
            t.setStarttime(new Date().getTime());
            list.add(t);
            //System.out.println("Submited"+t.getThreadname());
            counter++;
        }
    }
}
ThreadRuning
class:

public class ThreadRuning extends Thread{

    private long starttime;
    private String threadname;

    public void run(){
        for(int i=0;i<10;i++){
            //System.out.println("Name of Thread "+threadname+ "Executing times"+i);
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    }
// getter setter.


}
公共类线程运行扩展线程{
私人长启动时间;
私有字符串threadname;
公开募捐{

对于(inti=0;i,除了尝试在ArrayList的并发环境中工作之外,还应该真正了解Java中的引用

if (list.size()>0) {
    ThreadRuning t = list.remove(0);
    System.out.println(t.getState()+" name "+t.getThreadname());
    if(t!=null)t.start();
    //System.out.println("Startinf job"+t.getThreadname());
}

该方法返回已删除的对象。它不会创建该对象的新实例。这就是为什么当您再次尝试启动线程时,会出现
IllegalThreadStateException

除了尝试在ArrayList的并发环境中工作之外,您还应该真正了解Java中的引用

if (list.size()>0) {
    ThreadRuning t = list.remove(0);
    System.out.println(t.getState()+" name "+t.getThreadname());
    if(t!=null)t.start();
    //System.out.println("Startinf job"+t.getThreadname());
}

该方法返回已删除的对象。它不会创建该对象的新实例。这就是为什么当您再次尝试启动线程时,会出现
IllegalThreadStateException

当您共享一个对象时,它需要是线程安全的,以避免导致难以修复的错误的不可预知的行为。这里是您的共享
ArrayList
这不是线程安全的,您应该使用线程安全的集合。如果您确实需要
列表
,只需使用装饰器
集合。synchronizedList(List)
作为下一步:

List<ThreadRuning> list = Collections.synchronizedList(new ArrayList<ThreadRuning>());
new SubmitJob(list).start();
new JobMoniter(list).start();
List List=Collections.synchronizedList(新的ArrayList());
新提交作业(列表).start();
新建作业监视器(列表).start();

然而,
队列
似乎更合适,
ConcurrentLinkedQueue
(这是一种本机线程安全的
队列
实现)在这里可能是一个不错的选择。

当您共享对象时,它需要是线程安全的,以避免导致难以修复的错误的不可预知的行为。在这里,您共享的
数组列表
不是线程安全的,您应该使用线程安全的集合。如果您确实需要
列表
,只需使用decorator
集合即可ns.synchronizedList(列表)
如下所示:

List<ThreadRuning> list = Collections.synchronizedList(new ArrayList<ThreadRuning>());
new SubmitJob(list).start();
new JobMoniter(list).start();
List List=Collections.synchronizedList(新的ArrayList());
新提交作业(列表).start();
新建作业监视器(列表).start();

然而,
队列
似乎更合适,
ConcurrentLinkedQueue
(这是一种本机线程安全的
队列
实现)在这里可能是一个不错的选择。

ArrayList
不是线程安全的。如果您从两个单独的线程中修改它而不使用同步,它的行为将不可预测。
ArrayList
不是线程安全的。它在中的含义非常明确。您必须同步或使用更合适的数据结构,如队列。
ArrayListt
不是线程安全的。如果您从两个单独的线程修改它而不使用同步,它的行为将不可预测。
ArrayList
不是线程安全的。它在中的说明非常响亮和清晰。您必须同步或使用更合适的数据结构,如队列。谢谢您的回答。我知道为什么
IllegalThreadStateException
是来的。它只有当remove方法返回相同的对象时才会来,是吗?谢谢你的回答。我知道为什么
IllegalThreadStateException
会来。它只有当remove方法返回相同的对象时才会来,是吗?谢谢Nicolas,我的问题已经在你的建议之后了。谢谢Nicolas,我的问题已经在你的建议之后了。