黑马程序员技术交流社区
标题:
同步问题代码排错
[打印本页]
作者:
祁振朋
时间:
2013-3-19 00:04
标题:
同步问题代码排错
本帖最后由 祁振朋 于 2013-3-19 18:04 编辑
class FourTicket
{
public static void main(String[] args)
{
new TicketSeller ().start();
new TicketSeller ().start();
new TicketSeller ().start();
new TicketSeller ().start();
}
}
class TicketSeller extends Thread
{
private static int ticket=100;
private Object obj=new Object();
public void run(){
while (true)
{
synchronized(obj)
{
if(ticket<=0)
{break;}
try
{
Thread.sleep(1000);
}
catch (Exception e)
{
e.printStackTrace();
}
System.out.println(getName()+"售出第"+ticket +"张票");
ticket--;
}
}
}
}
复制代码
编译没错,可是不能实现同步。请问是哪儿错了?
作者:
李尧
时间:
2013-3-19 00:17
我复制你的代码测试了一下,问题可能是出在第16行:private Object obj=new Object();
你每次new TicketSeller ().start(); 也就new了一个Object(); 这样你4个线程用的4个Object对象,锁不唯一,所以就不同步了.
改成 private static Object obj=new Object(); 再试试看.
这是我个人看法,坐等高人给出更专业的解释.
作者:
曹玉龙
时间:
2013-3-19 00:40
本帖最后由 曹玉龙 于 2013-3-19 00:45 编辑
锁不结实,换把锁就好了,代码如下:
class FourTicket {
public static void main(String[] args) {
new TicketSeller().start();
new TicketSeller().start();
new TicketSeller().start();
new TicketSeller().start();
}
}
class TicketSeller extends Thread {
private static int ticket = 100;
public void run() {
while (true) {
//用本类作锁即可
synchronized (TicketSeller.class) {
if (ticket <= 0) {
break;}
try {
Thread.sleep(1000);
} catch (Exception e) {
e.printStackTrace();
}
System.out.println(getName() + "售出第" + ticket + "张票");
ticket--;
}
}
}
}
复制代码
作者:
杨玉辉
时间:
2013-3-19 00:44
本帖最后由 杨玉辉 于 2013-3-19 00:50 编辑
兄弟这个不多解释,实现同时卖票,线程同步就需要卖的是同一个资源:ticket
这时你的视频内容未看到后面的更深的知识点,建议你能弄懂这个练习锁,要表达的意思就是锁的作用,要想实现同步,还需共享资源(后面的视频可以看到)
至于下图出现负数的情况,完全是因为缺少必要的线程锁,出现了线程的等待唤醒机制的时候,不同线程抢夺了cpu 执行权,这些内容后面的视频都有涉及。
到时候你要做的就是,回头再来复习一下,加深理解synchronized 的作用,看看是不是有新的收获
ADJP8)7K80`E5LFJ1TGTK@I.jpg
(43.72 KB, 下载次数: 1)
下载附件
2013-3-19 00:50 上传
作者:
杨玉辉
时间:
2013-3-19 00:44
本帖最后由 杨玉辉 于 2013-3-19 00:46 编辑
奇怪,还会有重复内容,改了
作者:
谭辉
时间:
2013-3-19 10:33
本帖最后由 谭辉 于 2013-3-19 10:38 编辑
问题在于你创建线程时,new了四个不同的对象启动线程,自然四个线程的锁不是同一个锁;
可以把锁改成TicketSeller.class,或者用实现Runable接口的方式创建线程
class FourTicket
{
public static void main(String[] args)
{
TicketSeller t=new TicketSeller();
Thread t1=new Thread(t);
Thread t2=new Thread(t);
Thread t3=new Thread(t);
Thread t4=new Thread(t);
t1.start();
t2.start();
t3.start();
t4.start();
}
}
class TicketSeller implements Runnable
{
private static int ticket=100;
private Object obj=new Object();
public void run(){
while (true)
{
synchronized(obj)
{
if(ticket<=0)
{break;}
try
{
Thread.sleep(10);
}
catch (Exception e)
{
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName()+"售出第"+ticket +"张票");
ticket--;
}
}
}
}
复制代码
作者:
陈丽莉
时间:
2013-3-19 14:40
若还有问题,请继续追问;没有的话,请将帖子分类改成【已解决】~
欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/)
黑马程序员IT技术论坛 X3.2