1.方法声明时使用,放在范围操作符(public等)之后,返回类型声明(void等)之前.这时,线程获得的是成员锁,即一次只能有一个线程进入该方法,其他线程要想在此时调用该方法,只能排队等候,当前线程(就是在synchronized方法内部的线程)执行完该方法后,别的线程才能进入.
例如:
public synchronized void synMethod() {
//方法体
}
//方法体
}
2.对某一代码块使用,synchronized后跟括号,括号里是变量,这样,一次只有一个线程进入该代码块.此时,线程获得的是成员锁.例如:
public int synMethod(int a1){
synchronized(a1) {
//一次只能有一个线程进入
}
}
synchronized(a1) {
//一次只能有一个线程进入
}
}
3.synchronized后面括号里是一对象,此时,线程获得的是对象锁.例如:
public class MyThread implements Runnable {
public static void main(String args[]) {
MyThread mt = new MyThread();
Thread t1 = new Thread(mt, "t1");
Thread t2 = new Thread(mt, "t2");
Thread t3 = new Thread(mt, "t3");
Thread t4 = new Thread(mt, "t4");
Thread t5 = new Thread(mt, "t5");
Thread t6 = new Thread(mt, "t6");
t1.start();
t2.start();
t3.start();
t4.start();
t5.start();
t6.start();
}
public void run() {
synchronized (this) {
System.out.println(Thread.currentThread().getName());
}
}
}
public static void main(String args[]) {
MyThread mt = new MyThread();
Thread t1 = new Thread(mt, "t1");
Thread t2 = new Thread(mt, "t2");
Thread t3 = new Thread(mt, "t3");
Thread t4 = new Thread(mt, "t4");
Thread t5 = new Thread(mt, "t5");
Thread t6 = new Thread(mt, "t6");
t1.start();
t2.start();
t3.start();
t4.start();
t5.start();
t6.start();
}
public void run() {
synchronized (this) {
System.out.println(Thread.currentThread().getName());
}
}
}
对于3,如果线程进入,则得到当前对象锁,那么别的线程在该类所有对象上的任何操作都不能进行.在对象级使用锁通常是一种比较粗糙的方法。为什么要将整个对象都上锁,而不允许其他线程短暂地使用对象中其他同步方法来访问共享资源?如果一个对象拥有多个资源,就不需要只为了让一个线程使用其中一部分资源,就将所有线程都锁在外面。由于每个对象都有锁,可以如下所示使用虚拟对象来上锁:
class FineGrainLock {
MyMemberClass x, y;
Object xlock = new Object(), ylock = new Object();
public void foo() {
synchronized(xlock) {
//access x here
}
//do something here - but don't use shared resources
synchronized(ylock) {
//access y here
}
}
public void bar() {
synchronized(this) {
//access both x and y here
}
//do something here - but don't use shared resources
}
}
MyMemberClass x, y;
Object xlock = new Object(), ylock = new Object();
public void foo() {
synchronized(xlock) {
//access x here
}
//do something here - but don't use shared resources
synchronized(ylock) {
//access y here
}
}
public void bar() {
synchronized(this) {
//access both x and y here
}
//do something here - but don't use shared resources
}
}
4.synchronized后面括号里是类,此时,线程获得的是对象锁.例如:
class ArrayWithLockOrder{
private static long num_locks = 0;
private long lock_order;
private int[] arr;
public ArrayWithLockOrder(int[] a)
{
arr = a;
synchronized(ArrayWithLockOrder.class) {//-----这里
num_locks++; // 锁数加 1。
lock_order = num_locks; // 为此对象实例设置唯一的 lock_order。
}
}
public long lockOrder()
{
return lock_order;
}
public int[] array()
{
return arr;
}
}
class SomeClass implements Runnable
{
public int sumArrays(ArrayWithLockOrder a1,
ArrayWithLockOrder a2)
{
int value = 0;
ArrayWithLockOrder first = a1; // 保留数组引用的一个
ArrayWithLockOrder last = a2; // 本地副本。
int size = a1.array().length;
if (size == a2.array().length)
{
if (a1.lockOrder() > a2.lockOrder()) // 确定并设置对象的锁定
{ // 顺序。
first = a2;
last = a1;
}
synchronized(first) { // 按正确的顺序锁定对象。
synchronized(last) {
int[] arr1 = a1.array();
int[] arr2 = a2.array();
for (int i=0; i<size; i++)
value += arr1[i] + arr2[i];
}
}
}
return value;
}
public void run() {
//
}
}
private static long num_locks = 0;
private long lock_order;
private int[] arr;
public ArrayWithLockOrder(int[] a)
{
arr = a;
synchronized(ArrayWithLockOrder.class) {//-----这里
num_locks++; // 锁数加 1。
lock_order = num_locks; // 为此对象实例设置唯一的 lock_order。
}
}
public long lockOrder()
{
return lock_order;
}
public int[] array()
{
return arr;
}
}
class SomeClass implements Runnable
{
public int sumArrays(ArrayWithLockOrder a1,
ArrayWithLockOrder a2)
{
int value = 0;
ArrayWithLockOrder first = a1; // 保留数组引用的一个
ArrayWithLockOrder last = a2; // 本地副本。
int size = a1.array().length;
if (size == a2.array().length)
{
if (a1.lockOrder() > a2.lockOrder()) // 确定并设置对象的锁定
{ // 顺序。
first = a2;
last = a1;
}
synchronized(first) { // 按正确的顺序锁定对象。
synchronized(last) {
int[] arr1 = a1.array();
int[] arr2 = a2.array();
for (int i=0; i<size; i++)
value += arr1[i] + arr2[i];
}
}
}
return value;
}
public void run() {
//
}
}
对于4,如果线程进入,则线程在该类中所有操作不能进行,包括静态变量和静态方法,实际上,对于含有静态方法和静态变量的代码块的同步,我们通常用4来加锁.
相关推荐
`synchronized`关键字有两种主要的使用方式:一种是在方法声明中使用,另一种则是在代码块中使用。 ##### 1. synchronized方法 在方法声明中添加`synchronized`关键字,可以将整个方法体变成同步代码块。例如: `...
synchronized 关键字可以被用于两种范围内:对象实例和类范围。 1. 对象实例范围:synchronized 关键字可以被用于对象实例的方法上,以防止多个线程同时访问同一个对象的 synchronized 方法。例如: ```java public...
"Java 中 synchronized 用法详解" Synchronized 是 Java 语言中用于解决多线程共享数据同步问题的关键字。它可以作为函数的修饰符,也可以作为函数内的语句,用于实现同步方法和同步语句块。在 Java 中,...
synchronized的两种用法** - **方法级别同步:** 可以通过在方法声明前加上`synchronized`关键字来同步整个方法。这将确保每次只有一个线程可以调用该方法。 ```java public synchronized void method() { // ...
4. **同步局部变量**:如果需要同步的资源是局部变量,则可以使用`synchronized`来声明一个代码块,将局部变量作为锁。 - 示例: ```java public void method() { Object localLock = new Object(); ...
本实例大全将全面解析`synchronized`的使用方式,包括同步方法、同步语句块、类锁和对象锁。 ### 1. 同步方法 同步方法是通过在方法声明前加上`synchronized`关键字实现的。这样,同一时间只有一个线程可以执行该...
本文将深入探讨`synchronized`的几种使用示例,包括方法加锁、代码块加锁(针对`this`和对象)以及静态方法加锁。 1. **方法加锁** 当在实例方法前使用`synchronized`关键字时,它会锁定当前对象的监视器,只有...
1. **synchronized的两种使用方式** - **方法同步**:在方法声明前加上`synchronized`关键字,这将使得整个方法成为同步方法,每次只有一个线程可以执行该方法。 ```java public synchronized void someMethod...
java多线程中synchronized关键字的用法 解压密码 www.jiangyea.com
一、`synchronized`的基本用法 1. **方法同步**:在方法声明前加上`synchronized`,整个方法都会被锁定,任何时刻只有一个线程能执行该方法。 ```java public synchronized void method() { // 方法体 } ``` 2. **...
synchronized 的使用方法可以分为两种,一种是使用 synchronized 关键字修饰方法,另一种是使用 synchronized 代码块。例如,在使用 synchronized void addOne() 方法时,可以使用 synchronized 关键字修饰方法,...
`synchronized`还有一种高级用法——同步类方法(静态方法),这会锁定整个类,而非单个对象: ```java public class MyClass { public static synchronized void method() { // ... } } ``` 在这种情况下,所有...
2. **synchronized的两种使用方式** - **synchronized方法**:在方法声明前加上`synchronized`关键字,整个方法体被视为同步代码块。这样,每次只有一个线程能执行该方法。 - **synchronized代码块**:使用`{}`...
这些房间可以被分为两种:上锁房间(synchronized 方法)和不上锁房间(普通方法)。每个对象都有一个钥匙(key),该钥匙可以打开所有上锁的房间。 Synchronized 方法 当一个线程想要进入一个上锁房间时,它需要...
本测试案例深入探讨了`synchronized`的使用方法,包括同步单个对象、同步多个对象以及成功与失败的场景对比。 一、`synchronized`关键字的基本概念 `synchronized`关键字可以修饰方法或用作代码块,其主要作用是...
在Java中,为了保证多线程环境下数据的一致性和安全性,可以采用两种主要的方法:`synchronized`和`volatile`。 ##### 1. synchronized关键字 `synchronized`是一种基于锁的同步机制,它可以应用于方法或者代码块...
Synchronized 的使用方法有四种: 1. synchronized 修饰普通方法 2. synchronized 修饰普通代码块 3. synchronized 修饰静态方法 4. synchronized 修饰静态方法中的代码块 在使用 synchronized 同步锁时,需要注意...
下面将详细介绍 `synchronized` 的四种主要用法。 1. **修饰实例方法**: 当 `synchronized` 修饰一个实例方法时,它会锁定当前对象的监视器,即所谓的“成员锁”。这意味着同一时间只有一个线程可以执行该方法。...
通过使用`synchronized`,可以确保同一时刻只有一个线程能够访问被标记为同步的方法或代码块,从而避免多线程环境下的数据不一致问题。 #### 一、基本概念 `synchronized`关键字主要具有以下特性: 1. **互斥性**...
通过在方法或代码块上使用`synchronized`,可以确保同一时间只有一个线程能访问这些代码区域,从而有效避免了多线程环境下的数据竞争和不一致性问题。 #### 二、synchronized的作用机制 `synchronized`主要通过对象...