5

根据(优秀)问题C++ OutputIterator post-increment requirements,我们观察到对于 type 的可取消引用和可递增值r以及适当类型的OutputIteratorX,表达式o

*r++ = o;

是有效的并且具有等效的语义

X a(r);
++r;
*a = o;

但是,如果在中间期间多次增加,是否仍然a是可取消引用分配的情况?r也就是说,这段代码有效吗?

X a(r);
++r;
++r;
*a = o;

很难看出对一个值的操作如何影响对另一个值的操作的有效性,但例如InputIterator(24.2.3) 在后置条件下具有++r

之前的值的任何副本r不再需要是可解引用的或在 的域中==

相关部分:24.2.2 迭代器24.2.4 输出迭代器17.6.3.1 模板参数要求

此外,如果这不需要有效,是否存在利用其无效性有助于实现OutputIterator类型(效率、简单性)同时仍遵守现有要求的任何情况?

4

1 回答 1

2

这个问题在 2004 年作为缺陷 485提出, n3066中的措辞澄清了这个问题,要求输出迭代器只需要支持一系列交替递增和取消引用/分配。因此,在您的示例中,r在 first 之后不需要是可递增的++r,除非有中间的取消引用/赋值。SGI 的STL也需要这种行为(见脚注 3)。正如你上面提到的,n3225 出现时没有 n3066 的修复,所以缺陷 2035被提出;但遗憾的是,该修复程序没有进入 C++11 的已发布版本(ISO/IEC 14882:2011)。

此外,缺陷 2035 表示a(from X a(r++);) 不能像 一样使用*a = 0

“在此操作之后 [即++r]r不需要是可递增的,并且之前的值的任何副本r都不再需要是可取消引用或可递增的。”

在某些情况下,这可能有助于实现(就简单性而言):参见例如this question on ostream_iterator,其中此类(无效)双增量被忽略,简单地返回*this;只有取消引用/赋值会导致ostream_iterator实际增加。

于 2012-08-13T17:06:47.827 回答