将参数传递给synchronized块的目的是什么? [英] What is the purpose of passing parameter to synchronized block?

查看:268
本文介绍了将参数传递给synchronized块的目的是什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我知道


当你同步一段代码时,你要指定你想要使用哪个对象的锁
锁,所以你可以,例如,使用一些
第三方对象作为这段代码的锁。这给你
能够在
a单个对象中拥有多个锁定代码同步。

When you synchronize a block of code, you specify which object's lock you want to use as the lock, so you could, for example, use some third-party object as the lock for this piece of code. That gives you the ability to have more than one lock for code synchronization within a single object.

但是,我不明白需要将参数传递给块。因为我是否传递String的实例并不重要,无论传递给块的参数如何,一些随机类的实例作为同步块的同步块都能正常工作。

However, I don't understand the need of passing argument to the block. Because it doesn't matter whether I pass String's instance, Some random class's instance to the synchronized block as the synchronized block works perfectly irrespective of the parameter being passed to the block.

所以我的问题是如果反正同步阻止两个线程同时进入临界区。那么为什么需要传递一个论点呢? (我的意思是默认获取一些随机对象的锁定。)

我希望我正确地解决了我的问题。

I hope I framed my question correctly.

我尝试了以下示例,其中随机参数是同步块。

I have tried the following example with random parameters being to the synchronized block.

public class Launcher {

    public static void main(String[] args) {
        AccountOperations accOps=new AccountOperations();

        Thread lucy=new Thread(accOps,"Lucy");
        Thread sam=new Thread(accOps,"Sam");

        lucy.start();
        sam.start();

    }

}

使用非静态同步块:

public class AccountOperations implements Runnable{
    private  Account account = new Account();


    public void run(){

        for(int i=0;i<5;i++){

            makeWithdrawal(10);                 
        }
    }

    public  void makeWithdrawal(int amount){
        String str="asd"
        synchronized (str /* pass any non-null object the synchronized block works*/) {
            if(account.getAmount()>10){

                try{
                    Thread.sleep(5000);             
                }catch(InterruptedException e){
                    e.printStackTrace();
                }
                account.withdraw(amount);
                System.out.println(Thread.currentThread().getName()+" has withdrawn 10, current balance "+ account.getAmount());
            }else{
                System.out.println("Insufficient funds "+account.getAmount());
            }
        }

    }

}

使用静态同步块:

public class AccountOperations implements Runnable{
    private static Account account = new Account();


    public void run(){

        for(int i=0;i<5;i++){

            makeWithdrawal(10);                 
        }
    }

    public static void makeWithdrawal(int amount){

        synchronized (String.class /* pass any class literal synchronized block works*/) {
            if(account.getAmount()>10){

                try{
                    Thread.sleep(5000);             
                }catch(InterruptedException e){
                    e.printStackTrace();
                }
                account.withdraw(amount);
                System.out.println(Thread.currentThread().getName()+" has withdrawn 10, current balance "+ account.getAmount());
            }else{
                System.out.println("Insufficient funds "+account.getAmount());
            }
        }

    }

}


推荐答案


如果无论如何同步阻止两个线程同时进入临界区。那么为什么需要传递参数?

if anyways synchronized block stops two threads from entering the critical section simultaneously. Then why there is a need of passing an argument?

同步块根据传递给它的对象决定停止哪些线程。您传递的对象充当由synchronized块保护的关键部分的标识符。

Synchronized block decides which threads to stop based on the object that you pass to it. The object that you pass serves as the identifier of the critical section guarded by the synchronized block.

您的程序中可能有许多关键部分,所有部分都可以执行彼此同时。例如,如果必须同时访问两个不相关的集合,则可以为每个集合设置单独的临界区。这样,只有当其他线程已经访问同一个集合时,才会停止线程;访问两个不同集合的两个不同线程将被允许同时进行。

You may have many critical sections in your program, all of which could be executed concurrently with each other. For example, if you have two unrelated collections that must be accessed concurrently, you can set up separate critical sections for each collection. This way threads would be stopped only when other threads are already accessing the same collection; two different threads accessing two different collections would be allowed to proceed concurrently.

你的第一个例子是非平凡的。它起作用的原因是字符串对象被初始化为字符串文字。由于文字的实习,进入函数的所有线程都将获得相同的 String 对象,因此synchronized块将正确保护临界区。

Your first example is non-trivial. The reason it works is that the string object is initialized to a string literal. Due to literal's interning, all threads entering the function will obtain the same String object, so the synchronized block will properly guard the critical section.

这篇关于将参数传递给synchronized块的目的是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆