我正在尝试使用多个线程的代码。 以下是我的代码:
package com.thread.practice;
public class ThreadPratice1 {
public static void main(String[] args) {
MyRunnable r = new MyRunnable();
Thread t1 = new Thread(r, "Thread 1");
Thread t2 = new Thread(r, "Thread 2");
t1.start();
t2.start();
}
}
package com.thread.practice;
public class MyRunnable implements Runnable {
private static int i = 0;
@Override
public void run() {
for(i = 0; i <10;i++){
System.out.println("Thread: "+ Thread.currentThread().getName()
+" value of i: "+i);
try {
//System.out.println("Thread: "+ i);
Thread.sleep(1000);
//System.out.println("inside runnable: "+Thread.currentThread().getState());
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
但是在输出中,它总是在开头两次将i的值打印为0。
输出有点像这样:
Thread: Thread 1 value of i: 0
Thread: Thread 2 value of i: 0
Thread: Thread 1 value of i: 2
Thread: Thread 2 value of i: 2
Thread: Thread 1 value of i: 3
Thread: Thread 2 value of i: 4
Thread: Thread 1 value of i: 5
Thread: Thread 2 value of i: 6
Thread: Thread 1 value of i: 7
Thread: Thread 2 value of i: 8
Thread: Thread 1 value of i: 9
请有人帮助我理解这个问题吗?
答案 0 :(得分:2)
因为执行两个线程时i
的值为0
。
换句话说,线程1和线程2几乎同时盯着,所以他们两个为第一个循环设置i
为0。
for(i = 0; i <10;i++) {
然后,线程之间的值会发生变化,因为您将i
设置为静态。所以它将在你的两个线程之间共享。
答案 1 :(得分:2)
你做了#34;我&#34; static,这意味着它将在所有线程和对象上相同。拿走静态修改器,你的代码就能正常工作。
编辑:我误解了你的问题 - 在for循环中没有将i设置为0,它看起来像这样:
for(;i<10;i++) { /*mycode*/}
这两个中的一个可能是你想要的,你的问题有点模糊
答案 2 :(得分:0)
i
的值。执行for循环需要有限的时间。由于您(几乎)一起启动线程,因此在另一个线程完成一个循环后,两个线程可能会也可能不会打印i
。因为你没有做到确保线程安全,所以结果将像你得到的那样无法预测。
答案 3 :(得分:0)
首先,您不应该使用原始 int 类型进行并发,它不是线程安全的,它可能会导致Race Condition,
并尝试使用AtomicInteger
替换int
,它的线程安全。例子可能是:
public class ThreadPratice1 {
public static void main(String[] args) {
AtomicInteger number = new AtomicInteger(0);
MyRunnable r = new MyRunnable(number);
Thread t1 = new Thread(r, "Thread 1");
Thread t2 = new Thread(r, "Thread 2");
t1.start();
t2.start();
}
}
class MyRunnable implements Runnable {
private AtomicInteger number;
public MyRunnable(AtomicInteger number) {
this.number = number;
}
@Override
public void run() {
while (number.get() < 10) {
System.out.println("Thread: " + Thread.currentThread().getName()
+ " value of i: " + number.getAndIncrement());
}
}
}