Java 我可以在抽象类中创建一个方法来构造实例化类的实例吗?

Java 我可以在抽象类中创建一个方法来构造实例化类的实例吗?,java,constructor,abstract-class,Java,Constructor,Abstract Class,我有两个扩展抽象模型的类。这两个类都实现了一个名为instance()的方法,以基本上确保在任何时候只有一个类的实例。instance()的结构对于这两个类都是完全相同的,所以我认为最好将其升级到抽象类。但是,该方法调用实例化类的默认构造函数。是否可以从抽象类调用此构造函数?如果是,怎么做?还有什么其他方法可以推广这种方法 简化示例类 我有一个模型的抽象类 public abstract class Models{ public List<Model> models = ne

我有两个扩展抽象模型的类。这两个类都实现了一个名为instance()的方法,以基本上确保在任何时候只有一个类的实例。instance()的结构对于这两个类都是完全相同的,所以我认为最好将其升级到抽象类。但是,该方法调用实例化类的默认构造函数。是否可以从抽象类调用此构造函数?如果是,怎么做?还有什么其他方法可以推广这种方法

简化示例类 我有一个模型的抽象类

public abstract class Models{
    public List<Model> models = new ArrayList<Model>();

    /** load the different models, with the models with pre-trained model*/
    public abstract void load();
}
尝试性方法 我尝试过使用工厂方法模式,但这不起作用,因为实例是静态方法,而抽象工厂方法不能从静态方法调用

无法对非静态方法makeModels()进行静态引用 从类型模型


是的,但您可能希望将其提取到一个单独的类中。

由于父类的静态性质和类型擦除问题,我认为您无法将所有实例化逻辑移动到父类中,但您确实可以组织代码以使其可重用。我为您编写了一个简单的复制/粘贴示例,只对您的设计做了一点修改,重点放在实例化部分,因此我省略了一些属性和日志代码:

接口

public interface Models {
    void load();
}
public class TestDrive {

    @Test
    public void testEquality() {

        HeroModels a1 = HeroModels.instance();
        HeroModels a2 = HeroModels.instance();

        Assert.assertEquals(a1, a2);

        System.out.println("a1: " + a1);
        System.out.println("a2: " + a2);
    }
}
抽象实现

public abstract class BaseModels implements Models {

    protected static <T extends Models> T instance(Class<T> type, T candidate) {
        if (candidate == null) {
            try {
                candidate = type.newInstance();
                candidate.load();
            } catch (InstantiationException | IllegalAccessException e) {
                e.printStackTrace();
            }
        }
        return candidate;
    }
}
public class HeroModels extends BaseModels {

    static HeroModels instance;

    public static HeroModels instance() {
        instance = instance(HeroModels.class, instance);
        return instance;
    }

    @Override
    public void load() {
        System.out.println("Loading HeroModels...");
    }
}
一个简单的测试用例

public interface Models {
    void load();
}
public class TestDrive {

    @Test
    public void testEquality() {

        HeroModels a1 = HeroModels.instance();
        HeroModels a2 = HeroModels.instance();

        Assert.assertEquals(a1, a2);

        System.out.println("a1: " + a1);
        System.out.println("a2: " + a2);
    }
}
测试用例输出

正在加载模型。。。
a1:HeroModels@736e9adb 
a2:HeroModels@736e9adb


从输出中可以看到,
HeroModels
类只加载了一次。
BaseModel
类中的
instance(…)
方法被设置为受保护的,以明确它是供孩子们使用的,孩子们可能有他们自己的静态实例属性。

你能补充一点说明吗?对于你最初的答案,我可以用谷歌搜索“工厂模式”。但是在这里,我没有太多的内容来探讨您的建议,您不能在抽象类中创建静态方法。在您的案例中使用Factory或Builder类可能会有所帮助。作为旁注,要创建不同步的单例,可以使用Holder模式。