您的位置:首页 > 编程语言 > Java开发

java中Synchronized用法介绍

2017-12-28 21:25 561 查看

synchronized关键字介绍

java提供关键字synchronized用来防止多个线程对同一临界区进行访问时,产生的资源冲突。要解决资源冲突就要引入一个锁的概念,

所有的对象都含有单一的锁,。

synchronized可以用来修饰非静态方法

public synchronized void a(){
*******
};


修饰同步代码块

public synchronized void a(){
synchronized(this){
*******
}
};


你可以把可能在多线程访问下发生冲突的代码段放到,同步代码块中,而不是修饰整个函数,被synchronized修饰的方法是很影响多线程性能的,虽然保证了程序的正确运行,更推荐使用同步代码块。同步代码块需要一个Object的参数,表示谁获取了这个Object的对象锁,那个线程就能运行这段代码块的内容,其他线程将会阻塞,如果参数为this就表示获取的是当前对象的锁。

当多个线程调用同一个对象中被synchronized修饰的某一个方法时,该对象都会被加锁,该对象的其他被synchronized修饰的方法只有等到该方法执行完后,对象的锁被释放后才有可能获得执行的机会(只针对于其他线程而言无法调用别的被synchronized修饰的方法,当前线程可以

package com.thread.study;

class A {
public synchronized void a() {
System.out.println(" i am a synchronized  static function");
try {
Thread.sleep(5000);
} catch (InterruptedException e) {

e.printStackTrace();
}
System.out.println("release the lock");
}

public synchronized void b() {
System.out.println(" try get lock");
}
}

public class SynchronizedTest {
public static void main(String[] args) {
A a = new A();
Thread one = new Thread(new Runnable() {
public void run() {

a.a();
}
});
one.start();
Thread two = new Thread(new Runnable() {

public void run() {

a.b();
}
});
two.start();
}
}


2个线程分别调度a对象中的a()方法和b()方法,a()运行时会沉睡5秒,使用Thread.sleep()方式,不会释放锁,而调用wait()方法是当前线程会释放锁,然后进入阻塞状态。当a()被one线程运行时,试图运行b()方法的线程阻塞至one线程运行完。结果如下



synchronized 修饰静态的方法和修饰类

public synchronized static void a(){
*******
};


public synchronized A(){
*******
};


静态的方法是直接和类挂钩的,当调用被synchronized修饰的静态方法,当一个线程调用其中的一个静态方法时,其他线程试图调用该类的该静态方法或其他静态方法时都会被阻塞,让我们修改一下上面的例子

package com.thread.study;

class A {
public synchronized static void a() {
System.out.println(" i am a synchronized  static function");
try {
Thread.sleep(5000);
} catch (InterruptedException e) {

e.printStackTrace();
}
System.out.println("release the lock");
}

public synchronized  static void b() {
System.out.println(" try get lock");
}
}

public class SynchronizedTest {
public static void main(String[] args) {
A a = new A();
Thread one = new Thread(new Runnable() {
public void run() {

A.a();
}
});
one.start();
Thread two = new Thread(new Runnable() {

public void run() {

A.b();
}
});
two.start();
}
}


结果


是一样的,但是如果b()方法如果不是静态的,two线程访问时不会被阻塞,

package com.thread.study;

class A {
public synchronized static void a() {
System.out.println(" i am a synchronized  static function");
try {
Thread.sleep(5000);
} catch (InterruptedException e) {

e.printStackTrace();
}
System.out.println("release the lock");
}

public synchronized  void b() {
System
4000
.out.println(" try get lock");
}
}

public class SynchronizedTest {
public static void main(String[] args) {
A a = new A();
Thread one = new Thread(new Runnable() {
public void run() {

A.a();
}
});
one.start();
Thread two = new Thread(new Runnable() {

public void run() {

a.b();
}
});
two.start();
}
}


结果如下



因为static 的a()方法是和类绑定的,而b方法是和对象a绑定的。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  java 线程