2 smile life smile_life_ 于 2017.12.19 11:06 提问

关于实现Runnable接口创建线程的测试问题,如图

图片说明

5个回答

ZhihengTao
ZhihengTao   2017.12.19 13:52
已采纳

首先,两个线程使用的runnable对象是相同的,不考虑寄存器等缓存的因素,可以认为两个线程中看到的i是相同的,都是runnable对象的一个属性。
其次,线程宏观上并行,但微观上不一定,和CPU的核数以及当前CPU的线程负载有关,所以常常有同一进程内线程交替执行的情况。为了保证程序的正确性,对于临界资源常常需要加锁。

对于你的测试情况,可能的运行流程之一是:
thread 1 (i=0 -> 20) [wait] -> thread 2 (i = 21-> 100) [destroy] -> thread 1 (i=100) [destroy]
即你所说的“在线程1准备输出20的时候换到了线程2执行,执行完线程2后再执行线程1,因为线程1是执行了输出语句,只是在显示到控制台的路上”

如果你想验证线程的切换,建议可以这样试一下:
使用两个属性i,j,两个线程分别写其中一个,然后分别在两个线程中观察两个属性值。即:
thread 1:
i++; print i, j
thread 2:
j++; print i, j

wb_snail
wb_snail   2017.12.19 12:41

你理解错了,不是一个线程对象,你new了两个Thread,虽然传入的是同一个Runnable实现类对象,但是实际运行的是两个互不相干的线程,i变量也是每个线程一份的

smile_life_
smile_life_ 也就是说 i 变量是这两个线程共享的,线程1变化了 i 变量的值,线程2再去运行,那么i 就是变化后的值
4 个月之前 回复
smile_life_
smile_life_ 除了有重复之外,这两个线程的i变量是连续的,通过断点调试也可以知道。也就是说图中的方式是多个线程可以共享线程的target类的实例变量
4 个月之前 回复
fqewfwerfw
fqewfwerfw   2017.12.19 11:14

你的for循环便利是小于100,最大是99,况且线程保持独立性,不会被其他线程所共享

smile_life_
smile_life_ 实现了runnable接口,线程1和线程2 负责的都是同一个对象,也就是说i是共享的才对
4 个月之前 回复
tonlon924
tonlon924   2017.12.19 11:51

线程交替获得cpu时间片,线程1先执行,故会出现线程1先执行完成的可能。谢谢。

smile_life_
smile_life_ 也就是说 i 变量是这两个线程共享的,线程1变化了 i 变量的值,线程2再去运行,那么i 就是变化后的值
4 个月之前 回复
smile_life_
smile_life_ 我想问的问题在图片里面,为什么输出的是20,是不是在线程1准备输出20的时候换到了线程2执行,执行完线程2后再执行线程1,因为线程1是执行了输出语句,只是在显示到控制台的路上,这个时候i值的任何变化都与线程1的输出语句无关了?
4 个月之前 回复
u011444274
u011444274   2017.12.22 01:32

new了两个线程,两个线程每次只有一个执行,且随机的

Csdn user default icon
上传中...
上传图片
插入图片
准确详细的回答,更有利于被提问者采纳,从而获得C币。复制、灌水、广告等回答会被删除,是时候展现真正的技术了!