This is the mail archive of the
libstdc++@gcc.gnu.org
mailing list for the libstdc++ project.
[PATCH] _M_replace clean up (take 2)
- From: Paolo Carlini <pcarlini at unitus dot it>
- To: libstdc++ at gcc dot gnu dot org
- Date: Sun, 09 Dec 2001 03:36:23 +0100
- Subject: [PATCH] _M_replace clean up (take 2)
Hi,
privately, Nathan Myers pointed out a serious defect of my previous patch: when
true input-iterators are involved, distance cannot be used. Also, contrary to my
expectations, this case may *really* happen (not in the current testsuite ;)
Therefore, an unified _M_replace(input_iterator_tag) may avoid a double
redundant buffering (inside _M_replace(input_iterator_tag), and then, again,
inside _M_replace(forward_iterator_tag)) but has to be sligthly different from
the current _M_replace(forward_iterator_tag), which uses distance.
This is only a first *preparatory* step toward a really efficient solution,
which should be able to detect when buffering is not needed at all
(http://gcc.gnu.org/ml/libstdc++/2001-12/msg00142.html)
Tested i686-pc-linux-gnu.
Cheers,
Paolo.
//////////////
2001-12-09 Paolo Carlini <pcarlini@unitus.it>
Nathan Myers <ncm@cantrip.org>
* include/bits/basic_string.tcc (_M_replace(input_iterator_tag)):
Remove.
* include/bits/basic_string.h (_M_replace(forward_iterator_tag)):
Adjust signature to input_iterator_tag and avoid using distance.
* src/string-inst.cc: Adjust declarations.
diff -prN libstdc++-v3-orig/include/bits/basic_string.h
libstdc++-v3/include/bits/basic_string.h
*** libstdc++-v3-orig/include/bits/basic_string.h Sat Dec 8 17:57:02 2001
--- libstdc++-v3/include/bits/basic_string.h Sat Dec 8 18:29:10 2001
*************** namespace std
*** 639,649 ****
_M_replace(iterator __i1, iterator __i2, _InputIterator __k1,
_InputIterator __k2, input_iterator_tag);
- template<class _FwdIterator>
- basic_string&
- _M_replace(iterator __i1, iterator __i2, _FwdIterator __k1,
- _FwdIterator __k2, forward_iterator_tag);
-
// _S_construct_aux is used to implement the 21.3.1 para 15 which
// requires special behaviour if _InIter is an integral type
template<class _InIter>
--- 639,644 ----
diff -prN libstdc++-v3-orig/include/bits/basic_string.tcc
libstdc++-v3/include/bits/basic_string.tcc
*** libstdc++-v3-orig/include/bits/basic_string.tcc Sat Dec 8 17:56:54 2001
--- libstdc++-v3/include/bits/basic_string.tcc Sun Dec 9 03:14:16 2001
*************** namespace std
*** 497,523 ****
_M_replace(iterator __i1, iterator __i2, _InputIter __k1,
_InputIter __k2, input_iterator_tag)
{
- basic_string __s(__k1, __k2);
- return this->replace(__i1, __i2, __s._M_ibegin(), __s._M_iend());
- }
-
- template<typename _CharT, typename _Traits, typename _Alloc>
- template<typename _ForwardIter>
- basic_string<_CharT, _Traits, _Alloc>&
- basic_string<_CharT, _Traits, _Alloc>::
- _M_replace(iterator __i1, iterator __i2, _ForwardIter __k1,
- _ForwardIter __k2, forward_iterator_tag)
- {
- size_type __dnew = static_cast<size_type>(distance(__k1, __k2));
size_type __dold = __i2 - __i1;
- size_type __dmax = this->max_size();
-
- if (__dmax <= __dnew)
- __throw_length_error("basic_string::_M_replace");
size_type __off = __i1 - _M_ibegin();
// Save concerned source string data in a temporary.
basic_string __temp(__k1, __k2);
_M_mutate(__off, __dold, __dnew);
// Invalidated __i1, __i2 (and clobbered original source string
--- 497,508 ----
_M_replace(iterator __i1, iterator __i2, _InputIter __k1,
_InputIter __k2, input_iterator_tag)
{
size_type __dold = __i2 - __i1;
size_type __off = __i1 - _M_ibegin();
// Save concerned source string data in a temporary.
basic_string __temp(__k1, __k2);
+ size_type __dnew = __temp.size();
_M_mutate(__off, __dold, __dnew);
// Invalidated __i1, __i2 (and clobbered original source string
diff -prN libstdc++-v3-orig/src/string-inst.cc libstdc++-v3/src/string-inst.cc
*** libstdc++-v3-orig/src/string-inst.cc Sat Dec 8 18:42:47 2001
--- libstdc++-v3/src/string-inst.cc Sat Dec 8 18:43:18 2001
*************** namespace std
*** 71,91 ****
template
S&
S::_M_replace(S::iterator, S::iterator, S::iterator, S::iterator,
! forward_iterator_tag);
template
S&
S::_M_replace(S::iterator, S::iterator, S::const_iterator,
! S::const_iterator, forward_iterator_tag);
template
S&
! S::_M_replace(S::iterator, S::iterator, C*, C*, forward_iterator_tag);
template
S&
S::_M_replace(S::iterator, S::iterator, const C*, const C*,
! forward_iterator_tag);
template
C*
--- 71,91 ----
template
S&
S::_M_replace(S::iterator, S::iterator, S::iterator, S::iterator,
! input_iterator_tag);
template
S&
S::_M_replace(S::iterator, S::iterator, S::const_iterator,
! S::const_iterator, input_iterator_tag);
template
S&
! S::_M_replace(S::iterator, S::iterator, C*, C*, input_iterator_tag);
template
S&
S::_M_replace(S::iterator, S::iterator, const C*, const C*,
! input_iterator_tag);
template
C*