代码之家  ›  专栏  ›  技术社区  ›  Yardena

Java-本地类和泛型,为什么编译器警告?

  •  5
  • Yardena  · 技术社区  · 17 年前

    local classes 很少使用,通常本地类是匿名的。有人知道为什么下面的代码会生成编译器警告吗?

    public class Stuff<E> {
      Iterator<E> foo() {
        class InIterator implements Iterator<E> {
          @Override public boolean hasNext() { return false; }
          @Override public E next() { return null; }
          @Override public void remove() { }
        }
        return new InIterator();
      }
    }
    

    警告已经发出 new InIterator()

    [unchecked] unchecked conversion
    found   : InIterator
    required: java.util.Iterator<E>
    

    如果未更改的类被设置为匿名,或者如果它被设置为成员,则警告将消失。但是,作为命名的局部类,它需要声明 class InIterator<E> implements ... 让警告消失。

    发生什么事?

    4 回复  |  直到 17 年前
        1
  •  3
  •   David Berger    17 年前

    我相信现在的情况是,您通过命名忽略了泛型类型参数 InIterator

    这属于愚蠢的编译器警告的范畴:您已经编写了100%的类 起动器 Iterator<E> ,但编译器无法识别它。(我想这取决于编译器。我在Eclipse编译器中没有看到警告,但我知道Eclipse编译器处理泛型的方式与JDK编译器略有不同。)

    public class Stuff<E> {
      Iterator<E> foo() {
        class InIterator<F> implements Iterator<F> {
          @Override public boolean hasNext() { return false; }
          @Override public E next() { return null; }
          @Override public void remove() { }
        }
        return new InIterator<E>();
      }
    }
    
        2
  •  1
  •   itsadok    17 年前

    嗯,这里没有警告。

    import java.util.Iterator;
    
    public class Stuff<E> {
        Iterator<E> foo() {
            class InIterator implements Iterator<E> {
                public boolean hasNext() {
                    return false;
                }
    
                public E next() {
                    return null;
                }
    
                public void remove() {
                }
            }
            return new InIterator();
        }
    
        public static void main(String[] args) {
            Iterator<String> i = new Stuff<String>().foo();
        }
    }
    
        3
  •  1
  •   Yardena    17 年前

    我现在确信这是一个javac错误。上面的解决方案向InIterator添加了一个泛型参数,该参数隐藏或替换了E,这是没有帮助的,因为它们阻止了迭代器做一些有用的事情,比如返回类型为E-Stuff的E的元素。

    public class Stuff<E> {
      E bar;
      Iterator<E> foo() {
        class InIterator<Z> implements Iterator<E> {
          @Override public boolean hasNext() { return false; }
          @Override public E next() { return bar;  }
          @Override public void remove() { }
        }
        return new InIterator<Void>();
      }
    }
    

    肯定是个虫子。

        4
  •  1
  •   newacct    17 年前

    是的,我也同意这应该是一个bug。如果将本地类从方法中“提升”到成员类中,它也可以正常工作。除了不同的作用域和对局部变量的访问之外,两者之间没有太大区别。

    public class Stuff<E> {
      class InIterator implements Iterator<E> {
        @Override public boolean hasNext() { return false; }
        @Override public E next() { return null; }
        @Override public void remove() { }
      }
      Iterator<E> foo() {
        return new InIterator();
      }
    }