简体   繁体   English

在java中,如何使用私有构造函数创建一个类,其超类也有一个私有构造函数?

[英]In java, how do I make a class with a private constructor whose superclass also has a private constructor?

As an example: 举个例子:

public class Foo {
    private Foo() {}
}

public class Bar extends Foo {
    private Bar() {}

    static public doSomething() {
    }
}

That's a compilation error right there. 那是一个编译错误。 A class needs to, at least, implicitly call its superclass's default constructor, which in this case is isn't visible in Foo . 一个类至少需要隐式调用它的超类的默认构造函数,在这种情况下,它在Foo中是不可见的。

Can I call Object 's constructor from Bar instead? 我可以从Bar调用Object的构造函数吗?

You can't. 你不能。 You need to make Foo's constructor package private at the very least (Though I'd probably just make it protected. 你需要让Foo的构造函数包至少是私有的(虽然我可能只是让它受到保护。

(Edit - Comments in this post make a good point) (编辑 - 这篇文章中的评论很有用)

This is actually a symptom of a bad form of inheritance, called implementation inheritance. 这实际上是一种糟糕的继承形式的症状,称为实现继承。 Either the original class wasn't designed to be inherited, and thus chose to use a private constructor, or that the entire API is poorly designed. 原始类不是为了继承而设计的,因此选择使用私有构造函数,或者整个API设计不当。

The fix for this isn't to figure out a way to inherit, but to see if you can compose the object instead of inheriting, and do so via interfaces. 解决这个问题的方法不是找出继承的方法,而是要确定是否可以组合对象而不是继承,并通过接口来实现。 Ie, class Foo is now interface Foo, with a FooImpl. 即,Foo类现在是Foo接口,具有FooImpl。 Then interface bar can extend Foo, with a BarImpl, which has no relation to FooImpl. 然后界面栏可以扩展Foo,使用BarImpl,它与FooImpl无关。

Inside BarImpl, you could if you wish to do some code reuse, have a FooImpl inside as a member, but that's entirely up to the implementation, and will not be exposed. 在BarImpl内部,如果你想做一些代码重用,你可以将FooImpl作为成员,但这完全取决于实现,并且不会暴露。

You won't be able to create an instance of Bar for as long as Foo has a private constructor. 只要Foo具有私有构造函数,您将无法创建Bar的实例。 The only way you would be able to do it is if Foo had a protected constructor. 你能做到的唯一方法就是Foo有一个受保护的构造函数。

You can't call Object's constructor directly from Bar while it's a subclass of Foo, it would have to through Foo's constructor, which is private in this case. 你不能直接从Bar调用Object的构造函数,而它是Foo的子类,它必须通过Foo的构造函数,在这种情况下是私有的。

When you declare Foo's constructor private, it does not create a default public constructor. 当您将Foo的构造函数声明为private时,它不会创建默认的公共构造函数。 Since Bar has to invoke Foo's constructor, it is not possible to leave it private. 由于Bar 必须调用Foo的构造函数,因此不可能将其保密。 I would suggest, as others have, on using protected instead of private. 我会像其他人一样建议使用protected而不是private。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM