当前位置: 首页 > 知识库问答 >
问题:

新类与新对象用于java中的锁

鱼志学
2023-03-14

从类和对象创建的锁有什么区别吗?

class AWTInvocationLock {}
Object lock = new AWTInvocationLock();

public void foo(){
    synchronized (lock) {
        // ...
    }
}

public Object lock = new Object();
public void bar(){
    synchronized (lock) {
        // ...
    }
}

java.awt中,我看到了这段代码,我想知道类AWTInvocationLock{}的想法,而不仅仅是new Object()

static void invokeAndWait(Object source, Runnable runnable)
    throws InterruptedException, InvocationTargetException
{
    // ...

    class AWTInvocationLock {}
    Object lock = new AWTInvocationLock();

    InvocationEvent event =
        new InvocationEvent(source, runnable, lock, true);

    synchronized (lock) {
        Toolkit.getEventQueue().postEvent(event);
        while (!event.isDispatched()) {
            lock.wait();
        }
    }

    //...
}

共有2个答案

拓拔俊艾
2023-03-14

当调用锁定特定对象的方法时,它会锁定该对象的实例,直到方法调用完成。从这个角度来看,实例化需要锁定的对象的位置并不重要,只要它在方法调用期间保持相同的对象,以实现锁定结果。

第一个代码段创建一个在处理程序实例中定义的对象(该类上有方法foo())。这意味着这个处理程序不会是单线程的,因为它总是锁定在您创建的锁对象的同一个实例上。

AWT方法通过创建另一个独立于处理程序实例的锁对象来增强这一点。这意味着处理程序的一个实例可以为不同的AWT组件处理多个事件,只要每个事件都由专用的锁对象控制(awtinocationlock())。

南宫书
2023-03-14

最好稍微描述一下代码:

class AWTInvocationLock {}
    Object lock = new AWTInvocationLock();

    InvocationEvent event =
        new InvocationEvent(source, runnable, lock, true);

    synchronized (lock) {
        Toolkit.getEventQueue().postEvent(event);
        while (!event.isDispatched()) {
            lock.wait();
        }
    }

锁定对象引用正在转义本地范围。ref存储InvocationEvent对象中:

InvocationEvent event =
            new InvocationEvent(source, runnable, lock, true);

EventQueue的调度线程正在侦听已发布的事件对象。线程对每个事件调用dispatch()方法。我还没有看过源代码,但我猜调用事件。dispatch()方法伪代码如下所示;

 1. synchronize(lock)
 2. runnable.run() -- store any exceptions to a "throwable" reference variable
 3. lock.notify()

因此,lock对象上的EventQueuedispatch线程调用notify(),这将从下一行的wait()调用中释放调用invokeAndWait()的线程。

从类创建的锁和从对象创建的锁有什么区别吗?

awtinocationlock是一个具有方法作用域的命名内部类。我从没在野外见过。这是语言中非常晦涩的一部分,我认识的人几乎都不知道。我永远不会使用它,因为Javadoc甚至不识别它们,也不会为它们生成文档!

 类似资料:
  • 我正在进行一些考试修改工作,创建了一个Employee抽象类和两个扩展到Employee类的其他类(AcademyicEmployee和ProfessionalEmployee)。 我在Employee类中设置了一个公共静态void main来运行这些行: 我知道您不能实例化一个抽象类,并且创建的实际对象是“new”关键字之后的任何内容,但为什么允许我这样做: 我想它的工作方式是“数据类型”然后“

  • 是否有一种方法可以从数据库中读取序列化对象。ser文件并更新或删除已序列化的对象之一? 下面是我的代码,读取的对象类型'驱动程序':

  • 问题内容: 试图从HQL查询创建对象,但无法弄清楚我在做什么错。 查询: (或者我应该使用新的MyCustomList(product.code,SUM(…,即使未映射)?)现在我想将此返回的列表转换为类似的对象: 检索数据: 使用Play框架 问题答案: 我认为第15.6节。select子句涵盖您要实现的目标: 15.6。选择子句 … 查询可以将多个对象和/或属性作为类型数组返回 : 或作为:

  • 是否可以在不创建新实例的情况下更改java中File类的文件路径? 返回 现在我想转到父目录。我想我可以用这样的东西 但我得用 我还有其他方法可以达到同样的效果吗?或者我可以创建多个实例,将它们存储在一个数组中,同时处理两个对象(目录)?

  • 我想在对象的现有状态上合并/覆盖新字段,这样param1就不会被删除 这样做 将导致MongoDB完全按照要求执行,并将some_key设置为该值。替换旧的。 我正在使用Java客户机,但任何示例都将受到赞赏

  • 另一个这个程序包帮助你的地方就是提供许多既支持面向对象设计理念又有共通功能的许多对象。 The PeriodicalExecuter object 这个对象提供一定间隔时间上重复调用一个方法的逻辑。 Method Kind Arguments Description [ctor](callback, interval) constructor callback: a parameterless f