【问题标题】:Ambiguous call from static context in JavaJava中静态上下文的模糊调用
【发布时间】:2014-08-28 01:16:57
【问题描述】:

main 方法尝试访问 var,但导致调用不明确。为什么? Base1 中的实例变量 var 无论如何都无法从静态上下文中访问(可见?)。

  class Base1 {
      int var;
  }

  interface Base2 {
      public static final int var = 0;
  }

  class Test extends Base1 implements Base2 { 
      public static void main(String args[]) {
          System.out.println("var:" + var); 
      }
  }

【问题讨论】:

  • @Pablo,包没关系。把代码sn-p放到一个文件里看看结果就行了。
  • @AlexR "错误 - 主文件中至少需要一个公共类"
  • 好吧,公开其中一个类。不是这个问题。
  • 错误信息一目了然:对 var 的引用不明确,Bof.Base1 中的变量 var 和 Base2 中的变量 var 都匹配
  • @AlexR,你是对的,我删除了答案。我怀疑答案更复杂,我认为这不可能是编译器问题。

标签: java static ambiguous non-static


【解决方案1】:

JLS rule for field access ambiguity

如果标识符命名了多个可访问(第 6.6 节)成员字段 键入T,则字段访问不明确且编译时错误 发生。

还有on the subject of accessibility

引用类型的成员(类、接口、字段或方法),或 类类型的构造函数,仅当类型为 可访问,并且声明成员或构造函数允许访问:

不区分实例字段访问是否会导致static上下文中的编译错误。

请注意,您本可以拥有

public static void main(String args[]) {
    Test test = new Test();
    System.out.println("var:" + test.var); 
}

你仍然有歧义。

【讨论】:

    【解决方案2】:

    为了明确起见,请将接口名称作为限定前缀:

    class Test extends Base1 implements Base2 { 
    
          public static void main(String args[]) {
              System.out.println("var:" + Base2.var); 
          }
     }
    

    【讨论】:

    • 有时编译器并不像我们期望的那样智能。代码的作者可能意味着非静态字段Base2.var 在这种情况下它是模棱两可的(并且是错误的)。 (另一方面,最好编写明确的代码,因为人脑需要一些能力来理解这一点。只需编写一个白痴理解的代码,而不是编译器也理解它:)
    【解决方案3】:

    在第一步编译器将在您扩展的类和您实现的接口中查找变量 var。因为它在第二步的两个地方都找到了一个变量,所以它显示了歧义。

    【讨论】:

      【解决方案4】:

      静态和非静态上下文不决定如何访问变量

      访问修饰符是实际规则的...

      将 Base1 中 var 的访问修饰符 更改为 private 并且歧义消失了,尽管这可能不是您想要的方式形成但访问修饰符实际上决定了对实例变量的引用,而不是静态的非静态上下文。

      class Base1 {
          private int var;
          //static int var=5;
      }
      
      interface Base2 {
          public static final int var = 0;
      }
      
      class ambiguousNonStaticCall extends Base1 implements Base2 { 
          public static void main(String args[]) {
              System.out.println("var:" + var); 
          }
      }
      

      以上代码编译正常。

      【讨论】:

        猜你喜欢
        • 2011-05-27
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2010-12-02
        • 1970-01-01
        • 1970-01-01
        • 2018-08-29
        • 1970-01-01
        相关资源
        最近更新 更多