2012-04-24 29 views
3

它无处不在,静态方法不能被重写,但是当我试图减少访问说明符说从公共保护它会给出一个错误。例如在java中静态方法重载的奇怪例子

public class StaticOverrideFunda { 

    public static void foo(){ 
     System.out.println("Parent Foo"); 
    } 
} 

public class B extends StaticOverrideFunda{ 


    protected static void foo(){ 
     System.out.println("Child Foo"); 
    } 

    /** 
    * @param args 
    */ 
    public static void main(String[] args) { 
     // TODO Auto-generated method stub 
     B.foo();    
    } 
} 

它说

不能减少继承的方法

这样的知名度INSENSE它是继压倒一切的规则,为什么我们要说富没有被覆盖在B班?为什么我们说这是隐藏/遮蔽而不是压倒一切?

+4

“它遵循最重要的规则”:错误。它打破了“不能降低继承方法的可见性”条款。你的问题到底是什么? – Viruzzo 2012-04-24 11:52:48

回答

8

它下面一些相同的规则作为压倒一切的,但是,这并不意味着它是压倒一切的。在这种情况下,它是“在重写和隐藏要求” section 8.4.8.3 of the JLS规则,:

访问修饰符(6.6节)压倒一切的或隐藏的方法必须至少提供尽可能多的访问,因为重写或隐藏的方法如下:[...]

它仍然不重写,因为该方法不会被调用多态 - 你不能写一个通话将有时最终调用StaticOverrideFunda.foo有时最后叫B.foo;目标完全是在编译时确定的。

值得回顾8.4.8节的其余部分,其中定义为作为在实例方法上发生的事情而被重写。

+2

嗯,这对我来说是一个惊喜。不允许隐藏方法比隐藏方法具有更少的可见性有什么意义?这对于可以多态调用的方法来说是有意义的,因为任何可以调用超类方法的东西都必须被允许调用子类。但是,隐藏而不是覆盖的静态方法并非如此。 – Wyzard 2012-04-24 11:59:23

+1

@Wyzard:我同意禁止降低能见度有点奇怪。然而,它有可能试图避免出现明确调用Subclass.foo()这种私有方法的情况,该方法通常会解析为“Superclass.foo()”。无论哪种方式,它的行为都完全按照JLS来进行,而且还没有压倒一切。老实说,我建议不要在与子类静态方法同名的子类中声明一个静态方法。这只会导致混乱。 – 2012-04-24 12:03:40

-1

你自己在你的问题中发布了答案,覆盖意味着在相同方法的子类中有不同的代码。由于无法重写静态方法,因此无法通过修改访问说明符来使用可见性。