【问题标题】:Referencing subclass in static variable在静态变量中引用子类
【发布时间】:2018-02-12 20:40:10
【问题描述】:

Intellij 检查工具警告在静态变量中引用子类不是一个好习惯,因为它可能导致死锁。使用以下文本:

此检查报告的类引用了它们自己的子类 他们的静态初始化器或静态字段。这样的参考可以 在多线程环境中导致 JVM 级别的死锁,当一个 线程尝试加载超类,另一个线程尝试加载 同时子类化。

以下示例表明:

class Generator {
    public static Generator fiveGenerator = new FixedGenerator(5);
    public static Generator sixGenerator = new FixedGenerator(6);

    int generateNumber() {
        //some generation code
    }
    private class FixedGenerator extends Generator {
        FixedGenerator(int num) {
            this.num = num;
        }

        @Override
        int generate() {
            return this.num;
        }
    }
}

请注意:

  • FixedGenerator 类是并且应该是私有的。

  • fiveGeneratorsixGenerator 是并且应该是公开的。

对此我有两个问题:

  • 这是一种不好的做法吗?为什么?这怎么会导致死锁?

  • 等效代码实现的正确方法是什么?

【问题讨论】:

  • 很难猜出这段代码应该做什么,所以很难给出建议。我在这里没有看到任何僵局的危险。此类中没有同步。
  • “据我所知,在静态变量中引用子类不是一个好习惯,因为它会导致死锁”。这不符合我的 - 你的来源(或声明背后的推理)是什么?
  • 遗憾的是,这是一个很好的问题,但有些人似乎并不理解这个问题。

标签: java deadlock


【解决方案1】:

此代码不会导致任何死锁。
死锁和并发有关,你没有并发。
可能有初始化问题,但你也不会因为FixedGenerator()调用Generator()Generator()没有调用FixedGenerator()而没有循环。

这是一种不好的做法吗?

这是因为类不应该引用/知道它们的子类。

等效代码实现的正确方法是什么?

您可以避免私有类中的继承。
作为替代方案,您可以选择组合而不是继承。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-09-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-05
    • 2011-01-12
    • 2013-07-05
    相关资源
    最近更新 更多