Java Keyword Synchronized learning record

Synchronized

Java programming ideas: each object contains a lock (also called "monitor"), it automatically becomes part of the object, call any synchronized method, the object is locked, no longer the object of any other call that synchronized method, unless the first method to complete their work, and unlock.
Features: Jvm level, unfair, pessimistic, exclusive, reentrant, heavyweight.
Action: modifying code blocks and methods.

A method of modifying code blocks and

synchronized modification static method, we can call it "Locks", that is, as long as there is a thread instance object gets the lock, other threads instance of an object need to wait. Non-static method modification, which we call the object lock, that is a different thread synchronization method instance object is under the same class can call.

/**
 * @PackageName com.a.squirrel.synchronize
 * @Author: squirrel
 * @Date: 2018/6/25 10:04
 * @Description: synchronized解析辅助类
 */
public class SynchronizedDescription {

    private String tmpStr;

    private int tmpInt;

    /**
      * @Author squirrel
      * @Description 非静态同步方法
      * @Date 2018/6/25
      * @Param [synchronizedDescription]
      * @return
     **/
    public synchronized void testSynchronizedMethod(SynchronizedDescription synchronizedDescription){
        System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:==========我是非静态同步方法=======");
        System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:调用非静态同步方法时间为:"+getNowTime());
        try {
            Thread.sleep(5000);// 当前线程休眠5s,休眠过程中不会释放锁
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    /**
      * @Author squirrel
      * @Description 同步代码块
      * @Date 2018/6/25
      * @Param [synchronizedDescription]
      * @return
     **/
    public void testSynchronizedBlockMethod(SynchronizedDescription synchronizedDescription){
        synchronized (synchronizedDescription){// 锁定实例对象
            System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:==========我是同步代码块=======");
            System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:调用同步代码块时间为:"+getNowTime());
            try {
                Thread.sleep(2000);// 当前线程休眠2s,休眠过程中不会释放锁
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    /**
      * @Author squirrel
      * @Description 静态同步方法
      * @Date 2018/6/25
      * @Param [synchronizedDescription]
      * @return
     **/
    public synchronized static void testSynchronizedStaticMethod(SynchronizedDescription synchronizedDescription){
        System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:==========我是静态同步方法=======");
        System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:调用静态同步方法时间为:"+getNowTime());
        try {
            Thread.sleep(10000);// 当前线程休眠10s,休眠过程中不会释放锁
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

    /**
      * @Author squirrel
      * @Description 获取当前时间
      * @Date 2018/6/25
      * @Param []
      * @return java.lang.String
     **/
    private static String getNowTime(){
        return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date());
    }

    public SynchronizedDescription(String tmpStr, int tmpInt) {
        this.tmpStr = tmpStr;
        this.tmpInt = tmpInt;
    }

    public String getTmpStr() {
        return tmpStr;
    }

    public void setTmpStr(String tmpStr) {
        this.tmpStr = tmpStr;
    }

    public int getTmpInt() {
        return tmpInt;
    }

    public void setTmpInt(int tmpInt) {
        this.tmpInt = tmpInt;
    }
}
/**
 * @PackageName com.a.squirrel.synchronize
 * @Author: squirrel
 * @Date: 2018/6/25 10:10
 * @Description: 测试类
 */
public class TestSynchronized {

    public static void main(String[] args) {
        // 创建阻塞队列
        final BlockingQueue<Runnable> queue = new ArrayBlockingQueue<>(100);
        // 创建线程池
        final ThreadPoolExecutor threadPool = new ThreadPoolExecutor(2,20,60, TimeUnit.SECONDS,queue);
        threadPool.allowCoreThreadTimeOut(true);
        for (int i =0;i<100;i++){
            threadPool.execute(new Runnable() {
                @Override
                public void run() {
                    final String tmpStr = Thread.currentThread().getName();
                    final String[] split = tmpStr.split("-");
                    int tmpInt = Integer.parseInt(split[split.length-1]);
                    SynchronizedDescription synchronizedDescription = new SynchronizedDescription(tmpStr,tmpInt);
                    // 调用同步代码块
                    synchronizedDescription.testSynchronizedBlockMethod(synchronizedDescription);
                    // 调用非静态同步方法
                    synchronizedDescription.testSynchronizedMethod(synchronizedDescription);
                    // 调用静态同步方法
                    synchronizedDescription.testSynchronizedStaticMethod(synchronizedDescription);
                }
            });
        }
    }
}

Operating results can verify the above conclusion:

Let's change the synchronization object synchronization code block:

    /**
      * @Author squirrel
      * @Description 同步代码块
      * @Date 2018/6/25
      * @Param [synchronizedDescription]
      * @return
     **/
    public void testSynchronizedBlockMethod(SynchronizedDescription synchronizedDescription){
        synchronized (SynchronizedDescription.class){// 锁定类对象
            System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:==========我是同步代码块=======");
            System.out.println("线程:"+synchronizedDescription.getTmpInt()+"-->:调用同步代码块时间为:"+getNowTime());
            try {
                Thread.sleep(2000);// 当前线程休眠2s,休眠过程中不会释放锁
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }


From the above chart we can draw a conclusion, here borrow a diagram to explain this conclusion:

The principle:

Depth understanding of the Java Virtual Machine: the object stored in memory layout may be divided into three regions: the first objects, instance data, and alignment padding.

synchronized object lock is a pointer to its monitor objects, each instance will have a monitor, which monitor you can create and destroy objects together, you can also attempt to acquire the object lock automatically generated when a thread. In the implementation of monitorenter instruction, we must first try to obtain the object lock, if the object is not locked, or the current thread already owns the lock of the object, then put the lock counter is incremented when the instruction execution monitorexit, release the lock while the lock counter will be minus one.

Guess you like

Origin www.cnblogs.com/yzss/p/10984666.html