类型参数extends和方法参数不匹配错误

时间:2014-04-03 10:41:34

标签: java generics

我创建了如下内容:

ConcreteObserver1是IObserver的子类

接口定义:

public interface ISubject<T,O extends IObserver<T>> {

    public void addObserver(O observer);

    public void removeObserver(O observer);

    public void updateAllSubjects(T value);

}


 public interface IObserver<T> {

    public void update(T value);

}

public class ConcreteObserver1<T> implements IObserver<T> {

包含IObserver的具体主题类

public class ConcreteSubject<T, O extends IObserver<T>> implements
        ISubject<T,O> {

    public ConcreteSubject() {
        addObserver(new ConcreteObserver1<T>());
    }

    ConcurrentSkipListSet<O> observersList = new ConcurrentSkipListSet<O>();

    public void addObserver(O observer) {
        observersList.add(observer);

addObserver(new ConcreteObserver1<T>());无效。

抱怨如下

ConcreteSubject类型中的方法addObserver(O)不适用于参数(ConcreteObserver1)

为什么?

我在O extends IObserver<T>类型参数定义中告诉ConcreteSubject,其中说O是IObserver的子类型,即ConcreteObserver1

为什么抱怨。

1 个答案:

答案 0 :(得分:1)

类型参数O被定义为IObserver<T>的子类型,这是正确的。但它可能代表任何子类型。你没有说它代表ConcreteObserver1的任何地方。它也可以代表ConcreteObserver42或其他东西。

根据您目前发布的内容,您似乎不必将O定义为ConcreteSubject的类型参数。您可以明确地说ConcreteSubject始终使用ConcreteObserver1。如果情况并非如此,您应该更清楚地解释您的意图(并且可能以更易读的形式)。

(根据评论编辑)

interface ISubject<T,O extends IObserver<T>> 
{
    void addObserver(O observer);
    void removeObserver(O observer);
    void updateAllSubjects(T value);

}
interface IObserver<T> 
{
    void update(T value);
}

class ConcreteObserver1<T> implements IObserver<T> 
{
    @Override
    public void update(T value) {}
}
class ConcreteObserver2<T> implements IObserver<T>
{
    @Override
    public void update(T value) {}
}
class ConcreteObserver3<T> implements IObserver<T>
{
    @Override
    public void update(T value) {}
}


class ConcreteSubject<T> implements ISubject<T,IObserver<T>>
{
    ConcurrentSkipListSet<IObserver<T>> observersList =
        new ConcurrentSkipListSet<IObserver<T>>();

    public ConcreteSubject()
    {
        addObserver(new ConcreteObserver1<T>());
        addObserver(new ConcreteObserver2<T>());
        addObserver(new ConcreteObserver3<T>());
    }

    @Override
    public void addObserver(IObserver<T> observer)
    {
        observersList.add(observer);
    }

    @Override
    public void removeObserver(IObserver<T> observer)
    {
        observersList.remove(observer);
    }

    @Override
    public void updateAllSubjects(T value)
    {
        for (IObserver<T> observer : observersList)
        {
            observer.update(value);
        }
    }
}