不要从超类构造函数中调用子类方法 [英] Don’t call subclass methods from a superclass constructor

查看:111
本文介绍了不要从超类构造函数中调用子类方法的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

考虑以下代码

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package example0;

/**
 *
 * @author yccheok
 */
public class Main {

    static class A {
        private final String var;

        public A() {
            var = getVar();
            // Null Pointer Exception.
            System.out.println("var string length is " + var.length());
        }

        public String getVar() {
            return "String from A";
        }
    }

    static class B extends A {
        private final String bString;

        // Before B ever constructed, A constructor will be called.
        // A is invoking a overriden getVar, which is trying to return
        // an initialized bString.
        public B() {                
            bString = "String from B";
        }

        @Override
        public String getVar() {
            return bString;
        }
    }

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        B b = new B();
    }

}

目前,在我看来,那里有两种方法可以避免这种问题。

Currently, in my mind, there are two ways to avoid such problem.

要么是A级的最后一堂课。

Either making class A final class.

static final class A {
    private final String var;

    public A() {
        var = getVar();
        // Null Pointer Exception.
        System.out.println("var string length is " + var.length());
    }

    public String getVar() {
        return "String from A";
    }
}

使getVar方法最终

Making getVar method final

static class A {
    private final String var;

    public A() {
        var = getVar();
        // Null Pointer Exception.
        System.out.println("var string length is " + var.length());
    }

    public final String getVar() {
        return "String from A";
    }
}

作者试图提出防范上述问题的方法。但是,解决方案似乎很麻烦,因为有一些规则要遵循。

The author trying to suggest ways to prevent the above problem. However, the solution seems cumbersome as there are some rules to be followed.

http://benpryor.com/blog/2008/01/02/dont-call-subclass-methods-from -a-superclass-constructor /

除了最终和作者建议的方式之外,还有更多方法可以防止上述问题(不要调用子类)来自超类构造函数的方法)发生了?

Beside making final and the author suggested way, is there more ways to prevent the above problem (Don’t call subclass methods from a superclass constructor) from happen?

推荐答案


使getVar方法最终成为

这绝对是你需要做的。

This is definitely what you need to do.

如果您正在转发初始化对象的方法的功能,则不应让子类破坏该方法。

If you're relaying on the functionality of a method to initialize an object, you shouldn't let subclasses broke that method.

回答你的问题其他方法来阻止它是让 getVar 私有 A

Answering your question, other way to prevent it is to make getVar private in A.

查看代码的简化版本:

// A.java
class A {
    private final String var;
    public A(){
        var = getVar();
        var.length();
    }
    private String getVar(){
        return "This is the value";
    }
}
class B extends A {
    private final String other;
    public B(){
        other = "Other string";
    }
    public String getVar(){
        return other;
    }
}
class Main{
    public static void main( String [] args ) {
        new B();
    }
}

BTW,你为什么把这些作为静态嵌套类,只是为了制造混乱?

BTW, why did you put those as static nested classes, just to create confusion?

这篇关于不要从超类构造函数中调用子类方法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆