Java - 使用循环填充线程的ArrayList

时间:2013-08-23 21:41:32

标签: java multithreading arraylist

这个问题可能很容易回答,但我只是不明白。 我减少了我的问题,直到留下这一小段代码才能找到这个问题的“起源”: 我正在尝试用循环填充线程的ArrayList。

public static int u=0;

public void test(){
    while (u <10) {
        synchronized(threadList){
            threadList.add(u, new Thread(){                
                @Override public void run(){                    
                    System.out.println("Thread at Index: " + u);                     
                } 
            });
        }
        u++;            
    }

    threadList.get(2).start();    
}

在最后一行,我想通过启动索引'2'处的线程来测试上面的循环。 我期待控制台显示“Thread at Index:2”,但显示如下: “指数线程:10” 无论我在“.get(int)” - 方法中写入哪个整数,我都会收到索引“10”。

为什么?以及如何解决这个问题?

线程的创建似乎有效......整数'你'是问题吗?

我感谢任何帮助! 提前谢谢!

3 个答案:

答案 0 :(得分:9)

u方法

中引用run
@Override public void run(){                    
    System.out.println("Thread at Index: " + u);                     
} 

检索u的当前值。在循环结束时和线程运行时,该值为10

尝试以下

public static int u = 0;

public void test(){
    while (u <10) {
        synchronized(threadList){
            threadList.add(u, new Thread(){     
                int i = u;

                @Override public void run(){                    
                    System.out.println("Thread at Index: " + i);                     
                } 
            });
        }
        u++;            
    }

    threadList.get(2).start();    
}

在您的匿名Thread课程中,您将实例字段i设置为调用构造函数时的值u,并在run()时打印该值被执行。

您在尚未执行的上下文中引用u,一个帖子。当最终调用run()方法时,程序将评估变量u,但是在程序执行的那一点上,它的值将为10.相反,如果你执行上述操作,变量i将在该确切时刻保存该值。这是因为当新的Thread启动并执行时,会进行字段初始化并立即评估u

答案 1 :(得分:1)

    while (u <10) {
        synchronized(threadList){

            final int u_final = u;

            threadList.add(u, new Thread(){                
                @Override public void run(){                    
                    System.out.println("Thread at Index: " + u_final );
                } 
            });
        }
        u++;            
    }

使用final变量,很清楚它的值是什么,因为它永远不会改变。

答案 2 :(得分:-1)

尝试两种方式:

package com.test;

import java.util.ArrayList;

public class TestThread5 {
    public static int u=0;
    public ArrayList<Thread> threadList = new ArrayList<>();
    public void test() throws InterruptedException{
        while (u <10) {
            synchronized(threadList){
                threadList.add(u, new Thread(){                
                    @Override public void run(){                    
                        System.out.println("Thread at Index: " + u);                     
                    } 
                });
            }
            u++;            
        }
        for ( u = 0; u < 10; u++) {
            Thread thread = threadList.get(u); 
            thread.start();
            thread.join();
        }
       // threadList.get(2).start();    
    }
    public static void main(String[] args) throws InterruptedException {
        new TestThread5().test();
    }
}

package com.test;

import java.util.ArrayList;
import java.util.Iterator;

public class TestThread4 {
    public  int u=0;
    public ArrayList<Thread> threadList = new ArrayList<>();
    public void test() throws InterruptedException{
        while (u <10) {
            synchronized(threadList){
                threadList.add(u, new MyThread(u));
            }
            u++;            
        }
        for(Thread thread :threadList){
            thread.start();
            thread.join();
        }
       // ((Thread) threadList.get(2)).start();    
    }
    public static void main(String[] args) throws InterruptedException {
        new TestThread4().test();
    }
}
class MyThread extends Thread{
    private int u;
    public MyThread(int u){
        this.u = u;
    }
    @Override
    public void run() {
        System.out.println("Thread at Index: " + u);  
    }

}