遵循Java - Inherited Fluent method return type to return incident class' type, not parent's中描述的解决方案。我想将它扩展到多个层次。
解决方案显然在一个层面上工作。这是编译和可运行的代码(无依赖关系):
public enum X {
;
static interface BaseFoo<T, S extends BaseFoo<T, S>> {
S foo();
}
static interface Foo<T> extends BaseFoo<T, Foo<T>> {
void foo1();
}
static abstract class AbstractFooBase<T, S extends BaseFoo<T, S>> implements BaseFoo<T, S> {
abstract void internalFoo();
@Override
public S foo() {
internalFoo();
return (S)this;
}
}
static class FooImpl<T> extends AbstractFooBase<T, Foo<T>> implements Foo<T> {
@Override
void internalFoo() {
System.out.println("inside FooImpl::internalFoo()");
}
@Override
public void foo1() {
System.out.println("inside FooImpl::foo1()");
}
}
public static void main(String[] args) {
Foo<String> foo = new FooImpl<String>();
foo.foo().foo1();
}
}
但是,当我在对象继承层次结构中添加新级别时,事情变得越来越困难。下面的代码不会编译:
public enum X {
;
static interface BaseFoo<T, S extends BaseFoo<T, S>> {
S foo();
}
static interface Foo<T> extends BaseFoo<T, Foo<T>> {
void foo1();
}
static interface BaseBar<T, S extends BaseBar<T, S>> extends BaseFoo<T, S> {
S bar();
}
static interface Bar<T> extends BaseBar<T, Bar<T>> {
void bar1();
}
static abstract class AbstractFooBase<T, S extends BaseFoo<T, S>> implements BaseFoo<T, S> {
abstract void internalFoo();
@Override
public S foo() {
internalFoo();
return (S)this;
}
}
static class FooImpl<T> extends AbstractFooBase<T, Foo<T>> implements Foo<T> {
@Override
void internalFoo() {
System.out.println("inside FooImpl::internalFoo()");
}
@Override
public void foo1() {
System.out.println("inside FooImpl::foo1()");
}
}
static abstract class AbstractBarBase<T, S extends BaseBar<T, S>> extends FooImpl<T> implements BaseBar<T, S> {
abstract void internalBar();
@Override
public S bar() {
internalBar();
return (S)this;
}
}
static class BarImpl<T> extends AbstractBarBase<T, Bar<T>> implements Bar<T> {
@Override
void internalBar() {
System.out.println("inside BarImpl::internalBar()");
}
@Override
public void bar1() {
System.out.println("inside BarImpl::bar1()");
}
}
public static void main(String[] args) {
Foo<String> foo = new FooImpl<String>();
foo.foo().foo1();
Bar<Boolean> bar = new BarImpl<Boolean>();
bar.foo().bar1();
}
}
编译时错误消息是:
X.java:40: X.BaseFoo cannot be inherited with different arguments: <T,S> and <T,X.Foo<T>>
static abstract class AbstractBarBase<T, S extends BaseBar<T, S>> extends FooImpl<T> implements BaseBar<T, S> {
^
X.java:49: X.BaseFoo cannot be inherited with different arguments: <T,X.Bar<T>> and <T,X.Foo<T>>
static class BarImpl<T> extends AbstractBarBase<T, Bar<T>> implements Bar<T> {
^
Note: X.java uses unchecked or unsafe operations.
Note: Recompile with -Xlint:unchecked for details.
2 errors
任何想法如何解决它?
答案 0 :(得分:1)
这是您的继承层次结构:
如您所见,其中一些类型多次继承相同的接口类型。实际上,BarImpl
实现了BaseFoo
四次,并且一些继承链为其类型参数S
提供了不同的参数。可以说BarImpl
实现了以下内容:
BaseFoo<T, Foo<T>>
(通过Foo
)BaseFoo<T, Foo<T>>
(通过FooImpl
)BaseFoo<T, Bar<T>>
(通过Bar
)BaseFoo<T, Bar<T>>
(通过BarImpl
)The same interface cannot be implemented with different type arguments,因此您收到编译错误。
正如我在你的后续问题上指出的那样,我的回答here讨论了如何正确地模拟“自我类型”来实现像你想要的那样的层次化流畅的构建模式。在其中,我指出需要在所有中间类型中维护变量“自我类型”(代码中为S
) - 仅使用被理解为{{1}的“叶类”来解析它}。您的代码违反了该规则,因为中间类型final
,Foo
和Bar
过早地解析了FooImpl
。
以下解决方案可解决此问题:
S
我的更改如下:
static interface BaseFoo<T, S extends BaseFoo<T, S>> {
S foo();
}
static interface Foo<T, S extends Foo<T, S>> extends BaseFoo<T, S> {
void foo1();
}
static interface BaseBar<T, S extends BaseBar<T, S>> extends BaseFoo<T, S> {
S bar();
}
static interface Bar<T, S extends Bar<T, S>> extends BaseBar<T, S> {
void bar1();
}
static abstract class AbstractFooBase<T, S extends BaseFoo<T, S>> implements BaseFoo<T, S> {
abstract void internalFoo();
@Override
public S foo() {
internalFoo();
return (S)this;
}
}
static abstract class AbstractIntermediateFoo<T, S extends AbstractIntermediateFoo<T, S>> extends AbstractFooBase<T, S> implements Foo<T, S> {
@Override
void internalFoo() {
System.out.println("inside FooImpl::internalFoo()");
}
@Override
public void foo1() {
System.out.println("inside FooImpl::foo1()");
}
}
static final class FooImpl<T> extends AbstractIntermediateFoo<T, FooImpl<T>> { }
static abstract class AbstractBarBase<T, S extends AbstractBarBase<T, S>> extends AbstractIntermediateFoo<T, S> implements BaseBar<T, S> {
abstract void internalBar();
@Override
public S bar() {
internalBar();
return (S)this;
}
}
static final class BarImpl<T> extends AbstractBarBase<T, BarImpl<T>> implements Bar<T, BarImpl<T>> {
@Override
void internalBar() {
System.out.println("inside BarImpl::internalBar()");
}
@Override
public void bar1() {
System.out.println("inside BarImpl::bar1()");
}
}
public static void main(String[] args) {
FooImpl<String> foo = new FooImpl<String>();
foo.foo().foo1();
BarImpl<Boolean> bar = new BarImpl<Boolean>();
bar.foo().bar1();
}
S
Foo
S
Bar
拆分为以下内容:
FooImpl
,AbstractIntermediateFoo
,维护abstract
,并实施S
和internalFoo
。foo1
,具体,FooImpl
,并解析final
。S
BarImpl
。final
中,将main
和foo
声明为bar
和FooImpl
- 此处的编码不可行。