ArrayList方法中的参数不一致

时间:2013-01-23 16:37:45

标签: java

在ArrayList API中 add()采用泛型参数类型的参数,但包含() indexOf()采用类型参数的对象

public class ArrayList<E> ...{
     public boolean add(E e);  
     public boolean contains(Object o);
     public int indexOf(Object o);
     ....
}

Java Doc for ArrayList

所以我只是想知道它是否与Generics有关或者它的设计是否一致?

我查看了 Openjdk 的实现,但未找到任何具体原因。

2 个答案:

答案 0 :(得分:10)

API所说的是:

  1. 您不能add()任何非E;
  2. 的内容
  3. 但是,您可以搜索非E的内容(但可以比较E的实例)。
  4. 考虑以下示例:

    public class Main {
        public static class Key {
            private final int k;
            public Key(int k) {
                this.k = k;
            }
            @Override
            public boolean equals(Object obj) {
                if (!(obj instanceof Key)) {
                    return false;
                }
                Key rhs = (Key)obj;
                return k == rhs.k;
            }
            @Override
            public int hashCode() {
                //...
                return 0;
            }
        }
        public static class Data extends Key {
            private final int d;
            public Data(int k, int d) {
                super(k);
                this.d = d;
            }
        }
        public static void main(String[] args) {
            List<Data> l = new ArrayList<Data>();
            l.add(new Data(123, 456));
            l.add(new Data(42, 24));
            System.out.println(l.contains(new Key(789)));
            System.out.println(l.contains(new Key(123)));
            System.out.println(l.contains(new Key(42)));
        }
    }
    

    如果contains()仅限于Data,则最后三行不会编译。

答案 1 :(得分:3)

以下是一个很好的解释:Why does Set.contains() take an Object, and not E?