// TEMPLATE CLASS istream_iterator
template<class _Ty,
class _Elem = char,
class _Traits = char_traits<_Elem>,
class _Diff = ptrdiff_t>
class istream_iterator
: public iterator<input_iterator_tag, _Ty, _Diff,
const _Ty *, const _Ty&>
{ // wrap _Ty extracts from input stream as input iterator
typedef istream_iterator<_Ty, _Elem, _Traits, _Diff> _Myt;
public:
typedef _Elem char_type;
typedef _Traits traits_type;
typedef basic_istream<_Elem, _Traits> istream_type;
#if _SECURE_SCL
typedef _Range_checked_iterator_tag _Checked_iterator_category;
#endif
istream_iterator()
: _Myistr(0)
{ // construct singular iterator
}
istream_iterator(istream_type& _Istr)
: _Myistr(&_Istr)
{ // construct with input stream
_Getval();
}
const _Ty& operator*() const
{ // return designated value
#if _HAS_ITERATOR_DEBUGGING
if (_Myistr == 0)
{
_DEBUG_ERROR("istream_iterator is not dereferencable");
_SCL_SECURE_OUT_OF_RANGE;
}
#else
_SCL_SECURE_VALIDATE_RANGE(_Myistr != 0);
#endif /* _HAS_ITERATOR_DEBUGGING */
return (_Myval);
}
const _Ty *operator->() const
{ // return pointer to class object
return (&**this);
}
_Myt& operator++()
{ // preincrement
#if _HAS_ITERATOR_DEBUGGING
if (_Myistr == 0)
{
_DEBUG_ERROR("istream_iterator is not incrementable");
_SCL_SECURE_OUT_OF_RANGE;
}
#else
_SCL_SECURE_VALIDATE_RANGE(_Myistr != 0);
#endif /* _HAS_ITERATOR_DEBUGGING */
_Getval();
return (*this);
}
_Myt operator++(int)
{ // postincrement
_Myt _Tmp = *this;
++*this;
return (_Tmp);
}
bool _Equal(const _Myt& _Right) const
{ // test for iterator equality
return (_Myistr == _Right._Myistr);
}
protected:
void _Getval()
{ // get a _Ty value if possible
if (_Myistr != 0 && !(*_Myistr >> _Myval))
_Myistr = 0;
}
static void _Xran()
{ // report an out_of_range error
_THROW(out_of_range, "invalid istream_iterator");
}
istream_type *_Myistr; // pointer to input stream
_Ty _Myval; // lookahead value (valid if _Myistr is not null)
};
// istream_iterator TEMPLATE OPERATORS
template<class _Ty,
class _Elem,
class _Traits,
class _Diff> inline
bool operator==(
const istream_iterator<_Ty, _Elem, _Traits, _Diff>& _Left,
const istream_iterator<_Ty, _Elem, _Traits, _Diff>& _Right)
{ // test for istream_iterator equality
return (_Left._Equal(_Right));
}
template<class _Ty,
class _Elem,
class _Traits,
class _Diff> inline
bool operator!=(
const istream_iterator<_Ty, _Elem, _Traits, _Diff>& _Left,
const istream_iterator<_Ty, _Elem, _Traits, _Diff>& _Right)
{ // test for istream_iterator inequality
return (!(_Left == _Right));
}
红色部分就是重点了,其实这种迭代器不能自增,只是不断把流中的元素放到自己所存的值里,当到达流末尾时,直接将判断指针设为0。