You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@stdcxx.apache.org by an...@apache.org on 2006/06/08 15:41:04 UTC
svn commit: r412750 - in /incubator/stdcxx/trunk/tests: include/21.strings.h
src/21.strings.cpp strings/21.string.append.cpp
strings/21.string.assign.cpp strings/21.string.insert.cpp
strings/21.string.replace.cpp
Author: antonp
Date: Thu Jun 8 06:41:03 2006
New Revision: 412750
URL: http://svn.apache.org/viewvc?rev=412750&view=rev
Log:
2006-06-08 Anton Pevtsov <an...@moscow.vdiweb.com>
* 21.strings.h (RangeBase): New base class to exercise the range
template methods overloads - append, assign, insert and replace.
* 21.strings.cpp (_rw_setvars): append_range and assign_range
cases separated from others due to the changes in the
corresponding tests.
* 21.string.append.cpp (AppendRange, AppendRangeOverload): New class
templates to abstract out the invocation of the append member
template and its overloads.
(test_append): Added RangeBase& argument and eliminated
test_append_range (obviated by the addition of the argument).
(test_append): Dispatched to the appropriate specialization
based on the iterator id (if any).
* 21.string.assign.cpp: Same
* 21.string.insert.cpp: Same
* 21.string.replace.cpp (ReplaceBase): moved to 21.strings.h
and renamed to RangeBase.
(ReplaceRangeOverload): begin overloads moved to the base class.
(test_replace): parameter type changed to RangeBase.
Modified:
incubator/stdcxx/trunk/tests/include/21.strings.h
incubator/stdcxx/trunk/tests/src/21.strings.cpp
incubator/stdcxx/trunk/tests/strings/21.string.append.cpp
incubator/stdcxx/trunk/tests/strings/21.string.assign.cpp
incubator/stdcxx/trunk/tests/strings/21.string.insert.cpp
incubator/stdcxx/trunk/tests/strings/21.string.replace.cpp
Modified: incubator/stdcxx/trunk/tests/include/21.strings.h
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/include/21.strings.h?rev=412750&r1=412749&r2=412750&view=diff
==============================================================================
--- incubator/stdcxx/trunk/tests/include/21.strings.h (original)
+++ incubator/stdcxx/trunk/tests/include/21.strings.h Thu Jun 8 06:41:03 2006
@@ -777,6 +777,71 @@
}
+/**************************************************************************/
+
+// base class-functor for the range template overloads testing
+template <class String>
+struct RangeBase {
+
+ typedef typename String::value_type StringChar;
+ typedef typename String::pointer StringPtr;
+ typedef typename String::const_pointer StringConstPtr;
+ typedef typename String::iterator StringIter;
+ typedef typename String::const_iterator StringConstIter;
+ typedef typename String::reverse_iterator StringRevIter;
+ typedef typename String::const_reverse_iterator StringConstRevIter;
+
+ RangeBase () { }
+
+ virtual ~RangeBase () { /* silence warnings */ }
+
+ static StringPtr
+ begin (String &str, StringPtr*) {
+ return _RWSTD_CONST_CAST (StringPtr, str.data ());
+ }
+
+ static StringConstPtr
+ begin (const String &str, StringConstPtr*) {
+ return str.data ();
+ }
+
+#ifndef _RWSTD_NO_DEBUG_ITER
+
+ // when debugging iterators are enabled string::iterator and
+ // string::pointer are distinct types; otherwise they are the
+ // same type
+
+ static StringIter
+ begin (String &str, StringIter*) {
+ return str.begin ();
+ }
+
+ static StringConstIter
+ begin (const String &str, StringConstIter*) {
+ return str.begin ();
+ }
+
+#endif // _RWSTD_NO_DEBUG_ITER
+
+ static StringRevIter
+ begin (String &str, StringRevIter*) {
+ return str.rbegin ();
+ }
+
+ static StringConstRevIter
+ begin (const String &str, StringConstRevIter*) {
+ return str.rbegin ();
+ }
+
+ virtual String&
+ operator() (String &str, const StringTestCaseData<StringChar>&) const {
+ RW_ASSERT (!"logic error: should be never called");
+ return str;
+ }
+};
+
+/**************************************************************************/
+
#define Disabled(which) \
StringIds::opt_memfun_disabled [which & ~StringIds::fid_mask]
Modified: incubator/stdcxx/trunk/tests/src/21.strings.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/src/21.strings.cpp?rev=412750&r1=412749&r2=412750&view=diff
==============================================================================
--- incubator/stdcxx/trunk/tests/src/21.strings.cpp (original)
+++ incubator/stdcxx/trunk/tests/src/21.strings.cpp Thu Jun 8 06:41:03 2006
@@ -661,6 +661,17 @@
case StringIds::append_range:
case StringIds::assign_range:
+ rw_asnprintf (&buf, &bufsize, "%{+}<%{$Iterator:-Iterator}>("
+ "%{?}begin()%{:}%{$Iterator:-Iterator}(%{#*s})%{;}"
+ "%{?} + %zu%{;}, "
+ "%{?}begin()%{:}%{$Iterator:-Iterator}(...)%{;}"
+ "%{?} + %zu%{;}"
+ "%{?}, const allocator_type&%{;})",
+ self, int (arg_len), arg,
+ 0 != pcase->off2, pcase->off2,
+ self, 0 != range2_end, range2_end, use_alloc);
+ break;
+
case StringIds::ctor_range:
case StringIds::ctor_range_alloc:
rw_asnprintf (&buf, &bufsize, "%{+}<%{$Iterator:-Iterator}>("
Modified: incubator/stdcxx/trunk/tests/strings/21.string.append.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/strings/21.string.append.cpp?rev=412750&r1=412749&r2=412750&view=diff
==============================================================================
--- incubator/stdcxx/trunk/tests/strings/21.string.append.cpp (original)
+++ incubator/stdcxx/trunk/tests/strings/21.string.append.cpp Thu Jun 8 06:41:03 2006
@@ -281,7 +281,7 @@
#undef TEST
#define TEST(str, arg, off, size, res, bthrow) { \
- __LINE__, off, size, -1, -1, -1, \
+ __LINE__, -1, -1, off, size, -1, \
str, sizeof str - 1, \
arg, sizeof arg - 1, res, sizeof res - 1, bthrow \
}
@@ -483,158 +483,97 @@
/**************************************************************************/
-template <class charT, class Traits, class Allocator, class Iterator>
-void test_append_range (const charT *wstr,
- std::size_t wstr_len,
- const charT *warg,
- std::size_t warg_len,
- std::size_t res_len,
- Traits*,
- Allocator*,
- const Iterator &it,
- const StringTestCase &tcase)
-{
- typedef std::basic_string <charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
+// invokes specializations of the member function template
+// on the required iterator categories
+template <class String, class Iterator>
+struct AppendRange: RangeBase<String> {
- const char* const itname =
- tcase.arg ? type_name (it, (charT*)0) : "basic_string::iterator";
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
- // compute the size of the controlled sequence and the size
- // of the sequence denoted by the argument keeping in mind
- // that the latter may refer to the former
- const std::size_t size1 = wstr_len;
- const std::size_t size2 = tcase.arg ? warg_len : size1;
+ AppendRange () { }
- // construct the string object to be modified
- String s_str (wstr, size1);
+ virtual String&
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
- // compute the offset and the extent (the number of elements)
- // of the second range into the argument of the function call
- const std::size_t off =
- std::size_t (tcase.off) < size2 ? std::size_t (tcase.off) : size2;
- const std::size_t ext =
- off + tcase.size < size2 ? std::size_t (tcase.size) : size2 - off;
-
- if (tcase.arg) {
- const charT* const beg = warg + off;
- const charT* const end = beg + ext;
+ const StringTestCase &tcase = tdata.tcase_;
- const Iterator first (beg, beg, end);
- const Iterator last (end, beg, end);
+ const String &cstr = str;
- s_str.append (first, last);
- }
- else {
- // self-referential modification (appending a range
- // of elements with a subrange of its own elements)
- const StringIter first (s_str.begin () + off);
- const StringIter last (first + ext);
+ // when (0 == tcase.arg) exercise self-referential modification
+ // (i.e., replacing a range of elements with a subrange of its
+ // own elements)
+ const StringChar* const beg =
+ (tcase.arg ? tdata.arg_ : cstr.data ()) + tdata.off2_;
- s_str.append (first, last);
- }
+ const StringChar* const end = beg + tdata.ext2_;
- // detrmine whether the produced sequence matches the exepceted result
- const std::size_t match = rw_match (tcase.res, s_str.data (), tcase.nres);
+ const Iterator first (beg, beg, end);
+ const Iterator last (end, beg, end);
- rw_assert (match == res_len, 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s}, got %{/*.*Gs}, "
- "difference at offset %zu for %s",
- __LINE__, int (tcase.nres), tcase.res,
- int (sizeof (charT)), int (s_str.size ()), s_str.c_str (),
- match, itname);
-}
+ return str.append (first, last);
+ }
+};
/**************************************************************************/
-template <class charT, class Traits, class Allocator>
-void test_append_range (const charT *wstr,
- std::size_t wstr_len,
- const charT *warg,
- std::size_t warg_len,
- std::size_t res_len,
- Traits*,
- Allocator*,
- const StringTestCase &tcase)
+// invokes possible overloads of the member function template
+// on common RandomAccessIterator types
+template <class String, class Iterator>
+struct AppendRangeOverload: RangeBase<String>
{
- if (tcase.bthrow) // this method doesn't throw
- return;
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
- test_append_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, InputIter<charT>(0, 0, 0), tcase);
+ AppendRangeOverload () { }
- // there is no need to call test_append_range
- // for other iterators in this case
- if (0 == tcase.arg)
- return;
-
- test_append_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, ConstFwdIter<charT>(0, 0, 0), tcase);
-
- test_append_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, ConstBidirIter<charT>(0, 0, 0), tcase);
-
- test_append_range (wstr, wstr_len, warg, warg_len, res_len,
- (Traits*)0, (Allocator*)0,
- ConstRandomAccessIter<charT>(0, 0, 0), tcase);
-}
-
-/**************************************************************************/
+ virtual String&
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
-template <class charT, class Traits, class Allocator>
-void test_append (charT, Traits*, Allocator*,
- const StringFunc &func,
- const StringTestCase &tcase)
-{
- typedef std::basic_string <charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
- typedef typename UserTraits<charT>::MemFun UTMemFun;
+ const StringTestCase &tcase = tdata.tcase_;
- static const std::size_t BUFSIZE = 256;
+ const std::size_t off = tdata.off2_;
+ const std::size_t ext = tdata.ext2_;
- static charT wstr_buf [BUFSIZE];
- static charT warg_buf [BUFSIZE];
+ if (0 == tcase.arg) {
+ // exercise self-referential modification (i.e., replacing
+ // a range of elements with a subrange of its own elements)
- std::size_t str_len = sizeof wstr_buf / sizeof *wstr_buf;
- std::size_t arg_len = sizeof warg_buf / sizeof *warg_buf;
+ const Iterator first (begin (str, (Iterator*)0) + off);
+ const Iterator last (first + ext);
- charT* wstr = rw_expand (wstr_buf, tcase.str, tcase.str_len, &str_len);
- charT* warg = rw_expand (warg_buf, tcase.arg, tcase.arg_len, &arg_len);
+ return str.append (first, last);
+ }
- static charT wres_buf [BUFSIZE];
- std::size_t res_len = sizeof wres_buf / sizeof *wres_buf;
- charT* wres = rw_expand (wres_buf, tcase.res, tcase.nres, &res_len);
+ String str_arg (tdata.arg_, tdata.arglen_);
- // special processing for append_range to exercise all iterators
- if (Append (range) == func.which_) {
- test_append_range (wstr, str_len, warg, arg_len, res_len,
- (Traits*)0, (Allocator*)0, tcase);
+ const Iterator first (begin (str_arg, (Iterator*)0) + off);
+ const Iterator last (first + ext);
- if (wstr != wstr_buf)
- delete[] wstr;
+ return str.append (first, last);
+ }
+};
- if (warg != warg_buf)
- delete[] warg;
+/**************************************************************************/
- if (wres != wres_buf)
- delete[] wres;
+template <class charT, class Traits, class Allocator>
+void test_append (charT*, Traits*, Allocator*, const RangeBase<
+ std::basic_string <charT, Traits, Allocator> > &rng,
+ const StringTestCaseData<charT> &tdata)
+{
+ typedef std::basic_string <charT, Traits, Allocator> String;
+ typedef typename String::iterator StringIter;
+ typedef typename UserTraits<charT>::MemFun TraitsFunc;
- return;
- }
+ const StringFunc &func = tdata.func_;
+ const StringTestCase &tcase = tdata.tcase_;
// construct the string object to be modified
// and the (possibly unused) argument string
- /* const */ String str (wstr, str_len);
- const String arg (warg, arg_len);
-
- if (wstr != wstr_buf)
- delete[] wstr;
-
- if (warg != warg_buf)
- delete[] warg;
-
- wstr = 0;
- warg = 0;
+ /* const */ String str (tdata.str_, tdata.strlen_);
+ const String arg (tdata.arg_, tdata.arglen_);
// save the state of the string object before the call
// to detect wxception safety violations (changes to
@@ -650,7 +589,7 @@
std::size_t* const rg_calls = rw_get_call_counters ((Traits*)0, (charT*)0);
if (rg_calls)
- total_length_calls = rg_calls [UTMemFun::length];
+ total_length_calls = rg_calls [TraitsFunc::length];
rwt_free_store* const pst = rwt_get_free_store (0);
SharedAlloc* const pal = SharedAlloc::instance ();
@@ -686,12 +625,8 @@
#else // if defined (_RWSTD_NO_EXCEPTIONS)
- if (tcase.bthrow) {
- if (wres != wres_buf)
- delete[] wres;
-
+ if (tcase.bthrow)
return;
- }
#endif // _RWSTD_NO_EXCEPTIONS
@@ -708,7 +643,7 @@
case Append (cptr):
ret_ptr = &str.append (ptr_arg);
if (rg_calls)
- n_length_calls = rg_calls [UTMemFun::length];
+ n_length_calls = rg_calls [TraitsFunc::length];
break;
case Append (cstr):
@@ -720,13 +655,17 @@
break;
case Append (cstr_size_size):
- ret_ptr = &str.append (str_arg, tcase.off, tcase.size);
+ ret_ptr = &str.append (str_arg, tcase.off2, tcase.size2);
break;
case Append (size_val):
ret_ptr = &str.append (tcase.size, val_arg);
break;
+ case Append (range):
+ ret_ptr = &rng (str, tdata);
+ break;
+
case PushBack (val):
str.push_back (val_arg);
ret_ptr = &str;
@@ -746,27 +685,29 @@
"line %d. %{$FUNCALL} returned invalid reference, "
"offset is %td", __LINE__, ret_off);
+ // for convenience
+ static const int cwidth = sizeof (charT);
+
// verify that strings are of equal length
- rw_assert (res_len == str.size (), 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s}, "
+ rw_assert (tdata.reslen_ == str.size (), 0, tcase.line,
+ "line %d. %{$FUNCALL} expected %{/*.*Gs}, "
"length %zu, got %{/*.*Gs}, length %zu",
- __LINE__, int (tcase.nres), tcase.res,
- res_len, int (sizeof (charT)),
+ __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+ tdata.reslen_, cwidth,
int (str.size ()), str.c_str (), str.size ());
- if (res_len == str.size ()) {
+ if (tdata.reslen_ == str.size ()) {
// if the result length matches the expected length
// (and only then), also verify that the modified
// string matches the expected result
const std::size_t match =
rw_match (tcase.res, str.c_str (), tcase.nres);
- rw_assert (match == res_len, 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s}, "
+ rw_assert (match == tdata.reslen_, 0, tcase.line,
+ "line %d. %{$FUNCALL} expected %{/*.*Gs}, "
"got %{/*.*Gs}, difference at offset %zu",
- __LINE__, int (tcase.nres), tcase.res,
- int (sizeof (charT)), int (str.size ()),
- str.c_str (), match);
+ __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+ cwidth, int (str.size ()), str.c_str (), match);
}
// verify that Traits::length was used
@@ -859,23 +800,92 @@
#endif // _RWSTD_NO_REPLACEABLE_NEW_DELETE
- rw_assert (expect_throws == throw_count, 0, tcase.line,
- "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
- "while changing capacity from %zu to %zu, got %zu",
- __LINE__, exceptions [3],
- str_state.capacity_, str.capacity (), throw_count);
+ // verify number of exceptions thrown
+ // for range version the allocation may take place several times
+ if (Append (range) != func.which_)
+ rw_assert (expect_throws == throw_count, 0, tcase.line,
+ "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
+ "while changing capacity from %zu to %zu, got %zu",
+ __LINE__, exceptions [3],
+ str_state.capacity_, str.capacity (), throw_count);
+ else
+ rw_assert (expect_throws <= throw_count, 0, tcase.line,
+ "line %d: %{$FUNCALL}: expected at least 1 %s exception "
+ "while changing capacity from %zu to %zu, got %zu",
+ __LINE__, exceptions [3],
+ str_state.capacity_, str.capacity (), throw_count);
// disable bad_alloc exceptions
*pst->throw_at_calls_ [0] = 0;
pal->throw_at_calls_ [pal->m_allocate] = 0;
+}
+
+/**************************************************************************/
+
+template <class charT, class Traits, class Allocator>
+void test_append (charT*, Traits*, Allocator*,
+ const StringTestCaseData<charT> &tdata)
+{
+ typedef std::basic_string<charT, Traits, Allocator> String;
+
+ if (tdata.func_.which_ == Append (range)) {
+
+ switch (tdata.func_.iter_id_) {
+
+ // exercise possible overloads of the member function template
+ // on common RandomAccessIterator types
+#undef TEST
+#define TEST(Iterator) do { \
+ typedef typename String::Iterator Iter; \
+ static const \
+ AppendRangeOverload<String, Iter> app; \
+ test_append ((charT*)0, (Traits*)0, (Allocator*)0, app, tdata); \
+ } while (0)
+
+ case StringIds::Pointer: TEST (pointer); break;
+ case StringIds::ConstPointer: TEST (const_pointer); break;
+ case StringIds::Iterator: TEST (iterator); break;
+ case StringIds::ConstIterator: TEST (const_iterator); break;
+
+ // disabled for now
+ case StringIds::ReverseIterator:
+ // TEST (reverse_iterator);
+ break;
+
+ case StringIds::ConstReverseIterator:
+ // TEST (const_reverse_iterator);
+ break;
+
+ // exercise specializations of the member function template
+ // on the required iterator categories
- if (wres != wres_buf)
- delete[] wres;
+#undef TEST
+#define TEST(Iterator) do { \
+ typedef Iterator<charT> Iter; \
+ static const \
+ AppendRange<String, Iter> app; \
+ test_append ((charT*)0, (Traits*)0, (Allocator*)0, app, tdata); \
+ } while (0)
+
+ case StringIds::Input: TEST (InputIter); break;
+ case StringIds::Forward: TEST (ConstFwdIter); break;
+ case StringIds::Bidir: TEST (ConstBidirIter); break;
+ case StringIds::Random: TEST (ConstRandomAccessIter); break;
+
+ default:
+ rw_error (0, 0, __LINE__, "bad iterator id");
+ }
+ }
+ else {
+ // exercise ordinary overloads of the member function
+ static const RangeBase<String > app;
+ test_append ((charT*)0, (Traits*)0, (Allocator*)0, app, tdata);
+ }
}
/**************************************************************************/
-DEFINE_STRING_TEST_DISPATCH (test_append);
+DEFINE_STRING_TEST_FUNCTIONS (test_append);
int main (int argc, char** argv)
{
@@ -903,7 +913,10 @@
const std::size_t test_count = sizeof tests / sizeof *tests;
- return rw_run_string_test (argc, argv, __FILE__,
- "lib.string.append",
- test_append, tests, test_count);
+ const int status =
+ rw_run_string_test (argc, argv, __FILE__,
+ "lib.string.append",
+ test_append_func_array, tests, test_count);
+
+ return status;
}
Modified: incubator/stdcxx/trunk/tests/strings/21.string.assign.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/strings/21.string.assign.cpp?rev=412750&r1=412749&r2=412750&view=diff
==============================================================================
--- incubator/stdcxx/trunk/tests/strings/21.string.assign.cpp (original)
+++ incubator/stdcxx/trunk/tests/strings/21.string.assign.cpp Thu Jun 8 06:41:03 2006
@@ -278,7 +278,7 @@
#undef TEST
#define TEST(str, arg, off, size, res, bthrow) { \
- __LINE__, off, size, -1, -1, -1, \
+ __LINE__, -1, -1, off, size, -1, \
str, sizeof str - 1, \
arg, sizeof arg - 1, res, sizeof res - 1, bthrow \
}
@@ -429,160 +429,100 @@
/**************************************************************************/
-template <class charT, class Traits, class Allocator, class Iterator>
-void test_assign_range (const charT *wstr,
- std::size_t wstr_len,
- const charT *warg,
- std::size_t warg_len,
- std::size_t res_len,
- Traits*,
- Allocator*,
- const Iterator &it,
- const StringTestCase &tcase)
-{
- typedef std::basic_string <charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
+// invokes specializations of the member function template
+// on the required iterator categories
+template <class String, class Iterator>
+struct AssignRange: RangeBase<String> {
- const char* const itname =
- tcase.arg ? type_name (it, (charT*)0) : "basic_string::iterator";
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
- // compute the size of the controlled sequence and the size
- // of the sequence denoted by the argument keeping in mind
- // that the latter may refer to the former
- const std::size_t size1 = wstr_len;
- const std::size_t size2 = tcase.arg ? warg_len : size1;
+ AssignRange () { }
- // construct the string object to be modified
- String str (wstr, size1);
+ virtual String&
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
- // compute the offset and the extent (the number of elements)
- // of the second range into the argument of the function call
- const std::size_t off =
- std::size_t (tcase.off) < size2 ? std::size_t (tcase.off) : size2;
- const std::size_t ext =
- off + tcase.size < size2 ? std::size_t (tcase.size) : size2 - off;
-
- if (tcase.arg) {
- const charT* const beg = warg + off;
- const charT* const end = beg + ext;
+ const StringTestCase &tcase = tdata.tcase_;
- const Iterator first (beg, beg, end);
- const Iterator last (end, beg, end);
+ const String &cstr = str;
- str.assign (first, last);
- }
- else {
- // self-referential modification (appending a range
- // of elements with a subrange of its own elements)
- const StringIter first (str.begin () + off);
- const StringIter last (first + ext);
+ // when (0 == tcase.arg) exercise self-referential modification
+ // (i.e., replacing a range of elements with a subrange of its
+ // own elements)
+ const StringChar* const beg =
+ (tcase.arg ? tdata.arg_ : cstr.data ()) + tdata.off2_;
- str.assign (first, last);
- }
+ const StringChar* const end = beg + tdata.ext2_;
- // detrmine whether the produced sequence matches the exepceted result
- const std::size_t match = rw_match (tcase.res, str.data (), tcase.nres);
+ const Iterator first (beg, beg, end);
+ const Iterator last (end, beg, end);
- rw_assert (match == res_len, 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s}, got %{/*.*Gs}, "
- "difference at off %zu for %s",
- __LINE__, int (tcase.nres), tcase.res,
- int (sizeof (charT)), int (str.size ()), str.c_str (),
- match, itname);
-}
+ return str.assign (first, last);
+ }
+};
/**************************************************************************/
-template <class charT, class Traits, class Allocator>
-void test_assign_range (const charT *wstr,
- std::size_t wstr_len,
- const charT *warg,
- std::size_t warg_len,
- std::size_t res_len,
- Traits*,
- Allocator*,
- const StringTestCase &tcase)
+// invokes possible overloads of the member function template
+// on common RandomAccessIterator types
+template <class String, class Iterator>
+struct AssignRangeOverload: RangeBase<String>
{
- if (tcase.bthrow) // this method doesn't throw
- return;
-
- test_assign_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, InputIter<charT>(0, 0, 0), tcase);
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
- // there is no need to call test_assign_range
- // for other iterators in this case
- if (0 == tcase.arg)
- return;
-
- test_assign_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, ConstFwdIter<charT>(0, 0, 0), tcase);
-
- test_assign_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, ConstBidirIter<charT>(0, 0, 0), tcase);
-
- test_assign_range (wstr, wstr_len, warg, warg_len, res_len,
- (Traits*)0, (Allocator*)0,
- ConstRandomAccessIter<charT>(0, 0, 0), tcase);
-}
+ AssignRangeOverload () { }
-/**************************************************************************/
+ virtual String&
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
-template <class charT, class Traits, class Allocator>
-void test_assign (charT, Traits*, Allocator*,
- const StringFunc &func,
- const StringTestCase &tcase)
-{
- typedef std::basic_string <charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
- typedef typename UserTraits<charT>::MemFun UTMemFun;
+ const StringTestCase &tcase = tdata.tcase_;
- static const std::size_t BUFSIZE = 256;
+ const std::size_t off = tdata.off2_;
+ const std::size_t ext = tdata.ext2_;
- static charT wstr_buf [BUFSIZE];
- static charT warg_buf [BUFSIZE];
+ if (0 == tcase.arg) {
+ // exercise self-referential modification (i.e., replacing
+ // a range of elements with a subrange of its own elements)
- std::size_t str_len = sizeof wstr_buf / sizeof *wstr_buf;
- std::size_t arg_len = sizeof warg_buf / sizeof *warg_buf;
+ const Iterator first (begin (str, (Iterator*)0) + off);
+ const Iterator last (first + ext);
- charT* wstr = rw_expand (wstr_buf, tcase.str, tcase.str_len, &str_len);
- charT* warg = rw_expand (warg_buf, tcase.arg, tcase.arg_len, &arg_len);
+ return str.assign (first, last);
+ }
- static charT wres_buf [BUFSIZE];
- std::size_t res_len = sizeof wres_buf / sizeof *wres_buf;
- charT* wres = rw_expand (wres_buf, tcase.res, tcase.nres, &res_len);
+ String str_arg (tdata.arg_, tdata.arglen_);
- // special processing for assign_range to exercise all iterators
- if (Assign (range) == func.which_) {
- test_assign_range (wstr, str_len, warg, arg_len,
- res_len, (Traits*)0, (Allocator*)0, tcase);
+ const Iterator first (begin (str_arg, (Iterator*)0) + off);
+ const Iterator last (first + ext);
- if (wstr != wstr_buf)
- delete[] wstr;
+ return str.assign (first, last);
+ }
+};
- if (warg != warg_buf)
- delete[] warg;
+/**************************************************************************/
- if (wres != wres_buf)
- delete[] wres;
+template <class charT, class Traits, class Allocator>
+void test_assign (charT*, Traits*, Allocator*, const RangeBase<
+ std::basic_string <charT, Traits, Allocator> > &rng,
+ const StringTestCaseData<charT> &tdata)
+{
+ typedef std::basic_string <charT, Traits, Allocator> String;
+ typedef typename String::iterator StringIter;
+ typedef typename UserTraits<charT>::MemFun TraitsFunc;
- return;
- }
+ const StringFunc &func = tdata.func_;
+ const StringTestCase &tcase = tdata.tcase_;
// construct the string object to be modified
// and the (possibly unused) argument string
- /* const */ String str (wstr, str_len);
- const String arg (warg, arg_len);
-
- if (wstr != wstr_buf)
- delete[] wstr;
+ /* const */ String str (tdata.str_, tdata.strlen_);
+ const String arg (tdata.arg_, tdata.arglen_);
- if (warg != warg_buf)
- delete[] warg;
-
- wstr = 0;
- warg = 0;
-
- std::size_t size = tcase.size >= 0 ? tcase.size : str.max_size () + 1;
+ std::size_t size = tcase.size >= 0 ? tcase.size : str.max_size () + 1;
+ std::size_t size2 = tcase.size2 >= 0 ? tcase.size2 : str.max_size () + 1;
// save the state of the string object before the call
// to detect wxception safety violations (changes to
@@ -598,7 +538,7 @@
std::size_t* const rg_calls = rw_get_call_counters ((Traits*)0, (charT*)0);
if (rg_calls)
- total_length_calls = rg_calls [UTMemFun::length];
+ total_length_calls = rg_calls [TraitsFunc::length];
rwt_free_store* const pst = rwt_get_free_store (0);
SharedAlloc* const pal = SharedAlloc::instance ();
@@ -634,12 +574,8 @@
#else // if defined (_RWSTD_NO_EXCEPTIONS)
- if (tcase.bthrow) {
- if (wres != wres_buf)
- delete[] wres;
-
+ if (tcase.bthrow)
return;
- }
#endif // _RWSTD_NO_EXCEPTIONS
@@ -655,7 +591,7 @@
case Assign (cptr):
ret_ptr = &str.assign (arg_ptr);
if (rg_calls)
- n_length_calls = rg_calls [UTMemFun::length];
+ n_length_calls = rg_calls [TraitsFunc::length];
break;
case Assign (cstr):
@@ -667,7 +603,7 @@
break;
case Assign (cstr_size_size):
- ret_ptr = &str.assign (arg_str, tcase.off, size);
+ ret_ptr = &str.assign (arg_str, tcase.off2, size2);
break;
case Assign (size_val): {
@@ -676,6 +612,10 @@
break;
}
+ case Assign (range):
+ ret_ptr = &rng (str, tdata);
+ break;
+
default:
RW_ASSERT (!"test logic error: unknown assign overload");
}
@@ -690,27 +630,28 @@
"line %d. %{$FUNCALL} returned invalid reference, "
"offset is %td", __LINE__, ret_off);
+ // for convenience
+ static const int cwidth = sizeof (charT);
+
// verfiy that strings length are equal
- rw_assert (res_len == str.size (), 0, tcase.line,
- "line %d. %{$FUNCALL}: expected %{#*s} with length "
+ rw_assert (tdata.reslen_ == str.size (), 0, tcase.line,
+ "line %d. %{$FUNCALL}: expected %{/*.*Gs} with length "
"%zu, got %{/*.*Gs} with length %zu", __LINE__,
- int (tcase.nres), tcase.res, res_len,
- int (sizeof (charT)), int (str.size ()),
- str.c_str (), str.size ());
+ cwidth, int (tdata.reslen_), tdata.res_, tdata.reslen_,
+ cwidth, int (str.size ()), str.c_str (), str.size ());
- if (res_len == str.size ()) {
+ if (tdata.reslen_ == str.size ()) {
// if the result length matches the expected length
// (and only then), also verify that the modified
// string matches the expected result
const std::size_t match =
rw_match (tcase.res, str.c_str(), tcase.nres);
- rw_assert (match == res_len, 0, tcase.line,
- "line %d. %{$FUNCALL}: expected %{#*s}, "
+ rw_assert (match == tdata.reslen_, 0, tcase.line,
+ "line %d. %{$FUNCALL}: expected %{/*.*Gs}, "
"got %{/*.*Gs}, difference at off %zu",
- __LINE__, int (tcase.nres), tcase.res,
- int (sizeof (charT)), int (str.size ()),
- str.c_str (), match);
+ __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+ cwidth, int (str.size ()), str.c_str (), match);
}
// verify that Traits::length was used
@@ -812,24 +753,92 @@
}
#endif
- rw_assert (expect_throws == throw_count, 0, tcase.line,
- "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
- "while changing capacity from %zu to %zu, got %zu",
- __LINE__, exceptions [3],
- str_state.capacity_, str.capacity (), throw_count);
+ // verify number of exceptions thrown
+ // for range version the allocation may take place several times
+ if (Assign (range) != func.which_)
+ rw_assert (expect_throws == throw_count, 0, tcase.line,
+ "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
+ "while changing capacity from %zu to %zu, got %zu",
+ __LINE__, exceptions [3],
+ str_state.capacity_, str.capacity (), throw_count);
+ else
+ rw_assert (expect_throws <= throw_count, 0, tcase.line,
+ "line %d: %{$FUNCALL}: expected at least 1 %s exception "
+ "while changing capacity from %zu to %zu, got %zu",
+ __LINE__, exceptions [3],
+ str_state.capacity_, str.capacity (), throw_count);
// disable bad_alloc exceptions
*pst->throw_at_calls_ [0] = 0;
pal->throw_at_calls_ [pal->m_allocate] = 0;
+}
+
+/**************************************************************************/
- if (wres != wres_buf)
- delete[] wres;
+template <class charT, class Traits, class Allocator>
+void test_assign (charT*, Traits*, Allocator*,
+ const StringTestCaseData<charT> &tdata)
+{
+ typedef std::basic_string<charT, Traits, Allocator> String;
+
+ if (tdata.func_.which_ == Assign (range)) {
+
+ switch (tdata.func_.iter_id_) {
+
+ // exercise possible overloads of the member function template
+ // on common RandomAccessIterator types
+#undef TEST
+#define TEST(Iterator) do { \
+ typedef typename String::Iterator Iter; \
+ static const \
+ AssignRangeOverload<String, Iter> app; \
+ test_assign ((charT*)0, (Traits*)0, (Allocator*)0, app, tdata); \
+ } while (0)
+
+ case StringIds::Pointer: TEST (pointer); break;
+ case StringIds::ConstPointer: TEST (const_pointer); break;
+ case StringIds::Iterator: TEST (iterator); break;
+ case StringIds::ConstIterator: TEST (const_iterator); break;
+
+ // disabled for now
+ case StringIds::ReverseIterator:
+ // TEST (reverse_iterator);
+ break;
+
+ case StringIds::ConstReverseIterator:
+ // TEST (const_reverse_iterator);
+ break;
+
+ // exercise specializations of the member function template
+ // on the required iterator categories
+#undef TEST
+#define TEST(Iterator) do { \
+ typedef Iterator<charT> Iter; \
+ static const \
+ AssignRange<String, Iter> app; \
+ test_assign ((charT*)0, (Traits*)0, (Allocator*)0, app, tdata); \
+ } while (0)
+
+ case StringIds::Input: TEST (InputIter); break;
+ case StringIds::Forward: TEST (ConstFwdIter); break;
+ case StringIds::Bidir: TEST (ConstBidirIter); break;
+ case StringIds::Random: TEST (ConstRandomAccessIter); break;
+
+ default:
+ rw_error (0, 0, __LINE__, "bad iterator id");
+ }
+ }
+ else {
+ // exercise ordinary overloads of the member function
+ static const RangeBase<String> app;
+ test_assign ((charT*)0, (Traits*)0, (Allocator*)0, app, tdata);
+ }
}
/**************************************************************************/
-DEFINE_STRING_TEST_DISPATCH (test_assign);
+DEFINE_STRING_TEST_FUNCTIONS (test_assign);
int main (int argc, char** argv)
{
@@ -852,7 +861,10 @@
const std::size_t test_count = sizeof tests / sizeof *tests;
- return rw_run_string_test (argc, argv, __FILE__,
- "lib.string.assign",
- test_assign, tests, test_count);
+ const int status =
+ rw_run_string_test (argc, argv, __FILE__,
+ "lib.string.assign",
+ test_assign_func_array, tests, test_count);
+
+ return status;
}
Modified: incubator/stdcxx/trunk/tests/strings/21.string.insert.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/strings/21.string.insert.cpp?rev=412750&r1=412749&r2=412750&view=diff
==============================================================================
--- incubator/stdcxx/trunk/tests/strings/21.string.insert.cpp (original)
+++ incubator/stdcxx/trunk/tests/strings/21.string.insert.cpp Thu Jun 8 06:41:03 2006
@@ -299,13 +299,13 @@
TEST ("x@1411", 872, "x@3695", 128, 2284, "x@3695", 0),
TEST ("x@1412", 0, "x@2284", 0, 2284, "x@3696", 0),
- TEST ("\0", 2, "", 0, 0, "", 1),
+ TEST ("\0", 2, "", 0, 0, "\0", 1),
TEST ("", 0, "\0", 2, 0, "", 2),
- TEST ("a", 2, "", 0, 0, "", 1),
+ TEST ("a", 2, "", 0, 0, "a", 1),
TEST ("", 0, "a", 2, 0, "", 2),
- TEST ("x@4096", 4106, "", 0, 0, "", 1),
+ TEST ("x@4096", 4106, "", 0, 0, "x@4096", 1),
TEST ("", 0, "x@4096", 4106, 0, "", 2),
TEST ("last", 4, "test", 0, 4, "lasttest", 0)
@@ -546,163 +546,105 @@
/**************************************************************************/
-template <class charT, class Traits, class Allocator, class Iterator>
-void test_insert_range (const charT *wstr,
- std::size_t wstr_len,
- const charT *warg,
- std::size_t warg_len,
- std::size_t res_len,
- Traits*,
- Allocator*,
- const Iterator &it,
- const StringTestCase &tcase)
-{
- typedef std::basic_string <charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
+// invokes specializations of the member function template
+// on the required iterator categories
+template <class String, class Iterator>
+struct InsertRange: RangeBase<String> {
- const char* const itname =
- tcase.arg ? type_name (it, (charT*)0) : "basic_string::iterator";
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
- // compute the size of the controlled sequence and the size
- // of the sequence denoted by the argument keeping in mind
- // that the latter may refer to the former
- const std::size_t size1 = wstr_len;
- const std::size_t size2 = tcase.arg ? warg_len : size1;
+ InsertRange () { }
- // construct the string object to be modified
- String str (wstr, size1);
+ virtual String&
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
- // compute the offset and the extent (the number of elements)
- // of the first range into the string object being modified
- const std::size_t off1 =
- std::size_t (tcase.off) < size1 ? std::size_t (tcase.off) : size1;
+ const StringTestCase &tcase = tdata.tcase_;
- // compute the offset and the extent (the number of elements)
- // of the second range into the argument of the function call
- const std::size_t off2 =
- std::size_t (tcase.off2) < size2 ? std::size_t (tcase.off2) : size2;
- const std::size_t ext2 =
- off2 + tcase.size2 < size2 ? std::size_t (tcase.size2) : size2 - off2;
-
- // create an iterator into the string object being modified
- StringIter iter (str.begin () + off1);
-
- if (tcase.arg) {
- const charT* const beg = warg + off2;
- const charT* const end = beg + ext2;
+ // create a pair of iterators into the string object being modified
+ const StringIter first1 (str.begin () + tdata.off1_);
- const Iterator first (beg, beg, end);
- const Iterator last (end, beg, end);
+ const String &cstr = str;
- str.insert (iter, first, last);
- }
- else {
- // self-referential modification (inserting a range
- // of elements with a subrange of its own elements)
- const StringIter first (str.begin () + off2);
- const StringIter last (first + ext2);
+ // when (0 == tcase.arg) exercise self-referential modification
+ // (i.e., replacing a range of elements with a subrange of its
+ // own elements)
+ const StringChar* const beg =
+ (tcase.arg ? tdata.arg_ : cstr.data ()) + tdata.off2_;
- str.insert (iter, first, last);
- }
+ const StringChar* const end = beg + tdata.ext2_;
- // detrmine whether the produced sequence matches the exepceted result
- const std::size_t match = rw_match (tcase.res, str.data (), tcase.nres);
+ const Iterator first2 (beg, beg, end);
+ const Iterator last2 (end, beg, end);
- rw_assert (match == res_len, 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s}, got %{/*.*Gs}, "
- "difference at pos %zu for %s",
- __LINE__, int (tcase.nres), tcase.res,
- int (sizeof (charT)), int (str.size ()), str.c_str (),
- match, itname);
-}
+ str.insert (first1, first2, last2);
+ return str;
+ }
+};
-/**************************************************************************/
-template <class charT, class Traits, class Allocator>
-void test_insert_range (const charT *wstr,
- std::size_t wstr_len,
- const charT *warg,
- std::size_t warg_len,
- std::size_t res_len,
- Traits*,
- Allocator*,
- const StringTestCase &tcase)
+// invokes possible overloads of the member function template
+// on common RandomAccessIterator types
+template <class String, class Iterator>
+struct InsertRangeOverload: RangeBase<String>
{
- if (tcase.bthrow) // this method doesn't throw
- return;
-
- test_insert_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, InputIter<charT>(0, 0, 0), tcase);
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
- // there is no need to call test_insert_range
- // for other iterators in this case
- if (0 == tcase.arg)
- return;
-
- test_insert_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, ConstFwdIter<charT>(0, 0, 0), tcase);
-
- test_insert_range (wstr, wstr_len, warg, warg_len, res_len, (Traits*)0,
- (Allocator*)0, ConstBidirIter<charT>(0, 0, 0), tcase);
-
- test_insert_range (wstr, wstr_len, warg, warg_len, res_len,
- (Traits*)0, (Allocator*)0,
- ConstRandomAccessIter<charT>(0, 0, 0), tcase);
-}
-
-/**************************************************************************/
+ InsertRangeOverload () { }
-template <class charT, class Traits, class Allocator>
-void test_insert (charT, Traits*, Allocator*,
- const StringFunc &func,
- const StringTestCase &tcase)
-{
- typedef std::basic_string <charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
- typedef typename UserTraits<charT>::MemFun UTMemFun;
+ virtual String&
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
- static const std::size_t BUFSIZE = 256;
+ const StringTestCase &tcase = tdata.tcase_;
- static charT wstr_buf [BUFSIZE];
- static charT warg_buf [BUFSIZE];
+ // create a pair of iterators into the string object being modified
+ const StringIter first1 (str.begin () + tdata.off1_);
- std::size_t str_len = sizeof wstr_buf / sizeof *wstr_buf;
- std::size_t arg_len = sizeof warg_buf / sizeof *warg_buf;
+ const std::size_t off = tdata.off2_;
+ const std::size_t ext = tdata.ext2_;
- charT* wstr = rw_expand (wstr_buf, tcase.str, tcase.str_len, &str_len);
- charT* warg = rw_expand (warg_buf, tcase.arg, tcase.arg_len, &arg_len);
+ if (0 == tcase.arg) {
+ // exercise self-referential modification (i.e., replacing
+ // a range of elements with a subrange of its own elements)
- static charT wres_buf [BUFSIZE];
- std::size_t res_len = sizeof wres_buf / sizeof *wres_buf;
- charT* wres = rw_expand (wres_buf, tcase.res, tcase.nres, &res_len);
+ const Iterator first2 (begin (str, (Iterator*)0) + off);
+ const Iterator last2 (first2 + ext);
- // special processing for insert_range to exercise all iterators
- if (Insert (iter_range) == func.which_) {
- test_insert_range (wstr, str_len, warg, arg_len,
- res_len, (Traits*)0, (Allocator*)0, tcase);
- if (wstr != wstr_buf)
- delete[] wstr;
+ str.insert (first1, first2, last2);
+ return str;
+ }
- if (warg != warg_buf)
- delete[] warg;
+ String str_arg (tdata.arg_, tdata.arglen_);
- if (wres != wres_buf)
- delete[] wres;
+ const Iterator first2 (begin (str_arg, (Iterator*)0) + off);
+ const Iterator last2 (first2 + ext);
- return;
+ str.insert (first1, first2, last2);
+ return str;
}
+};
- /* const */ String str (wstr, str_len);
- const String arg (warg, arg_len);
+/**************************************************************************/
- if (wstr != wstr_buf)
- delete[] wstr;
+template <class charT, class Traits, class Allocator>
+void test_insert (charT*, Traits*, Allocator*, const RangeBase<
+ std::basic_string <charT, Traits, Allocator> > &rng,
+ const StringTestCaseData<charT> &tdata)
+{
+ typedef std::basic_string <charT, Traits, Allocator> String;
+ typedef typename String::iterator StringIter;
+ typedef typename UserTraits<charT>::MemFun TraitsFunc;
- if (warg != warg_buf)
- delete[] warg;
+ const StringFunc &func = tdata.func_;
+ const StringTestCase &tcase = tdata.tcase_;
- wstr = 0;
- warg = 0;
+ // construct the string object to be modified
+ // and the (possibly unused) argument string
+ /* const */ String str (tdata.str_, tdata.strlen_);
+ const String arg (tdata.arg_, tdata.arglen_);
// save the state of the string object before the call
// to detect wxception safety violations (changes to
@@ -713,7 +655,7 @@
// compute the offset and the extent (the number of elements)
// of the first range into the string object being modified
- const std::size_t size1 = str_len;
+ const std::size_t size1 = tdata.strlen_;
const std::size_t off1 =
std::size_t (tcase.off) < size1 ? std::size_t (tcase.off) : size1;
@@ -726,7 +668,7 @@
std::size_t* const rg_calls = rw_get_call_counters ((Traits*)0, (charT*)0);
if (rg_calls)
- total_length_calls = rg_calls [UTMemFun::length];
+ total_length_calls = rg_calls [TraitsFunc::length];
rwt_free_store* const pst = rwt_get_free_store (0);
SharedAlloc* const pal = SharedAlloc::instance ();
@@ -768,12 +710,8 @@
#else // if defined (_RWSTD_NO_EXCEPTIONS)
- if (tcase.bthrow) {
- if (wres != wres_buf)
- delete[] wres;
-
+ if (tcase.bthrow)
return;
- }
#endif // _RWSTD_NO_EXCEPTIONS
@@ -789,7 +727,7 @@
case Insert (size_cptr):
ret_ptr = &str.insert (tcase.off, arg_ptr);
if (rg_calls)
- n_length_calls = rg_calls [UTMemFun::length];
+ n_length_calls = rg_calls [TraitsFunc::length];
break;
case Insert (size_cstr):
@@ -823,6 +761,11 @@
break;
}
+ case Insert (iter_range): {
+ ret_ptr = &rng (str, tdata); // function returns void
+ break;
+ }
+
default:
RW_ASSERT (!"logic error: unknown insert overload");
return;
@@ -841,27 +784,28 @@
exp_off, ret_off,
Insert (iter_val) != func.which_, ret_off);
+ // for convenience
+ static const int cwidth = sizeof (charT);
+
// verfiy that strings length are equal
- rw_assert (res_len == str.size (), 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s} with length "
+ rw_assert (tdata.reslen_ == str.size (), 0, tcase.line,
+ "line %d. %{$FUNCALL} expected %{/*.*Gs} with length "
"%zu, got %{/*.*Gs} with length %zu", __LINE__,
- int (tcase.nres), tcase.res, res_len,
- int (sizeof (charT)), int (str.size ()),
- str.c_str (), str.size ());
+ cwidth, int (tdata.reslen_), tdata.res_, tdata.reslen_,
+ cwidth, int (str.size ()), str.c_str (), str.size ());
- if (res_len == str.size ()) {
+ if (tdata.reslen_ == str.size ()) {
// if the result length matches the expected length
// (and only then), also verify that the modified
// string matches the expected result
const std::size_t match =
rw_match (tcase.res, str.c_str(), tcase.nres);
- rw_assert (match == res_len, 0, tcase.line,
- "line %d. %{$FUNCALL} expected %{#*s}, "
+ rw_assert (match == tdata.reslen_, 0, tcase.line,
+ "line %d. %{$FUNCALL} expected %{/*.*Gs}, "
"got %{/*.*Gs}, difference at offset %zu",
- __LINE__, int (tcase.nres), tcase.res,
- int (sizeof (charT)), int (str.size ()),
- str.c_str (), match);
+ __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+ cwidth, int (str.size ()), str.c_str (), match);
}
// verify that Traits::length was used
@@ -954,23 +898,91 @@
#endif // _RWSTD_NO_REPLACEABLE_NEW_DELETE
- rw_assert (expect_throws == throw_count, 0, tcase.line,
- "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
- "while changing capacity from %zu to %zu, got %zu",
- __LINE__, exceptions [3],
- str_state.capacity_, str.capacity (), throw_count);
+ // verify number of exceptions thrown
+ // for range version the allocation may take place several times
+ if (Insert (iter_range) != func.which_)
+ rw_assert (expect_throws == throw_count, 0, tcase.line,
+ "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
+ "while changing capacity from %zu to %zu, got %zu",
+ __LINE__, exceptions [3],
+ str_state.capacity_, str.capacity (), throw_count);
+ else
+ rw_assert (expect_throws <= throw_count, 0, tcase.line,
+ "line %d: %{$FUNCALL}: expected at least 1 %s exception "
+ "while changing capacity from %zu to %zu, got %zu",
+ __LINE__, exceptions [3],
+ str_state.capacity_, str.capacity (), throw_count);
// disable bad_alloc exceptions
*pst->throw_at_calls_ [0] = 0;
pal->throw_at_calls_ [pal->m_allocate] = 0;
+}
+
+/**************************************************************************/
- if (wres != wres_buf)
- delete[] wres;
+template <class charT, class Traits, class Allocator>
+void test_insert (charT*, Traits*, Allocator*,
+ const StringTestCaseData<charT> &tdata)
+{
+ typedef std::basic_string<charT, Traits, Allocator> String;
+
+ if (tdata.func_.which_ == Insert (iter_range)) {
+
+ switch (tdata.func_.iter_id_) {
+
+ // exercise possible overloads of the member function template
+ // on common RandomAccessIterator types
+#undef TEST
+#define TEST(Iterator) do { \
+ typedef typename String::Iterator Iter; \
+ static const \
+ InsertRangeOverload<String, Iter> rep; \
+ test_insert ((charT*)0, (Traits*)0, (Allocator*)0, rep, tdata); \
+ } while (0)
+
+ case StringIds::Pointer: TEST (pointer); break;
+ case StringIds::ConstPointer: TEST (const_pointer); break;
+ case StringIds::Iterator: TEST (iterator); break;
+ case StringIds::ConstIterator: TEST (const_iterator); break;
+
+ // disabled for now
+ case StringIds::ReverseIterator:
+ // TEST (reverse_iterator);
+ break;
+
+ case StringIds::ConstReverseIterator:
+ // TEST (const_reverse_iterator);
+ break;
+
+ // exercise specializations of the member function template
+ // on the required iterator categories
+#undef TEST
+#define TEST(Iterator) do { \
+ typedef Iterator<charT> Iter; \
+ static const \
+ InsertRange<String, Iter> rep; \
+ test_insert ((charT*)0, (Traits*)0, (Allocator*)0, rep, tdata); \
+ } while (0)
+
+ case StringIds::Input: TEST (InputIter); break;
+ case StringIds::Forward: TEST (ConstFwdIter); break;
+ case StringIds::Bidir: TEST (ConstBidirIter); break;
+ case StringIds::Random: TEST (ConstRandomAccessIter); break;
+
+ default:
+ rw_error (0, 0, __LINE__, "bad iterator id");
+ }
+ }
+ else {
+ // exercise ordinary overloads of the member function
+ static const RangeBase<String> rep;
+ test_insert ((charT*)0, (Traits*)0, (Allocator*)0, rep, tdata);
+ }
}
/**************************************************************************/
-DEFINE_STRING_TEST_DISPATCH (test_insert);
+DEFINE_STRING_TEST_FUNCTIONS (test_insert);
int main (int argc, char** argv)
{
@@ -995,7 +1007,10 @@
const std::size_t test_count = sizeof tests / sizeof *tests;
- return rw_run_string_test (argc, argv, __FILE__,
- "lib.string.insert",
- test_insert, tests, test_count);
+ const int status =
+ rw_run_string_test (argc, argv, __FILE__,
+ "lib.string.insert",
+ test_insert_func_array, tests, test_count);
+
+ return status;
}
Modified: incubator/stdcxx/trunk/tests/strings/21.string.replace.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/strings/21.string.replace.cpp?rev=412750&r1=412749&r2=412750&view=diff
==============================================================================
--- incubator/stdcxx/trunk/tests/strings/21.string.replace.cpp (original)
+++ incubator/stdcxx/trunk/tests/strings/21.string.replace.cpp Thu Jun 8 06:41:03 2006
@@ -716,35 +716,19 @@
/**************************************************************************/
-template <class charT, class Traits, class Allocator>
-struct ReplaceBase {
- typedef std::basic_string<charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
-
- ReplaceBase () { }
-
- virtual ~ReplaceBase () { /* silence warnings */ }
-
- virtual String&
- operator() (String &str, const StringTestCaseData<charT>&) const {
- RW_ASSERT (!"logic error: should be never called");
- return str;
- }
-};
-
-/**************************************************************************/
-
// invokes specializations of the member function template
// on the required iterator categories
-template <class charT, class Traits, class Allocator, class Iterator>
-struct ReplaceRange: ReplaceBase<charT, Traits, Allocator> {
- typedef std::basic_string<charT, Traits, Allocator> String;
- typedef typename String::iterator StringIter;
+template <class String, class Iterator>
+struct ReplaceRange: RangeBase<String> {
+
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
ReplaceRange () { }
virtual String&
- operator() (String &str, const StringTestCaseData<charT>& tdata) const {
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
const StringTestCase &tcase = tdata.tcase_;
@@ -757,10 +741,10 @@
// when (0 == tcase.arg) exercise self-referential modification
// (i.e., replacing a range of elements with a subrange of its
// own elements)
- const charT* const beg =
+ const StringChar* const beg =
(tcase.arg ? tdata.arg_ : cstr.data ()) + tdata.off2_;
- const charT* const end = beg + tdata.ext2_;
+ const StringChar* const end = beg + tdata.ext2_;
const Iterator first2 (beg, beg, end);
const Iterator last2 (end, beg, end);
@@ -769,63 +753,20 @@
}
};
-/**************************************************************************/
// invokes possible overloads of the member function template
// on common RandomAccessIterator types
-template <class charT, class Traits, class Allocator, class Iterator>
-struct ReplaceRangeOverload: ReplaceBase<charT, Traits, Allocator>
+template <class String, class Iterator>
+struct ReplaceRangeOverload: RangeBase<String>
{
- typedef std::basic_string<charT, Traits, Allocator> String;
- typedef typename String::pointer StringPtr;
- typedef typename String::const_pointer StringConstPtr;
- typedef typename String::iterator StringIter;
- typedef typename String::const_iterator StringConstIter;
- typedef typename String::reverse_iterator StringRevIter;
- typedef typename String::const_reverse_iterator StringConstRevIter;
+ typedef typename String::iterator StringIter;
+ typedef typename String::value_type StringChar;
ReplaceRangeOverload () { }
- static StringPtr
- begin (String &str, StringPtr*) {
- return _RWSTD_CONST_CAST (StringPtr, str.data ());
- }
-
- static StringConstPtr
- begin (const String &str, StringConstPtr*) {
- return str.data ();
- }
-
-#ifndef _RWSTD_NO_DEBUG_ITER
-
- // when debugging iterators are enabled string::iterator and
- // string::pointer are distinct types; otherwise they are the
- // same type
-
- static StringIter
- begin (String &str, StringIter*) {
- return str.begin ();
- }
-
- static StringConstIter
- begin (const String &str, StringConstIter*) {
- return str.begin ();
- }
-
-#endif // _RWSTD_NO_DEBUG_ITER
-
- static StringRevIter
- begin (String &str, StringRevIter*) {
- return str.rbegin ();
- }
-
- static StringConstRevIter
- begin (const String &str, StringConstRevIter*) {
- return str.rbegin ();
- }
-
virtual String&
- operator() (String &str, const StringTestCaseData<charT>& tdata) const {
+ operator() (String &str,
+ const StringTestCaseData<StringChar>& tdata) const {
const StringTestCase &tcase = tdata.tcase_;
@@ -858,9 +799,9 @@
/**************************************************************************/
template <class charT, class Traits, class Allocator>
-void test_replace (charT*, Traits*, Allocator*,
- const ReplaceBase<charT, Traits, Allocator> &rep,
- const StringTestCaseData<charT> &tdata)
+void test_replace (charT*, Traits*, Allocator*, const RangeBase<
+ std::basic_string <charT, Traits, Allocator> > &rep,
+ const StringTestCaseData<charT> &tdata)
{
typedef std::basic_string <charT, Traits, Allocator> String;
typedef typename String::iterator StringIter;
@@ -1161,9 +1102,9 @@
void test_replace (charT*, Traits*, Allocator*,
const StringTestCaseData<charT> &tdata)
{
- if (tdata.func_.which_ == Replace (iter_iter_range)) {
+ typedef std::basic_string<charT, Traits, Allocator> String;
- typedef std::basic_string<charT, Traits, Allocator> String;
+ if (tdata.func_.which_ == Replace (iter_iter_range)) {
switch (tdata.func_.iter_id_) {
@@ -1173,7 +1114,7 @@
#define TEST(Iterator) do { \
typedef typename String::Iterator Iter; \
static const \
- ReplaceRangeOverload<charT, Traits, Allocator, Iter> rep; \
+ ReplaceRangeOverload<String, Iter> rep; \
test_replace ((charT*)0, (Traits*)0, (Allocator*)0, rep, tdata); \
} while (0)
@@ -1197,7 +1138,7 @@
#define TEST(Iterator) do { \
typedef Iterator<charT> Iter; \
static const \
- ReplaceRange<charT, Traits, Allocator, Iter> rep; \
+ ReplaceRange<String, Iter> rep; \
test_replace ((charT*)0, (Traits*)0, (Allocator*)0, rep, tdata); \
} while (0)
@@ -1212,7 +1153,7 @@
}
else {
// exercise ordinary overloads of the member function
- static const ReplaceBase<charT, Traits, Allocator> rep;
+ static const RangeBase<String> rep;
test_replace ((charT*)0, (Traits*)0, (Allocator*)0, rep, tdata);
}
}