java多线程并发处理(java线程并发与同步的概念)java教程 / Java中多线程同步与并发控制...

wufei123 发布于 2024-05-16 阅读(33)

关于多线程与并发,多线程是指系统在轮流执行不同的方法,由于CPU速度太快,所以我们看起来是同步执行的,这就是所谓的线程并发;线程并发时访问共享变量会引起数据不一致的问题,解决数据的不一致问题就需要用到线程同步。

此篇讲线程同步技术同步技术引出:先来个程序测试不同步的情况:classMyRunableimplementsRunnable{ privateint ticket = 10; @Override

publicvoidrun(){ while (true){ if (ticket > 0 ) { System.out.println(Thread.currentThread().getName()+

":ticket="+ticket--); try { Thread.sleep(1000); }

catch (InterruptedException e) { e.printStackTrace(); } }

else { System.out.println("卖光了"); break; } } } }

publicclassA{ publicstaticvoidmain(String[] args)throws InterruptedException { MyRunable r =

new MyRunable(); Thread t1 = new Thread(r,"线程1"); Thread t2 = new Thread(r,"线程2"

); Thread t3 = new Thread(r,"线程3"); Thread t4 = new Thread(r,"线程4"); t1.start(); t2.start(); t3.start(); t4.start(); } }

结果:可以看出卖票没有顺序的,而且把一张票卖给多个人,这肯定是不符合要求的线程2:ticket=10线程3:ticket=9线程1:ticket=8线程4:ticket=7线程2:ticket=6线程4:ticket=6。

线程3:ticket=4线程1:ticket=5线程1:ticket=3线程2:ticket=2线程3:ticket=3线程4:ticket=1 卖光了 卖光了 卖光了 卖光了为什么呢?1、run方法内的代码并不是同步执行完毕的,而是分时间段来执行的;

判断票数是否大于0,如果线程a判断大于0, 现在a挂起了,它之后会继续在其他时间片执行,现在线程b将票已经卖光了(ticket = 0),但是线程a获取了时间片,他会继续将0减1,结果可能就会出现-1的结果;

2、还有run方法中这句System.out.println(Thread.currentThread().getName()+":ticket="+ticket--);println是线程安全的,但是传入的ticket变量是在进行自减,自减其实是分为三步来完成的:

1.ticket = this.ticket 先取原值2.ticket+1 再加法运算3.ticket = ticket 再赋值所以,以上程序在非并发情况下,可能产生一张票卖多个人,卖空票,这就不是我们需要的结果,因为需要线程的同步来实现。

修改run方法,synchronized关键字当前线程执行synchronized方法的时候,其他线程是不能调用这个方法的,只有当前线程当前方法执行完毕后其他线程才会有机会来抢占publicvoidrun

() { while (true) { //同步代码块 synchronized (this) { if (ticket >

0) { try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } System.

out.println(Thread.currentThread().getName() + ":ticket=" + ticket--); } else { System.

out.println("卖光了"); break; } } } }

发表评论:

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

河南中青旅行社综合资讯 奇遇综合资讯 盛世蓟州综合资讯 综合资讯 游戏百科综合资讯 新闻42368