Synchronized 关键字

2019-01-19  本文已影响89人  正规程序员

Java多线程中的同步机制会对资源进行加锁,保证同一时刻只有一个线程操作该资源,避免多个线程同时访问该资源造成冲突。

Synchronized是Java中的同步锁关键字,主要修饰的对象有:

修饰非静态方法示例:

    /**
     * a()方法是经过synchronized修饰的非静态方法,同步的是在外部调用的对象实例。
     * 由于外部多线程中是不同的对象实例,则对count的操作未实现同步(示例现象:未有序递减)。
     */
    public synchronized void a() {
        print();
    }

修饰静态方法示例:

    /**
     * b()方法是经过synchronized修饰的静态方法,同步的是本类的对象实例,和外部多线程中的调用对象实例无关。
     * 外部多线程,谁先获得本类的对象锁,其他线程则处于阻塞状态,直到获得锁的线程解锁。
     */
    public static synchronized void b() {
        print();
    }

修饰方法块示例:

    /**
     * c()和d()是静态方法和非静态方法的壳,内部synchronized修饰的是方法块。
     * 同步的对象是synchronized(obj)内的非NULL的Object。
     * 1.若obj为Sync.class,则同步Sync.class本身,同理synchronized修饰静态方法;
     * 2.若obj为类属性,如string变量,则同步的是变量所属对象实例,即是外部调用的对象实例。
     */
    public void c() {
        synchronized (string) {
            print();
        }
    }

    public static void d() {
        synchronized (Sync.class) {
            print();
        }
    }

外部多线程中不同对象实例的调用:

    Count.INSTANT.count = 100;
    new Thread(() -> new Sync().a()).start();
    new Thread(() -> new Sync().a()).start();

print打印操作如下:

    public static void print() {
        while (Count.INSTANT.count > 0) {
            Count.INSTANT.count = Count.INSTANT.count - 1;
            Log.d("Sync", "count = " + Count.INSTANT.count);
        }
    }

单一数据源如下:

/**
 * 序列化单例模式,确保操作的是单一数据源
 */
public enum Count {
    INSTANT;
    public int count;
}

补充知识点

上一篇下一篇

猜你喜欢

热点阅读