2011-06-17 59 views
0

对于以下Java代码段,“run”的方法发生四次。我对这四次“跑步”事件的关系颇感混淆。原始代码很长,我只保留与我的问题相关的部分。关于方法覆盖

1. public final class Job extends AbstractJob { 
    2. private Job() { 
    3. } 
    4. public static void main(String[] args) throws Exception {  
    5.   new Job().run(new Path("testdata"), output, 10); 
    6. } 
    7. 
    8. @Override 
    9. public int run(String[] args) throws IOException, ClassNotFoundException,  InterruptedException { 
    10.   run(input, output, alpha0); 
    11.   return 0; 
    12. }  
    13. public void run(Path input, Path output, double alpha0) 
    14.  throws IOException, ClassNotFoundException, InterruptedException {  
    15.  ClusterDriver.run(directoryInput, output, alpha0);  
    16. } 
    17. } 

我可以低估这段代码的调用顺序,如下所示。

起初,他在第5行的方法被调用。由于其特定的参数设置,3个参数,编译器自动使用第13行中定义的run方法。(如果我们只有第5行中有一个参数,那么编译器将使用第9行中定义的run方法代替

在第9行中定义的run方法,它会调用在第10行,基本上是在13行

定义的run方法run方法是我的理解是否正确?

+1

这是关于方法*重载*,而不是*覆盖*。是的,你的理解是正确的。 – mre

+1

你似乎并不困惑,听起来对我来说很合适。也许你缺乏信心。 ;) –

回答

0

您的基本分析是正确的。

(只是为了澄清,其他人提出的观点:超载是当方法具有相同的名称,但不同的签名,而首要是当一个方法具有相同的名称和参数类型为超类的方法)

为了将来的参考,您应该知道在Java中的方法解析(名称+参数 - >方法选择)在重载方法的情况下实际上可能很难理解。使用的确切行为在Java Language Spec (JLS), section 15.12写上去,并涉及几个细微之处一般:

  • 重载方法分辨率为进行编译时,不能在运行时。 (方法中选择覆盖相同签名是在运行时完成的基础上,最具体的子类的方法)。如果编译器知道的参数是Foo实例(例如它的类是FooFoo子类)那么它将使用Foo作为参数的类,而不是它的“真实”类。

  • 决定使用哪种方法的问题包括:

    • 的方法是否是可变参数与否(具有...作为最后一个参数例如foo(Object a, String... b)
    • 的方法的是否声明的参数是原始类型或包裹元例如float VS Float
    • 一个方法的声明是否论据是不是另一个“更具体”(子类是比他们更超具体)

这是复杂的,但你有基本的了解。

2

是的,这是正确的,但这是方法超载,而不是覆盖。

在此类中定义了两个run方法,在第9和13行中使用不同数量的参数。因此,方法run过载。 (重写发生,如果虚拟基类方法是在子类重新定义 - 它显然与第9行所定义,如证明通过其注释的方法发生,但这个起着在这个特定的问题没有作用。)

而有两个调用run(在第5行和第10行),这两个调用都决定用3个参数调用该方法(在第13行定义)。

+0

+1,简洁和正确。 – mre

0

只有最后的运行方法定义的问题。

另一运行方法(这需要String[])调用此方法,因此它的作用就像某种“代理”,而其他run调用在main方法可以选择调用二者中的任何 - 要么'代理'运行方法(其中需要String[] args)或最后的运行方法,它实际上是“运行”。

0

你已经得到了最正确的事情,但很少发言我要纠正是:

if we only have one parameter in line 5, then compiler will use the run method defined in line 9 instead. 

这是不完全正确的,第9行的方法接受String[]类型的参数,你将需要传递一个数组来调用这个方法。

For the run method defined in line 9, it will call run method at line 10, which essentially is the run method defined at line 13. 

在第10行中,您将得到语法错误,因为input, output, alpha0在该方法中未定义。您需要通过String[] args参数并将其转换为input, output, alpha0参数,以调用run的其他实施。