简体   繁体   English

通过在子类型上返回迭代器来实现Iterable

[英]Implementing Iterable by returning an Iterator over a sub-type

In the following code: 在以下代码中:

public class Bar { ... }

public class Foo extends Bar { ... }

public class BarIterable implements Iterable<Bar> {

    List<Foo> foos = ...

    @Override
    public Iterator<Bar> iterator() {
        return foos.iterator();  // Error: Type mismatch ...
    }
}

I get an error at the indicated position since foos.iterator() returns an Iterable<Foo> rather than an Iterable<Bar> . 我在指定的位置出现错误,因为foos.iterator()返回Iterable<Foo>而不是Iterable<Bar> Unfortunately, a simple cast won't work: 不幸的是,简单的演员表不起作用:

return (Iterator<Bar>) foos.iterator();  // Error: Cannot cast ...

Java also doesn't allow me to change the definition of BarIterable to Java也不允许我将BarIterable的定义BarIterable

public class BarIterable implements Iterable<? extends Bar> { ...   // Error: A supertype may not specify any wildcard

What's a good way to resolve this problem that does not involve implementing Iterable<Foo> instead (the Iterable-implementation comes from another interface that doesn't know about Foo)? 解决这个问题的好方法是什么, 而不涉及实现Iterable<Foo> (Iterable-implementation来自另一个不了解Foo的接口)?

Do I have to write myself a wrapper Iterator-class that "unpacks" each value? 我是否必须自己编写一个“解包”每个值的包装器迭代器类?

Since Foo is a subtype of Bar , you could just cast the List . 由于FooBar的子类型,因此您可以直接转换List

return ((List<Bar>)(List<? extends Bar>) foos).iterator(); 

and suppress the warnings. 并压制警告。

Edit by Markus A.: 由马库斯编辑:

Or, you can cast the iterator directly using the intermediate-cast-trick: 或者,您可以使用middle-cast-trick直接强制转换迭代器:

return (Iterator<Bar>)(Iterator<? extends Bar>) foos.iterator();

End edit 结束编辑


With Java 8, you can stream over the elements and construct a new List of type Bar . 使用Java 8,您可以流式传输元素并构造一个新的Bar类型List

@Override
public Iterator<Bar> iterator() {
    return foos.stream().<Bar>map((foo) -> foo /* considered a Bar */).collect(Collectors.toList()).iterator();  
}

but you're doing a lot of intermediate operations just to view the List from a super type's point of view. 但是你要做的很多中间操作只是为了从超类型的角度来看List

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM