gpt4 book ai didi

java - 如何实现一个可迭代的类并公开一个真正不可变的 API?

转载 作者:行者123 更新时间:2023-12-01 08:15:21 26 4
gpt4 key购买 nike

我想在Java中实现一个可迭代的不可变类。我按照以下方式进行:

public final class MyIterable implements Iterable<Integer> {

private final Collection<Integer> items;

public MyIterable(Collection<Integer> items) {
this.items = Collections.unmodifiableCollection(new LinkedList<Integer>(items));
}

@Override
public Iterator<Integer> iterator() {
return items.iterator();
}
}

这一切都很好,我无法改变我的实例中的任何内容。然而,我的类仍然公开了一个 API,表明可以通过迭代器上的 remove() 方法修改其内部结构:

MyIterable myIterable = new MyIterable(Arrays.asList(1, 2, 3));
for (Iterator<Integer> it = myIterable.iterator(); it.hasNext();) {
it.remove(); // I do not want to expose this even
// though I know it will throw an error at runtime.
it.next();
}

是否有某种方法可以避免公开此删除方法,从而让我的类公开真正不可变的 API?理想的情况是实现类似 ReadOnlyIterable 的东西,但类似的东西在 Java 中似乎不可用。

最佳答案

它似乎通过其方法签名来表明这一点,但这些方法被专门记录为“不,我们不提供这些行为!”

为了实现这一点,您还必须记录您遵循与 UnmodifyingList 相同的行为。

开发人员有责任了解他们使用的库的用途库创建者有责任制作该信息可用

底线是,Iterable 已融入到语言中(for(a:b) 循环),而您可以创建自己的接口(interface) ReadOnlyIterable 它根本不会那么健壮。

这种方法的问题是牺牲了编译时完整性。换句话说,有人可以编译使用 remove() 方法的代码,直到运行时他们才会发现它不起作用。这意味着,如果它们碰巧没有正确测试,您将不会发现该方法不应该使用,直到投入生产。

您也许可以使用注释和警告来缓解这种情况 - 如果他们听取警告,或者使用告诉他们警告的 IDE,他们会更早发现。但是您不能依赖用户做正确的事情。这就是为什么你必须抛出异常而不是什么也不做。

关于java - 如何实现一个可迭代的类并公开一个真正不可变的 API?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13843777/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com