0

次の抽象クラスがあるとします。

public abstract class BaseVersionResponse<T extends BaseVO> {

    public abstract void populate(T versionVO);

}

および次の子クラス:

public class VersionResponseV1 extends BaseVersionResponse<VersionVOV1>
{
    protected String testFieldOne;
    protected String testFieldTwo;

    public String getTestFieldOne() {
        return testFieldOne;
    }  
    public void setTestFieldOne(String value) {
        this.testFieldOne = value;
    }
    public String getTestFieldTwo() {
        return testFieldTwo;
    }  
    public void setTestFieldTwo(String value) {
        this.testFieldTwo = value;
    }

    @Override
    public void populate(VersionVOV1 versionVO) {

        this.setTestFieldOne(versionVO.getFieldOne());
        this.setTestFieldTwo(versionVO.getFieldTwo());
}

私は呼び出し元のメソッドからこのようなことをしたいと思っています:

public void getVersionInfo(String version) {

    BaseVO versionVO = null;
    BaseVersionResponse<? extends BaseVO> baseVersionResponse = null;

    baseVersionResponse = createVersionResponse(version);

    versionVO = createVersionVO(version);

    baseVersionResponse.populate(versionVO);

}

どこで、次のようにcreateVersionResponse(...)なりcreateVersionVO(...)ます。

public BaseVersionResponse<? extends BaseVO> createVersionResponse(String version) {

    BaseVersionResponse<? extends BaseVO> specificVersionResponse = null;

    if (version.equalsIgnoreCase("V1")) {

        specificVersionResponse = new VersionResponseV1();

    } else if (version.equalsIgnoreCase("V2"))

        specificVersionResponse = new VersionResponseV2();

    return specificVersionResponse;
}

public BaseVO createVersionVO(String version) {

    BaseVO versionVO = null;

    if (version.equalsIgnoreCase("V1")) {

        versionVO = new VersionVOV1();

    } else if (version.equalsIgnoreCase("V2"))

        versionVO = new VersionVOV2();

    return versionVO;
}

VersionVOV1 は次のようになります。

public class VersionVOV1 extends BaseVO {

    private String fieldOne = null;
    private String fieldTwo = null;
    private String fieldThree = null;

    public String getFieldOne() {
        return fieldOne;
    }
    public void setFieldOne(String fieldOne) {
        this.fieldOne = fieldOne;
    }
    public String getFieldTwo() {
        return fieldTwo;
    }
    public void setFieldTwo(String fieldTwo) {
        this.fieldTwo = fieldTwo;
    }
    public String getFieldThree() {
        return fieldThree;
    }
    public void setFieldThree(String fieldThree) {
        this.fieldThree = fieldThree;
    }

}

このコード行をコンパイルしようとすると、私の問題が発生します。

baseVersionResponse.populate(versionVO);

getVersionInfo(...)。次のようなメッセージが表示されます。

タイプ BaseVersionResponse のメソッド populate(capture#3-of ?) は、引数 (BaseVO) には適用されません。

上記のpopulate方法で。

コードのこの時点では、 baseVersionResponse は実際には特定の子インスタンスであるため、クラスはその特定の子クラスからどの populate メソッドを呼び出すかを正確に認識しているというのが私の考えでした (これは明らかに正しくありません)。

ここで何が間違っていますか?これが正しいアプローチでない場合、これを行うためのより良い方法はありますか?

お時間をいただきありがとうございます!

4

2 に答える 2

1

タイプのキャプチャ (「<?>」) を取り出して、チェックを外したままにしておくと、問題なく動作するはずです。タイプ Object を使用してもコンパイルされます。

しかし、あなたの特定の例を考えると、おそらくあなたが望むのはメソッドです:

public BaseVersionResponse<?> createVersionResponse(String version)

変更:

public BaseVersionResponse<? extends BaseVO> createVersionResponse(String version)

次に、使用する代わりに

BaseVersionResponse<?>

使用する

BaseVersionResponse<? extends BaseVO>

戻り値の型は、インターフェイス/クラスを実装するものの 1 つになることがわかっているためです。

于 2015-03-19T01:15:06.070 に答える