多线程之synchronized
java的堆中信息是共享的,线程是把会堆中信息拷贝,对副本进行操作,操作完再同步堆中的信息,而堆中的信息可能被b线程修改了,a线程的副本还是未修改前的,此时就引发多并发问题。解决多并发的问题就是通过枷锁,使原先多个线程并行执行程序转为多个线程串行执行程序。
一个对象不管多少方法用synchronized修饰,都只拥有一把锁.
相关概念:
监视器
监视器可以看做是经过特殊布置的建筑,这个建筑有一个特殊的房间,该房间通常包含一些数据和代码,但是一次只能一个消费者(thread)使用此房间,
当一个消费者(线程)使用了这个房间,首先他必须到一个大厅(Entry Set)等待,调度程序将基于某些标准(e.g. FIFO)将从大厅中选择一个消费者(线程),进入特殊房间,如果这个线程因为某些原因被“挂起”,它将被调度程序安排到“等待房间”,并且一段时间之后会被重新分配到特殊房间,按照上面的线路,这个建筑物包含三个房间,分别是“特殊房间”、“大厅”以及“等待房间”。
简单来说,监视器用来监视线程进入这个特别房间,他确保同一时间只能有一个线程可以访问特殊房间中的数据和代码。
synchronized是一个重量级和重入锁,当一个线程持有锁时,这个线程再次获取相同的锁,是不用等待,可以直接获取,synchronized锁住的代码块,只有由持有锁的线程才能访问。
相关api简介:
Thread
Thread(Runnable target) 构造一个新线程,线程启动会调用target的run方法.
Object
notify()
唤醒在监视器里面的一个等待线程
wait()
让当前线程等待
例;
请编写2个线程,线程1顺序输出1,3,5,……, 99 等奇数,每个数 一 。
线程2顺序输出2,4,6……100等偶数,每个数 一 。
最终的结果要求是输出为 自然顺序:1,2,3,4,……99,100。
public class TestLock2 implements Runnable {private int num;private int initNum;public TestLock2(int num, int initNum) {this.num = num;this.initNum = initNum;}@Overridepublic void run() {synchronized (this) {while (initNum < num) {this.notify();System.out.println(Thread.currentThread().getName() + ":" + initNum);initNum++;try {this.wait();} catch (InterruptedException e) {e.printStackTrace();}}}}public static void main(String[] args) {//打印一百个数,两个线程个循环50次,两个都是用testLock2这个实例构造,testLock2里面的全局变量是共享的TestLock2 testLock2 = new TestLock2(51, 1);Thread thread1 = new Thread(testLock2);thread1.setName("线程1");Thread thread2 = new Thread(testLock2);thread2.setName("线程2");thread1.start();try {thread1.sleep(100);} catch (InterruptedException e) {e.printStackTrace();}thread2.start();}}
转载于:https://www.cnblogs.com/thomas-seven/p/9002791.html
总结
以上是生活随笔为你收集整理的多线程之synchronized的全部内容,希望文章能够帮你解决所遇到的问题。
- 上一篇: Oracle问题
- 下一篇: Postman接口测试之POST、GET