Java 编译警告:未经检查调用 XXX 作为原始类型的成员

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/30816147/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 10:12:29  来源:igfitidea点击:

Compilation warning: Unchecked call to XXX as member of the raw type

javagenericscompiler-warningsunchecked

提问by jcollin.be

I am getting the compiler warning:

我收到编译器警告:

warning: [unchecked] unchecked call to setView(V) as a member of the raw type AbstractPresenter

   this.presenter.setView(this);

where V is a type-variable:

V extends AbstractView declared in class AbstractPresenter

警告:[unchecked] 未经检查调用 setView(V) 作为原始类型 AbstractPresenter 的成员

   this.presenter.setView(this);

其中 V 是类型变量:

V 扩展了 AbstractPresenter 类中声明的 AbstractView

The code of the AbstractPresenterclass is the following:

AbstractPresenter类的代码如下:

public abstract class AbstractPresenter<V extends AbstractView, M> 
implements Presenter<V, M> {

    private M model;
    private V view;

    @Override
    public final V getView() {
        return this.view;
    }

    public final void setView(V view) {
        if (view == null) {
            throw new NullPointerException("view cannot be null.");
        }

        if (this.view != null) {
            throw new IllegalStateException("View has already been set.");
        }
        this.view = view;
    }

    @Override
    public final M getModel() {
        return this.model;
    }

    protected final void setModel(M model) {
        if (model == null) {
            throw new NullPointerException("model cannot be null.");
        }        
        this.model = model;
    }
}

The setViewmethod is called in the AbstractViewclass below:

setView方法在AbstractView下面的类中被调用:

public abstract class AbstractView<P extends AbstractPresenter> extends 
UserControl {
    private final P presenter;

    public AbstractView(P presenter) {
        this.presenter = presenter;
        this.initialisePresenter();
    }

    private void initialisePresenter() {
        if (this.presenter == null){
            throw new IllegalStateException();
        }

        this.presenter.setView(this); //This is the call that raises the warning
    }

    protected P getPresenter() {
        return this.presenter;
    }
}

I have searched the questions from other members regarding the same warning and tried to adapt the solutions to my issue but it did not work.

我搜索了其他成员关于相同警告的问题,并尝试根据我的问题调整解决方案,但没有奏效。

I don't understand why the warning is raised as the Vtype is forced in the declaration of the AbstractPresenterclass:

我不明白为什么VAbstractPresenter类的声明中强制类型会引发警告:

public abstract class AbstractPresenter<V extends AbstractView, M> 
implements Presenter<V, M> 

It is just a warning and I could ignore it but I would like to understand why it happens and I want to get my code as clean as possible.

这只是一个警告,我可以忽略它,但我想了解它为什么会发生,我想让我的代码尽可能干净。

采纳答案by Bohemian

Your types are raw - that is, your generic types are bonded to a type that itself has a type, but you haven't provided one, so it's raw.

你的类型是原始的——也就是说,你的泛型类型绑定到一个本身有类型的类型,但你没有提供一个类型,所以它是原始的。

Change your type bounds to be typed. Try this:

更改要键入的类型边界。尝试这个:

public abstract class AbstractPresenter<V extends AbstractView<V>, M> implements Presenter<V, M>

and

public abstract class AbstractView<P extends AbstractPresenter<P> extends UserControl

回答by RealSkeptic

Your problem is with this line:

您的问题出在这一行:

public abstract class AbstractView<P extends AbstractPresenter> extends

Your Pis declared as a type that extends a rawAbstractPresenter. Basically, we don't know what the Vand Mof that type is.

P被声明为扩展raw的类型AbstractPresenter。基本上,我们不知道该类型的VandM是什么。

Therefore this.presenteris of this raw type and we don't know its Vand M. Thus when you call its setViewwith this, the compiler cannot tell whether the types are correct or not.

因此this.presenter是这种原始类型,我们不知道它的VM。因此,当您setView使用 with调用它时this,编译器无法判断类型是否正确。

The same is true for

同样适用于

public abstract class AbstractPresenter<V extends AbstractView, M> 

Vis a type that extends a rawAbstractViewand we don't know what the base type of it is. Thus the compiler cannot do the work for which generics were meant.

V是一种扩展原始类型的类型,AbstractView我们不知道它的基本类型是什么。因此,编译器无法完成泛型所指的工作。

Whenever you make such type declarations, remember to specify the types of all generic types in the declaration, and use type variables that correctly represent the relationships between them.

每当您进行此类类型声明时,请记住在声明中指定所有泛型类型的类型,并使用正确表示它们之间关系的类型变量。

回答by The-null-Pointer-

I had wanted to add a comment but could not as i dont have enough reputation.

我本来想添加评论但不能因为我没有足够的声誉。

your types are raw. the presenter in AbstractView is raw type as the generic parameters passed to Abstract View is raw

你的类型是原始的。AbstractView 中的 Presenter 是原始类型,因为传递给 AbstractView 的通用参数是原始类型