first commit
This commit is contained in:
294
extern/stdcxx/4.2.1/tests/algorithms/25.adjacent.find.cpp
vendored
Normal file
294
extern/stdcxx/4.2.1/tests/algorithms/25.adjacent.find.cpp
vendored
Normal file
@@ -0,0 +1,294 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.adjacent.find.cpp - test exercising lib.alg.adjacent.find
|
||||
*
|
||||
* $Id: 25.adjacent.find.cpp 510071 2007-02-21 15:58:53Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 2004-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for adjacent_find()
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h>
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// used to initialize an array of objects of type UserClass
|
||||
static const char *xinit_begin;
|
||||
|
||||
int xinit ()
|
||||
{
|
||||
typedef unsigned char UChar;
|
||||
|
||||
static const char *cur = 0;
|
||||
|
||||
if (!cur || !*cur)
|
||||
cur = xinit_begin;
|
||||
|
||||
return UChar (*cur++);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class U>
|
||||
struct EqualityPredicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class
|
||||
// from being default constructible
|
||||
EqualityPredicate (T* /* dummy */, U* /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
class ConvertibleToBool {
|
||||
bool result_;
|
||||
public:
|
||||
ConvertibleToBool (bool res): result_ (res) { /* empty */ }
|
||||
operator bool() const { return result_; }
|
||||
};
|
||||
|
||||
ConvertibleToBool operator() (const T &x, const U &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return x == y;
|
||||
}
|
||||
};
|
||||
|
||||
template <class T, class U>
|
||||
std::size_t EqualityPredicate<T, U>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::adjacent_find()
|
||||
template <class ForwardIterator, class T>
|
||||
void do_test (int line, // line number of test case
|
||||
const char *src, // source sequence
|
||||
std::size_t resoff, // offset of result
|
||||
ForwardIterator dummy_iter,
|
||||
const T*,
|
||||
const char* predname)
|
||||
{
|
||||
static const char* const itname = type_name (dummy_iter, (T*)0);
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
if (std::size_t (-1) == resoff)
|
||||
resoff = nsrc;
|
||||
|
||||
// have the UserClass default ctor initialize objects from `src'
|
||||
xinit_begin = src;
|
||||
UserClass::gen_ = xinit;
|
||||
|
||||
UserClass* const xsrc = new UserClass [nsrc];
|
||||
|
||||
const ForwardIterator first =
|
||||
make_iter (xsrc, xsrc, xsrc + nsrc, dummy_iter);
|
||||
|
||||
const ForwardIterator last =
|
||||
make_iter (xsrc + nsrc, xsrc, xsrc + nsrc, dummy_iter);
|
||||
|
||||
// reset predicate counters
|
||||
UserClass::n_total_op_eq_ = 0;
|
||||
EqualityPredicate<T, T>::funcalls_ = 0;
|
||||
|
||||
// construct a predicate object
|
||||
const EqualityPredicate<T, T> pred (0, 0);
|
||||
|
||||
const ForwardIterator res = predname ?
|
||||
std::adjacent_find (first, last, pred)
|
||||
: std::adjacent_find (first, last);
|
||||
|
||||
// silence a bogus EDG eccp remark #550-D:
|
||||
// variable "res" was set but never used
|
||||
_RWSTD_UNUSED (res);
|
||||
|
||||
const std::size_t n_total_pred = predname ?
|
||||
EqualityPredicate<T, T>::funcalls_
|
||||
: UserClass::n_total_op_eq_;
|
||||
|
||||
// verify that the returned iterator is set as expected
|
||||
int success = res.cur_ == first.cur_ + resoff;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: adjacent_find<%s>(it = \"%s\", ...)"
|
||||
" == (it + %zu), got (it + %td)",
|
||||
__LINE__, itname, src,
|
||||
resoff, res.cur_ - first.cur_);
|
||||
|
||||
// verify the number of applications of the predicate (lwg issue 240):
|
||||
// Complexity: For a nonempty range, exactly
|
||||
// min((i - first) + 1, (last - first) - 1)
|
||||
// applications of the corresponding predicate, where i is
|
||||
// adjacent_find's return value.
|
||||
|
||||
// compute the expected number of invocations of the predicate
|
||||
std::size_t n_expect_pred = 0;
|
||||
|
||||
if (nsrc) {
|
||||
// test iterators are guaranteed to be in range
|
||||
_RWSTD_ASSERT (first.cur_ <= res.cur_ && res.cur_ <= last.cur_);
|
||||
|
||||
n_expect_pred = std::size_t (res.cur_ - first.cur_) + 1;
|
||||
const std::size_t tmp = std::size_t (last.cur_ - first.cur_) - 1;
|
||||
if (tmp < n_expect_pred)
|
||||
n_expect_pred = tmp;
|
||||
}
|
||||
|
||||
success = std::size_t (n_expect_pred) == n_total_pred;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: adjacent_find<%s>(\"%s\", ...) "
|
||||
"invoked %s %zu times, expected %td",
|
||||
__LINE__, itname, src,
|
||||
predname ? predname : "operator==()",
|
||||
n_total_pred, n_expect_pred);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator, class T>
|
||||
void run_tests (ForwardIterator dummy_iter, const T*, const char* predname)
|
||||
{
|
||||
static const char* const itname = type_name (dummy_iter, (T*)0);
|
||||
|
||||
rw_info (0, 0, 0, "std::adjacent_find (%s, %1$s%{?}, %s%{;})",
|
||||
itname, 0 != predname, predname);
|
||||
|
||||
#define TEST(src, off) \
|
||||
do_test (__LINE__, src, std::size_t (off), dummy_iter, \
|
||||
(UserClass*)0, predname)
|
||||
|
||||
// +------------------ subject sequence
|
||||
// | +-- offset of returned iterator,
|
||||
// | | -1 denotes the end of sequence
|
||||
// v v
|
||||
TEST ("", -1);
|
||||
TEST ("a", -1);
|
||||
TEST ("ab", -1);
|
||||
TEST ("abc", -1);
|
||||
TEST ("abcd", -1);
|
||||
TEST ("abcde", -1);
|
||||
TEST ("abcdef", -1);
|
||||
TEST ("abcdefg", -1);
|
||||
TEST ("abcdefgh", -1);
|
||||
TEST ("abcdefghi", -1);
|
||||
TEST ("abcdefghij", -1);
|
||||
TEST ("abcdefghijk", -1);
|
||||
|
||||
TEST ("aabcdefghij", 0);
|
||||
TEST ("abbcdefghij", 1);
|
||||
TEST ("abccdefghij", 2);
|
||||
TEST ("abcddefghij", 3);
|
||||
TEST ("abcdeefghij", 4);
|
||||
TEST ("abcdeffghij", 5);
|
||||
TEST ("abcdefgghij", 6);
|
||||
TEST ("abcdefghhij", 7);
|
||||
TEST ("abcdefghiij", 8);
|
||||
TEST ("abcdefghijj", 9);
|
||||
|
||||
TEST ("aaabcdefghi", 0);
|
||||
TEST ("abbbcdefghi", 1);
|
||||
TEST ("abcccdefghi", 2);
|
||||
TEST ("abcdddefghi", 3);
|
||||
TEST ("abcdeeefghi", 4);
|
||||
TEST ("abcdefffghi", 5);
|
||||
TEST ("abcdefggghi", 6);
|
||||
TEST ("abcdefghhhi", 7);
|
||||
TEST ("abcdefghiii", 8);
|
||||
TEST ("abcdefghijjj", 9);
|
||||
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
static
|
||||
void test_adjacent_find (const char* predname)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s%{?}, class %s%{;}> "
|
||||
"%1$s std::adjacent_find (%1$s, %1$s%{?}, %3$s%{;})",
|
||||
"ForwardIterator", 0 != predname, "BinaryPredicate",
|
||||
0 != predname);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (FwdIter<UserClass>(), (UserClass*)0, predname);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (BidirIter<UserClass>(), (UserClass*)0, predname);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (RandomAccessIter<UserClass>(), (UserClass*)0, predname);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_adjacent_find (0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "Predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_adjacent_find ("EqualityPredicate<UserClass, UserClass>");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.adjacent.find",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#"
|
||||
"|-no-Predicate#",
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
331
extern/stdcxx/4.2.1/tests/algorithms/25.binary.search.cpp
vendored
Normal file
331
extern/stdcxx/4.2.1/tests/algorithms/25.binary.search.cpp
vendored
Normal file
@@ -0,0 +1,331 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.binary.search.cpp - test exercising 25.3.4 [lib.binary.search]
|
||||
*
|
||||
* $Id: 25.binary.search.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <rw/_config.h>
|
||||
|
||||
#if defined (__IBMCPP__) && !defined (_RWSTD_NO_IMPLICIT_INCLUSION)
|
||||
// disable implicit inclusion to work around a limitation
|
||||
// of IBM VisualAge 5.0 (see PR #26959)
|
||||
# define _RWSTD_NO_IMPLICIT_INCLUSION
|
||||
#endif
|
||||
|
||||
#include <algorithm> // for binary_search()
|
||||
#include <cstring> // for strlen()
|
||||
|
||||
#include <alg_test.h> // for iterators
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test(), ...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// meets requirements listed at 25.3, p2
|
||||
template <class T>
|
||||
struct compare {
|
||||
bool operator() (const T &a, const T &b) const {
|
||||
_RWSTD_UNUSED (a);
|
||||
_RWSTD_UNUSED (b);
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
bool
|
||||
binary_search (FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
const lt_comp<assign<base<cpy_ctor> > >&);
|
||||
|
||||
template
|
||||
bool
|
||||
binary_search (FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
const lt_comp<assign<base<cpy_ctor> > >&,
|
||||
compare<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// distinct and not Less-Than-Comparable with class T (except as
|
||||
// defined below) to detect unwarranted assumptions made by the
|
||||
// implementation of the algorithms
|
||||
struct Y
|
||||
{
|
||||
UserClass xval_;
|
||||
|
||||
// not Default-Constructible
|
||||
Y (int /* dummy */, int /*dummy */): xval_ () { }
|
||||
|
||||
// CopyConstructible
|
||||
Y (const Y &rhs): xval_ (rhs.xval_) { }
|
||||
|
||||
private:
|
||||
|
||||
void operator=(Y&); // not Assignable
|
||||
};
|
||||
|
||||
|
||||
inline bool
|
||||
operator< (const UserClass &lhs, const Y &rhs)
|
||||
{
|
||||
return lhs < rhs.xval_;
|
||||
}
|
||||
|
||||
inline bool
|
||||
operator< (const Y &lhs, const UserClass &rhs)
|
||||
{
|
||||
return lhs.xval_ < rhs;
|
||||
}
|
||||
|
||||
// predicate used as the Compare argument to upper_bound()
|
||||
struct LessThan
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
LessThan (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
bool operator() (const UserClass &lhs, const Y &rhs) {
|
||||
++funcalls_;
|
||||
return lhs < rhs.xval_;
|
||||
}
|
||||
|
||||
bool operator() (const Y &lhs, const UserClass &rhs) {
|
||||
++funcalls_;
|
||||
return lhs.xval_ < rhs;
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (LessThan&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t LessThan::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator>
|
||||
void test_binary_search (int line,
|
||||
const char *src_str,
|
||||
char val_char,
|
||||
bool exp_res,
|
||||
std::size_t ncomp,
|
||||
const ForwardIterator &it,
|
||||
const T*,
|
||||
bool predicate)
|
||||
{
|
||||
RW_ASSERT (0 != src_str);
|
||||
|
||||
const char* const tname = "UserClass";
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const funname = predicate ? "LessThan" : "operator<()";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src_str);
|
||||
T* const xsrc = T::from_char (src_str, nsrc);
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
// construct the source range to pass to the algorithm
|
||||
const ForwardIterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const ForwardIterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
// construct the object to pass to the algorithm
|
||||
// the type of the object is distinct from the iterator's value_type
|
||||
// to detect unwarranted assumptions made by the implementation
|
||||
Y value (0, 0 /* dummy arguments */);
|
||||
value.xval_.data_.val_ = val_char;
|
||||
|
||||
// construct the Compare function object to pass to the algorithm
|
||||
// when `predicate' is true
|
||||
const LessThan comp (0, 0 /* dummy arguments */);
|
||||
|
||||
// reset the counter of invocations of T::operator<()
|
||||
T::n_total_op_lt_ = 0;
|
||||
|
||||
// invoke the appropriate form of the algorithm, storing
|
||||
// the resturned value
|
||||
const bool result = predicate
|
||||
? std::binary_search (first, last, value, comp)
|
||||
: std::binary_search (first, last, value);
|
||||
|
||||
// silence bogus EDG eccp 3.6 remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (result);
|
||||
|
||||
rw_assert (result == exp_res, 0, line,
|
||||
"binary_search <%s, const %s&%{?}, %s%{;}> (\"%s\", %#c, ...) "
|
||||
"expected %s, got %s",
|
||||
itname, tname, predicate, funname, src_str, val_char,
|
||||
exp_res ? "true" : "false", result ? "true" : "false");
|
||||
|
||||
// verify complexity
|
||||
const std::size_t n_ops = predicate
|
||||
? LessThan::funcalls_ : T::n_total_op_lt_;
|
||||
|
||||
rw_assert (n_ops <= ncomp, 0, line,
|
||||
"binary_search <%s, const %s&%{?}, %s%{;}> (\"%s\", %#c, ...) "
|
||||
"complexity: invoked %4$s at most %zu times, got %zu",
|
||||
itname, tname, predicate, funname, src_str, val_char,
|
||||
ncomp, n_ops);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator>
|
||||
void test_binary_search (const ForwardIterator &it,
|
||||
const T*,
|
||||
bool predicate)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const funname = predicate ? "LessThan" : "operator<()";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::binary_search (%s, %1$s, const UserClass&%{?}, %s%{;})",
|
||||
itname, predicate, funname);
|
||||
|
||||
#define TEST(str, val, res, comp) \
|
||||
test_binary_search (__LINE__, str, val, res, std::size_t (comp), \
|
||||
it, (T*)0, predicate)
|
||||
|
||||
// +--------------- source sequence
|
||||
// | +--------- value argument
|
||||
// | | +----- expected result: true/false
|
||||
// | | | +-- complexity: at most (log(last - first) + 2)
|
||||
// | | | | comparisons (or applications of the predicate)
|
||||
// | | | |
|
||||
// V V V V
|
||||
TEST ("", 'a', false, 0);
|
||||
TEST ("a", 'a', true, 2);
|
||||
TEST ("a", 'b', false, 2);
|
||||
TEST ("b", 'a', false, 2);
|
||||
|
||||
TEST ("aa", 'a', true, 3);
|
||||
TEST ("ab", 'a', true, 3);
|
||||
TEST ("ab", 'b', true, 3);
|
||||
TEST ("bb", 'a', false, 3);
|
||||
|
||||
TEST ("abcdefghij", 'a', true, 6);
|
||||
TEST ("abcdefghij", 'c', true, 6);
|
||||
TEST ("abcdefghij", 'f', true, 6);
|
||||
TEST ("abcdefghij", 'h', true, 6);
|
||||
TEST ("abcdefghij", 'j', true, 6);
|
||||
TEST ("aacceeggii", 'c', true, 6);
|
||||
TEST ("aacceeggii", 'g', true, 6);
|
||||
TEST ("aacceeggii", 'b', false, 6);
|
||||
TEST ("aacceeggii", 'f', false, 6);
|
||||
TEST ("aacceeggii", 'j', false, 6);
|
||||
TEST ("cccceeggii", 'a', false, 6);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_binary_search (const T*,
|
||||
bool predicate)
|
||||
{
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0, "template <class %s, class %s%{?}, class %s%{;}> "
|
||||
"bool std::binary_search (%1$s, %1$s, const %2$s&%{?}, %s%{;})",
|
||||
"ForwardIterator", "UserClass", predicate, "Compare", predicate,
|
||||
"Compare");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_binary_search (fwd_iter, (T*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_binary_search (bidir_iter, (T*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_binary_search (rand_iter, (T*)0, predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_binary_search ((UserClass*)0, false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"test of the Predicate form of std::binary_search disabled");
|
||||
}
|
||||
else {
|
||||
test_binary_search ((UserClass*)0, true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.binary.search",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-Predicate# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
408
extern/stdcxx/4.2.1/tests/algorithms/25.copy.cpp
vendored
Normal file
408
extern/stdcxx/4.2.1/tests/algorithms/25.copy.cpp
vendored
Normal file
@@ -0,0 +1,408 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.copy.cpp - test exercising 25.2.1 [lib.alg.copy]
|
||||
*
|
||||
* $Id: 25.copy.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for copy
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<assign<base<> > >
|
||||
copy (InputIter<const_cvt<base<>, assign<base<> > > >,
|
||||
InputIter<const_cvt<base<>, assign<base<> > > >,
|
||||
OutputIter<assign<base<> > >);
|
||||
|
||||
template
|
||||
BidirIter<assign<base<> > >
|
||||
copy_backward (BidirIter<const_cvt<base<>, assign<base<> > > >,
|
||||
BidirIter<const_cvt<base<>, assign<base<> > > >,
|
||||
BidirIter<assign <base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::copy()
|
||||
template <class InputIterator, class OutputIterator, class T>
|
||||
void test_copy (std::size_t N,
|
||||
const InputIterator &input_iter,
|
||||
const OutputIterator &output_iter,
|
||||
const T* )
|
||||
{
|
||||
static const char* const it1name = type_name (input_iter, (T*) 0);
|
||||
static const char* const it2name = type_name (output_iter, (T*) 0);
|
||||
|
||||
rw_info (0, 0, 0, "std::copy (%s, %1$s, %s)", it1name, it2name);
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
// create separate buffers for src and dst to ensure 25.2.1, p3
|
||||
T* const src = new T [N];
|
||||
T* const dst = new T [N];
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
T* const src_end = src + i + 1;
|
||||
T* const dst_end = dst + i + 1;
|
||||
|
||||
// exercise 25.2.1 - std::copy()
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
const InputIterator begin =
|
||||
make_iter (src, src, src_end, input_iter);
|
||||
|
||||
const InputIterator end =
|
||||
make_iter (src_end, src_end, src_end, input_iter);
|
||||
|
||||
const OutputIterator dest =
|
||||
make_iter (dst, dst, dst_end, output_iter);
|
||||
|
||||
const OutputIterator result =
|
||||
std::copy (begin, end, dest);
|
||||
|
||||
T* const resptr = result.cur_;
|
||||
|
||||
// verify 25.2.1, p2
|
||||
bool success = resptr == dst_end;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. copy(%p, %p, %p) == %p, got %p",
|
||||
i, src, src_end, dst, dst_end, resptr);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// check that algjrithm works correctly
|
||||
std::size_t j = 0;
|
||||
for (; j != i + 1; ++j) {
|
||||
success = src[j].data_.val_ == dst[j].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. copy(%p, %p, %p) mismatch at "
|
||||
"offset %zu: expected %d, got %d: (%p, %p, %zu)",
|
||||
i, src, src_end, dst,
|
||||
j, src[j].data_.val_, dst[j].data_.val_,
|
||||
dst, dst_end, j);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// verify 25.2.1, p4
|
||||
success = T::n_total_op_assign_ - last_n_op_assign == i + 1;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. copy(%p, %p, %p) complexity: ",
|
||||
"%zu != %zu", i + 1, src, src_end, dst,
|
||||
T::n_total_op_assign_ - last_n_op_assign, i + 1);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
delete[] src;
|
||||
delete[] dst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::copy_backward()
|
||||
template <class BidirIterator1, class BidirIterator2, class T>
|
||||
void test_copy_backward (std::size_t N,
|
||||
const BidirIterator1 &bidir_iter1,
|
||||
const BidirIterator2 &bidir_iter2,
|
||||
const T*)
|
||||
{
|
||||
static const char* const it1name = type_name (bidir_iter1, (T*) 0);
|
||||
static const char* const it2name = type_name (bidir_iter2, (T*) 0);
|
||||
|
||||
rw_info (0, 0, 0, "std::copy_backward (%s, %1$s, %s)", it1name, it2name);
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
// create separate buffers for src and dst to ensure 25.2.1, p3
|
||||
T* const src = new T [N];
|
||||
T* const dst = new T [N];
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
// default-construct a new T at the end of each sequence
|
||||
new (src + i) T ();
|
||||
new (dst + i) T ();
|
||||
|
||||
// exercise 25.2.1 - std::copy_backward()
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
T* const src_end = src + i + 1;
|
||||
T* const dst_end = dst + i + 1;
|
||||
|
||||
const BidirIterator1 begin =
|
||||
make_iter (src, src, src_end, bidir_iter1);
|
||||
|
||||
const BidirIterator1 end =
|
||||
make_iter (src_end, src, src_end, bidir_iter1);
|
||||
|
||||
const BidirIterator2 dest =
|
||||
make_iter (dst_end, dst, dst_end, bidir_iter2);
|
||||
|
||||
const BidirIterator2 result =
|
||||
std::copy_backward (begin, end, dest);
|
||||
|
||||
const T* const resptr = result.cur_;
|
||||
|
||||
// verify 25.2.1, p7
|
||||
bool success = resptr == dst;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. copy_backward(%p, %p, %p) == %p, got %p",
|
||||
i, src, src_end, dst_end, dst, resptr);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// verify 25.2.1, p5
|
||||
std::size_t j = 0;
|
||||
for (; j != i + 1; ++j) {
|
||||
success = src[j].data_.val_ == dst[j].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. copy_backward(%p, %p, %p) mismatch at "
|
||||
"offset %zu: expected %d, got %d: (%p, %p, %zu)",
|
||||
i, src, src_end, dst_end,
|
||||
j, src[j].data_.val_, dst[j].data_.val_,
|
||||
dst, dst_end, j);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// verify 25.2.1, p8
|
||||
success = T::n_total_op_assign_ - last_n_op_assign == i + 1;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. copy_backward(%p, %p, %p) complexity: "
|
||||
"%zu != %zu", i + 1, src, src_end, dst_end,
|
||||
T::n_total_op_assign_ - last_n_op_assign, i + 1);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
delete[] src;
|
||||
delete[] dst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 32; // --nloops
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
template <class InputIterator, class T>
|
||||
void test_copy (const std::size_t N, const InputIterator &dummy, T*)
|
||||
{
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, dummy, OutputIter<UserClass>((UserClass*)0,
|
||||
(UserClass*)0, (UserClass*)0), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, dummy, FwdIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, dummy, BidirIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, dummy, RandomAccessIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_copy (const std::size_t N)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"%2$s std::copy (%1$s, %1$s, %2$s)",
|
||||
"InputIterator", "OutputIterator");
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, InputIter<UserClass>((UserClass*)0, (UserClass*)0,
|
||||
(UserClass*)0), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, FwdIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, BidirIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy (N, RandomAccessIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator, class T>
|
||||
void test_copy_backward (const std::size_t N, const InputIterator &dummy, T*)
|
||||
{
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy_backward (N, dummy, BidirIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy_backward (N, dummy, RandomAccessIter<UserClass>(),
|
||||
(UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_copy_backward (const std::size_t N)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> %2$s "
|
||||
"std::copy_backward (%1$s, %1$s, %2$s)",
|
||||
"BidirectionalIterator1", "BidirectionalIterator2");
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy_backward (N, BidirIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_copy_backward (N, RandomAccessIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
// check that the number of loops is non-negative
|
||||
rw_fatal (-1 < rw_opt_nloops, 0, 0,
|
||||
"number of loops must be non-negative, got %d",
|
||||
rw_opt_nloops);
|
||||
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
test_copy (N);
|
||||
|
||||
test_copy_backward (N);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.copy",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops#"
|
||||
"|-no-InputIterator#"
|
||||
"|-no-OutputIterator#"
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
|
||||
276
extern/stdcxx/4.2.1/tests/algorithms/25.equal.cpp
vendored
Normal file
276
extern/stdcxx/4.2.1/tests/algorithms/25.equal.cpp
vendored
Normal file
@@ -0,0 +1,276 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.equal.cpp - test exercising 25.1.8 [lib.alg.equal]
|
||||
*
|
||||
* $Id: 25.equal.cpp 510071 2007-02-21 15:58:53Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for equal
|
||||
#include <functional> // for equal_to
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
bool
|
||||
equal (InputIter<eq_comp<base<> > >,
|
||||
InputIter<eq_comp<base<> > >,
|
||||
InputIter<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
bool
|
||||
equal (InputIter<eq_comp<base<> > >,
|
||||
InputIter<eq_comp<base<> > >,
|
||||
InputIter<eq_comp<base<> > >,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
|
||||
// exercises std::equal()
|
||||
template <class InputIterator1, class InputIterator2, class T>
|
||||
void test_equal (std::size_t N,
|
||||
const InputIterator1 &it1_dummy,
|
||||
const InputIterator2 &it2_dummy,
|
||||
T*,
|
||||
const char *predicate)
|
||||
{
|
||||
static const char* const it1name = type_name (it1_dummy, (T*)0);
|
||||
static const char* const it2name = type_name (it2_dummy, (T*)0);
|
||||
|
||||
rw_info (0, 0, 0, "std::equal (%s, %1$s, %s%{?}, %s%{;})",
|
||||
it1name, it2name, 0 != predicate, predicate);
|
||||
|
||||
// generate sequential values for each default constructed UserClass
|
||||
// for both lists
|
||||
UserClass::gen_ = gen_seq_2lists;
|
||||
|
||||
// use ::operator new() to prevent default initialization
|
||||
const std::size_t size = N * sizeof (UserClass);
|
||||
UserClass *buf1 = _RWSTD_STATIC_CAST (UserClass*, ::operator new (size));
|
||||
UserClass *buf2 = _RWSTD_STATIC_CAST (UserClass*, ::operator new (size));
|
||||
|
||||
const std::size_t mid_inx = N / 2;
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
// default-construct a new UserClass at the end of the array
|
||||
new (buf1 + i) UserClass ();
|
||||
|
||||
// build a nearly identical array only missing the N/2-th element
|
||||
if (i != mid_inx)
|
||||
new (buf2 + i) UserClass ();
|
||||
}
|
||||
|
||||
new (buf2 + mid_inx) UserClass ();
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
// exercise 25.1.8 - std::equal()
|
||||
std::size_t last_n_op_eq = UserClass::n_total_op_eq_;
|
||||
|
||||
UserClass* const buf1_end = buf1 + i + 1;
|
||||
UserClass* const buf2_end = buf2 + i + 1;
|
||||
|
||||
const InputIterator1 first1 =
|
||||
make_iter (buf1, buf1, buf1_end, it1_dummy);
|
||||
|
||||
const InputIterator1 last1 =
|
||||
make_iter (buf1_end, buf1_end, buf1_end, it1_dummy);
|
||||
|
||||
const InputIterator2 first2 =
|
||||
make_iter (buf2, buf2, buf2_end, it2_dummy);
|
||||
|
||||
bool res;
|
||||
|
||||
if (predicate) {
|
||||
res = std::equal (first1, last1, first2,
|
||||
std::equal_to<UserClass>());
|
||||
}
|
||||
else {
|
||||
res = std::equal (first1, last1, first2);
|
||||
}
|
||||
|
||||
// verify 25.1.8, p1
|
||||
int success = res && i < mid_inx || !res && mid_inx <= i;
|
||||
|
||||
const bool equal_expected = i < mid_inx;
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. equal(%s, %2$s, %s%{?}, %s%{;}) == %d, got %d",
|
||||
i + 1, it1name, it2name,
|
||||
0 != predicate, predicate,
|
||||
equal_expected, res);
|
||||
|
||||
// verify 25.1.8, p2
|
||||
success = UserClass::n_total_op_eq_ - last_n_op_eq <= (N + 1);
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. equal(%s, %2$s, %s%s%{?}, %s%{;}) complexity: "
|
||||
"%zu <= %zu",
|
||||
i + 1, it1name, it2name,
|
||||
0 != predicate, predicate,
|
||||
UserClass::n_total_op_eq_, i + 1);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
::operator delete (buf1);
|
||||
::operator delete (buf2);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
|
||||
template <class InputIterator, class T>
|
||||
void test_equal (const InputIterator &dummy, T*, const char *predicate)
|
||||
{
|
||||
static const std::size_t N = 1024;
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (N, dummy, InputIter<UserClass>((UserClass*)0,
|
||||
(UserClass*)0, (UserClass*)0), (UserClass*)0,
|
||||
predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (N, dummy, FwdIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (N, dummy, BidirIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (N, dummy, RandomAccessIter<UserClass>(), (UserClass*)0,
|
||||
predicate);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_equal (const char *predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"bool std::equal (%1$s, %1$s, %2$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2",
|
||||
0 != predicate, predicate);
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (InputIter<UserClass>((UserClass*)0, (UserClass*)0,
|
||||
(UserClass*)0), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (FwdIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (BidirIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal (RandomAccessIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_equal (0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "Predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal ("std::equal_to<UserClass>");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.equal",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#"
|
||||
"|-no-Predicate",
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
340
extern/stdcxx/4.2.1/tests/algorithms/25.equal.range.cpp
vendored
Normal file
340
extern/stdcxx/4.2.1/tests/algorithms/25.equal.range.cpp
vendored
Normal file
@@ -0,0 +1,340 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.equal.range.cpp - test exercising 25.3.3.3 [lib.equal.range]
|
||||
*
|
||||
* $Id: 25.equal.range.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <rw/_config.h>
|
||||
|
||||
#if defined (__IBMCPP__) && !defined (_RWSTD_NO_IMPLICIT_INCLUSION)
|
||||
// disable implicit inclusion to work around a limitation
|
||||
// of IBM VisualAge 5.0 (see PR #26959)
|
||||
# define _RWSTD_NO_IMPLICIT_INCLUSION
|
||||
#endif
|
||||
|
||||
#include <algorithm> // for equal_range()
|
||||
#include <cstring> // for strlen()
|
||||
|
||||
#include <alg_test.h> // for iterators
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test(), ...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
pair <FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
FwdIter<lt_comp<assign<base<cpy_ctor> > > > >
|
||||
equal_range (FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
const lt_comp<assign<base<cpy_ctor> > >&);
|
||||
|
||||
template
|
||||
pair <FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
FwdIter<lt_comp<assign<base<cpy_ctor> > > > >
|
||||
equal_range (FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
FwdIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
const lt_comp<assign<base<cpy_ctor> > >&,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// distinct and not Less-Than-Comparable with class T (except as
|
||||
// defined below) to detect unwarranted assumptions made by the
|
||||
// implementation of the algorithms
|
||||
struct Y
|
||||
{
|
||||
UserClass xval_;
|
||||
|
||||
// not Default-Constructible
|
||||
Y (char val, int /*dummy */): xval_ () {
|
||||
typedef unsigned char UChar;
|
||||
xval_.data_.val_ = int (UChar (val));
|
||||
}
|
||||
|
||||
// CopyConstructible
|
||||
Y (const Y &rhs): xval_ (rhs.xval_) { }
|
||||
|
||||
private:
|
||||
|
||||
void operator=(Y&); // not Assignable
|
||||
};
|
||||
|
||||
|
||||
inline conv_to_bool
|
||||
operator< (const UserClass &lhs, const Y &rhs)
|
||||
{
|
||||
return conv_to_bool::make (lhs < rhs.xval_);
|
||||
}
|
||||
|
||||
inline conv_to_bool
|
||||
operator< (const Y &lhs, const UserClass &rhs)
|
||||
{
|
||||
return conv_to_bool::make (lhs.xval_ < rhs);
|
||||
}
|
||||
|
||||
// predicate used as the Compare argument to upper_bound()
|
||||
struct LessThan
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
LessThan (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &lhs, const Y &rhs) {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (lhs < rhs.xval_);
|
||||
}
|
||||
|
||||
conv_to_bool operator() (const Y &lhs, const UserClass &rhs) {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (lhs.xval_ < rhs);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (LessThan&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t LessThan::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator>
|
||||
void test_equal_range (int line,
|
||||
const char *src_str,
|
||||
char val_char,
|
||||
std::size_t result_loff,
|
||||
std::size_t result_uoff,
|
||||
std::size_t ncomp,
|
||||
const ForwardIterator &it,
|
||||
const T*,
|
||||
bool predicate)
|
||||
{
|
||||
RW_ASSERT (0 != src_str);
|
||||
|
||||
const char* const tname = "UserClass";
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const funname = predicate ? "LessThan" : "operator<()";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src_str);
|
||||
T* const xsrc = T::from_char (src_str, nsrc + 1);
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
if (nsrc < result_uoff)
|
||||
result_uoff = nsrc;
|
||||
|
||||
// construct the source range to pass to the algorithm
|
||||
const ForwardIterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const ForwardIterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
// construct the object to pass to the algorithm
|
||||
// the type of the object is distinct from the iterator's value_type
|
||||
// to detect unwarranted assumptions made by the implementation of
|
||||
// the algorithm
|
||||
const Y value (val_char, 0 /* dummy */);
|
||||
|
||||
// construct the Compare function object to pass to the algorithm
|
||||
// when `predicate' is true
|
||||
const LessThan comp (0, 0 /* dummy arguments */);
|
||||
|
||||
// reset the counter of invocations of T::operator<()
|
||||
T::n_total_op_lt_ = 0;
|
||||
|
||||
// invoke the appropriate form of the algorithm, storing
|
||||
// the resturned value
|
||||
const std::pair <ForwardIterator, ForwardIterator> result = predicate
|
||||
? std::equal_range (first, last, value, comp)
|
||||
: std::equal_range (first, last, value);
|
||||
|
||||
// silence bogus EDG eccp 3.6 remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (result);
|
||||
|
||||
// verify correctness
|
||||
const std::size_t loff = std::size_t (result.first.cur_ - xsrc);
|
||||
const std::size_t uoff = std::size_t (result.second.cur_ - xsrc);
|
||||
|
||||
rw_assert (loff == result_loff && uoff == result_uoff, 0, line,
|
||||
"equal_range <%s, const %s&%{?}, %s%{;}> (\"%s\", %#c, ...) "
|
||||
"== first + { %zu, %zu }, got first + { %zu, %zu }",
|
||||
itname, tname, predicate, funname, src_str, val_char,
|
||||
loff, uoff, result_loff, result_uoff);
|
||||
|
||||
// verify complexity
|
||||
const std::size_t n_ops = predicate
|
||||
? LessThan::funcalls_ : T::n_total_op_lt_;
|
||||
|
||||
rw_assert (n_ops <= ncomp, 0, line,
|
||||
"equal_range <%s, const %s&%{?}, %s%{;}> (\"%s\", %#c, ...) "
|
||||
"complexity: invoked %4$s at most %zu times, got %zu",
|
||||
itname, tname, predicate, funname, src_str, val_char,
|
||||
ncomp, n_ops);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator>
|
||||
void test_equal_range (const ForwardIterator &it,
|
||||
const T*,
|
||||
bool predicate)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const funname = predicate ? "LessThan" : "operator<()";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::equal_range (%s, %1$s, const UserClass&%{?}, %s%{;})",
|
||||
itname, predicate, funname);
|
||||
|
||||
#define TEST(str, val, loff, uoff, comp) \
|
||||
test_equal_range (__LINE__, str, val, std::size_t (loff), \
|
||||
std::size_t (uoff), std::size_t (comp), \
|
||||
it, (T*)0, predicate)
|
||||
|
||||
// +------------------ source sequence
|
||||
// | +------------ value argument
|
||||
// | | +-------- lower offset of the returned pair
|
||||
// | | | +----- upper offset of the returned pair
|
||||
// | | | | +-- complexity: at most (2 * log(last - first) + 1)
|
||||
// | | | | | comparisons (or applications of the predicate)
|
||||
// | | | | |
|
||||
// V V V V V
|
||||
TEST ("", 'a', 0, 0, 0);
|
||||
TEST ("a", 'a', 0, 1, 2);
|
||||
TEST ("a", 'b', 1, 1, 1);
|
||||
TEST ("b", 'a', 0, 0, 2);
|
||||
|
||||
TEST ("aa", 'a', 0, 2, 4);
|
||||
TEST ("ab", 'a', 0, 1, 4);
|
||||
TEST ("ab", 'b', 1, 2, 3);
|
||||
TEST ("bb", 'a', 0, 0, 4);
|
||||
|
||||
TEST ("ace", 'a', 0, 1, 5);
|
||||
TEST ("ace", 'b', 1, 1, 4);
|
||||
TEST ("ace", 'c', 1, 2, 4);
|
||||
TEST ("ace", 'd', 2, 2, 4);
|
||||
TEST ("ace", 'e', 2, 3, 4);
|
||||
TEST ("ace", 'f', 3, 3, 4);
|
||||
|
||||
TEST ("aceg", 'a', 0, 1, 6);
|
||||
TEST ("aceg", 'b', 1, 1, 5);
|
||||
TEST ("aceg", 'c', 1, 2, 5);
|
||||
TEST ("aceg", 'd', 2, 2, 5);
|
||||
TEST ("aceg", 'e', 2, 3, 5);
|
||||
TEST ("aceg", 'f', 3, 3, 5);
|
||||
TEST ("aceg", 'g', 3, 4, 5);
|
||||
TEST ("aceg", 'h', 4, 4, 5);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int rw_opt_no_fwd_iter;
|
||||
static int rw_opt_no_bidir_iter;
|
||||
static int rw_opt_no_rnd_iter;
|
||||
static int rw_opt_no_predicate;
|
||||
|
||||
|
||||
template <class T>
|
||||
void test_equal_range (const T*,
|
||||
bool predicate)
|
||||
{
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0, "template <class %s, class %s%{?}, class %s%{;}> "
|
||||
"std::pair<%1$s, %1$s> std::equal_range "
|
||||
"(%1$s, %1$s, const %2$s&%{?}, %s%{;})",
|
||||
"ForwardIterator", "UserClass", predicate, "Compare",
|
||||
predicate, "Compare");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal_range (fwd_iter, (T*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal_range (bidir_iter, (T*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_equal_range (rand_iter, (T*)0, predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_equal_range ((UserClass*)0, false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"test of the Predicate form of std::equal_range disabled");
|
||||
}
|
||||
else {
|
||||
test_equal_range ((UserClass*)0, true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.equal.range",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-Predicate# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
321
extern/stdcxx/4.2.1/tests/algorithms/25.fill.cpp
vendored
Normal file
321
extern/stdcxx/4.2.1/tests/algorithms/25.fill.cpp
vendored
Normal file
@@ -0,0 +1,321 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.fill.cpp - test exercising 25.2.5 [lib.alg.fill]
|
||||
*
|
||||
* $Id: 25.fill.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for fill
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
fill (FwdIter<assign<base<> > >, FwdIter<assign<base<> > >,
|
||||
const assign<base<> >&);
|
||||
|
||||
template
|
||||
void
|
||||
fill_n (OutputIter<assign<base<> > >, Size<int>,
|
||||
const assign<base<> >&);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::fill()
|
||||
template <class ForwardIterator, class T>
|
||||
void test_fill (std::size_t N,
|
||||
const ForwardIterator &dummy_iter,
|
||||
const T*)
|
||||
{
|
||||
static const char* const itname = type_name (dummy_iter, (T*)0);
|
||||
static const char* const tname = "UserClass";
|
||||
|
||||
rw_info (0, 0, 0, "void std::fill (%s, %1$s, const %s&)", itname, tname);
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
T* const buf = new T [N];
|
||||
|
||||
for (std::size_t i = 0; i < N; ++i) {
|
||||
|
||||
T* const buf_end = buf + i;
|
||||
|
||||
const ForwardIterator begin =
|
||||
make_iter (buf, buf, buf_end, dummy_iter);
|
||||
|
||||
const ForwardIterator end =
|
||||
make_iter (buf_end, buf_end, buf_end, dummy_iter);
|
||||
|
||||
const T value;
|
||||
|
||||
// the number of invocations of the assignment operator
|
||||
std::size_t n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
std::fill (begin, end, value);
|
||||
|
||||
// compute the number of invocations of the assignment operator
|
||||
// by the algorithm
|
||||
n_op_assign = T::n_total_op_assign_ - n_op_assign;
|
||||
|
||||
bool success = true;
|
||||
|
||||
// verify 25.2.5, p2
|
||||
std::size_t j = 0;
|
||||
for ( ; success && j != i; ++j) {
|
||||
success = buf [j].data_.val_ == value.data_.val_;
|
||||
}
|
||||
|
||||
if (!rw_assert (success, 0, __LINE__,
|
||||
"%zu. fill (%s, %2$s, const %s&): buf [%zu]: %d != %d",
|
||||
i, itname, tname, j, buf [j].data_.val_,
|
||||
value.data_.val_))
|
||||
break;
|
||||
|
||||
// verify the complexity requirements:
|
||||
// Exactly last - first assignments.
|
||||
if (!rw_assert (n_op_assign == i, 0, __LINE__,
|
||||
"%zu. fill (%s, %2$s, const %s&) expected "
|
||||
"%zu invocations of %2$s::operator=(); got %zu",
|
||||
i, itname, tname, i, n_op_assign))
|
||||
break;
|
||||
}
|
||||
|
||||
delete[] buf;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::fill_n()
|
||||
template <class OutputIterator, class Size, class T>
|
||||
void test_fill_n (std::size_t N,
|
||||
const OutputIterator &dummy_iter,
|
||||
const Size*,
|
||||
const T*)
|
||||
{
|
||||
static const char* const itname = type_name (dummy_iter, (T*)0);
|
||||
static const char* const szname = "Size<int>";
|
||||
static const char* const tname = "UserClass";
|
||||
|
||||
rw_info (0, 0, 0, "void std::fill_n (%s, %s, const %s&)",
|
||||
itname, szname, tname);
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
T* const buf = new T [N];
|
||||
|
||||
for (std::size_t i = 0; i < N; ++i) {
|
||||
|
||||
T* const buf_end = buf + i;
|
||||
|
||||
const OutputIterator begin =
|
||||
make_iter (buf, buf, buf_end, dummy_iter);
|
||||
|
||||
const Size n (i, 0 /* dummy */);
|
||||
const T value;
|
||||
|
||||
// the number of invocations of the assignment operator
|
||||
std::size_t n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
std::fill_n (begin, n, value);
|
||||
|
||||
// compute the number of invocations of the assignment operator
|
||||
n_op_assign = T::n_total_op_assign_ - n_op_assign;
|
||||
|
||||
bool success = true;
|
||||
|
||||
// verify 25.2.5, p2
|
||||
std::size_t j = 0;
|
||||
for ( ; success && j != i; ++j) {
|
||||
success = buf [j].data_.val_ == value.data_.val_;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. fill_n (%s, %s, const %s&): buf [%zu]: %d != %d",
|
||||
i, itname, szname, tname, j, buf [j].data_.val_,
|
||||
value.data_.val_);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
success = n_op_assign == i;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. fill_n (%s, %s, const %s&) complexity: "
|
||||
"%zu != %zu", i, itname, szname, tname,
|
||||
n_op_assign, i);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
delete[] buf;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 32; // --nloops
|
||||
/* extern */ int rw_opt_no_fill; // --no-fill
|
||||
/* extern */ int rw_opt_no_fill_n; // --no-fill_n
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
static void
|
||||
test_fill (const std::size_t N)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"void std::fill (%1$s, %1$s, const %2$s&)",
|
||||
"ForwardIterator", "T");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill (N, FwdIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill (N, BidirIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill (N, RandomAccessIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_fill_n (const std::size_t N)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s> "
|
||||
"void std::fill_n (%1$s, %2$s, const %3$s&)",
|
||||
"OutputIterator", "Size", "T");
|
||||
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill_n (N, OutputIter<UserClass>(0, 0, 0), (Size<int>*)0,
|
||||
(UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill_n (N, FwdIter<UserClass>(), (Size<int>*)0, (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill_n (N, BidirIter<UserClass>(), (Size<int>*)0, (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill_n (N, RandomAccessIter<UserClass>(), (Size<int>*)0,
|
||||
(UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
// check that the number of loops is non-negative
|
||||
rw_fatal (-1 < rw_opt_nloops, 0, 0,
|
||||
"number of loops must be non-negative, got %d",
|
||||
rw_opt_nloops);
|
||||
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
if (rw_opt_no_fill) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::fill test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill (N);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fill_n) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::fill_n test disabled");
|
||||
}
|
||||
else {
|
||||
test_fill_n (N);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.fill",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops# "
|
||||
"|-no-fill# "
|
||||
"|-no-fill_n# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_fill,
|
||||
&rw_opt_no_fill_n,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
289
extern/stdcxx/4.2.1/tests/algorithms/25.find.cpp
vendored
Normal file
289
extern/stdcxx/4.2.1/tests/algorithms/25.find.cpp
vendored
Normal file
@@ -0,0 +1,289 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* find.cpp - test exercising 25.1.2 [lib.alg.find]
|
||||
*
|
||||
* $Id: 25.find.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 2000-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for find()
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
InputIter<eq_comp<base<> > >
|
||||
find (InputIter<eq_comp<base<> > >, InputIter<eq_comp<base<> > >,
|
||||
const eq_comp<base<> >&);
|
||||
|
||||
template
|
||||
InputIter<eq_comp<base<> > >
|
||||
find_if (InputIter<eq_comp<base<> > >, InputIter<eq_comp<base<> > >,
|
||||
predicate<eq_comp<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Predicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
Predicate (const T &val, int /* dummy */)
|
||||
: val_ (val) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
class ConvertibleToBool {
|
||||
bool result_;
|
||||
public:
|
||||
ConvertibleToBool (bool res): result_ (res) { /* empty */ }
|
||||
operator bool() const { return result_; }
|
||||
};
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
ConvertibleToBool operator() (T obj) /* not const */ {
|
||||
++funcalls_;
|
||||
return ConvertibleToBool (obj == val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (Predicate&);
|
||||
const T &val_;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
std::size_t Predicate<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator>
|
||||
void test_find (int line, // line number of test case
|
||||
const char *src, // source sequence
|
||||
std::size_t findoff, // offset of the element to find
|
||||
InputIterator dummy_iter,
|
||||
bool test_pred)
|
||||
{
|
||||
static const char* const itname = type_name (dummy_iter, (UserClass*)0);
|
||||
static const char* const pname = test_pred ? "Predicate" : "operator==";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
// normalize offset
|
||||
if (nsrc < findoff)
|
||||
findoff = nsrc;
|
||||
|
||||
// create always at least 1 element (used to test failed searches)
|
||||
UserClass* const tsrc = UserClass::from_char (src, nsrc + 1);
|
||||
UserClass* const src_begin = tsrc;
|
||||
UserClass* const src_end = tsrc + nsrc;
|
||||
|
||||
// current [first, last)
|
||||
const InputIterator first (src_begin, src_begin, src_end);
|
||||
const InputIterator last (src_end, src_begin, src_end);
|
||||
|
||||
// get a reference to the object to find (when findoff == nsrc
|
||||
// the sought for element is outside the source range and won't
|
||||
// be found)
|
||||
const UserClass &to_find = tsrc [findoff];
|
||||
|
||||
// construct a predicate object to use with find_if
|
||||
const Predicate<UserClass> pred (to_find, 0 /* dummy */);
|
||||
|
||||
// reset the operator==() counter
|
||||
UserClass::n_total_op_eq_ = 0;
|
||||
|
||||
// invoke find() or find_if(), depending on the predicate flag
|
||||
const InputIterator res = test_pred ?
|
||||
std::find_if (first, last, pred) : std::find (first, last, to_find);
|
||||
|
||||
// silence a bogus EDG eccp remark #550-D:
|
||||
// variable "res" was set but never used
|
||||
_RWSTD_UNUSED (res);
|
||||
|
||||
// verify 25.1.5 p2
|
||||
if (!rw_assert (res.cur_ == first.cur_ + findoff, 0, line,
|
||||
"line %d: find%{?}_if%{;} (%s = \"%s\", ..., '%c')"
|
||||
" == (it + %zu), got (it + %td)",
|
||||
__LINE__, test_pred, itname, src, to_find.data_.val_,
|
||||
findoff, res.cur_ - first.cur_)) {
|
||||
delete[] tsrc;
|
||||
return;
|
||||
}
|
||||
|
||||
// verify 25.1.5 p3
|
||||
// Complexity: At most last - first applications
|
||||
// of the corresponding predicate.
|
||||
// The complexity when find is successful is actually
|
||||
// (res - first) applications of the corresponding predicate.
|
||||
|
||||
const std::size_t npreds =
|
||||
test_pred ? pred.funcalls_ : UserClass::n_total_op_eq_;
|
||||
|
||||
rw_assert (npreds <= findoff + 1, 0, line,
|
||||
"line %d: find%{?}_if%{;} (%s = \"%s\", ..., '%c') "
|
||||
"invoked %s %zu times, expected no more than %zu",
|
||||
__LINE__, test_pred, itname, src, to_find.data_.val_,
|
||||
pname, npreds, findoff + 1);
|
||||
|
||||
delete[] tsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator>
|
||||
void test_find (InputIterator dummy_iter, bool test_pred)
|
||||
{
|
||||
static const char* const itname = type_name (dummy_iter, (UserClass*)0);
|
||||
|
||||
rw_info (0, 0, 0, "std::find%{?}_if%{;} (%s, %2$s, "
|
||||
"%{?}Predicate%{:}const UserClass&%{;})",
|
||||
test_pred, itname, test_pred);
|
||||
|
||||
#define TEST(src, off_find) \
|
||||
test_find (__LINE__, src, std::size_t (off_find), \
|
||||
dummy_iter, test_pred)
|
||||
|
||||
// +------------------ subject sequence
|
||||
// | +--- offset of the value to find (-1 for none)
|
||||
// | | also the offset of the returned iterator
|
||||
// | |
|
||||
// | |
|
||||
// v v
|
||||
TEST ("", -1);
|
||||
TEST ("a", 0);
|
||||
TEST ("aa", 0);
|
||||
TEST ("ab", 1);
|
||||
TEST ("aaa", 0);
|
||||
TEST ("abb", 1);
|
||||
TEST ("abc", 2);
|
||||
TEST ("abcc", 2);
|
||||
TEST ("abcd", 3);
|
||||
TEST ("abcde", 4);
|
||||
TEST ("abcdef", 5);
|
||||
TEST ("abcdefg", 6);
|
||||
TEST ("abcdefgh", 7);
|
||||
TEST ("abcdefghi", 8);
|
||||
TEST ("abcdefghij", 9);
|
||||
TEST ("abcdefghijk", 10);
|
||||
TEST ("abcdefghijk", -1);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
static void
|
||||
test_find (bool test_pred)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"%1$s std::find%{?}_if%{;} (%1$s, %1$s, "
|
||||
"%{?}%2$s%{:}const %2$s&%{;})",
|
||||
"InputIterator", test_pred ? "Predicate" : "T",
|
||||
test_pred);
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_find (InputIter<UserClass>(0, 0, 0), test_pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_find (ConstFwdIter<UserClass>(), test_pred);
|
||||
test_find (FwdIter<UserClass>(), test_pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_find (ConstBidirIter<UserClass>(), test_pred);
|
||||
test_find (BidirIter<UserClass>(), test_pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_find (ConstRandomAccessIter<UserClass>(), test_pred);
|
||||
test_find (RandomAccessIter<UserClass>(), test_pred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_find (false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "Predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_find (true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.find",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-InputIterator#"
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#"
|
||||
"|-no-Predicate#",
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
344
extern/stdcxx/4.2.1/tests/algorithms/25.find.end.cpp
vendored
Normal file
344
extern/stdcxx/4.2.1/tests/algorithms/25.find.end.cpp
vendored
Normal file
@@ -0,0 +1,344 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* find_end.cpp - test exercising 25.1.3 [lib.alg.find.end]
|
||||
*
|
||||
* $Id: 25.find.end.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for find_end()
|
||||
#include <functional> // for equal_to
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
find_end (FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
find_end (FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// used to initialize an array of objects of type T
|
||||
static const char *tinit_begin;
|
||||
|
||||
int tinit ()
|
||||
{
|
||||
typedef unsigned char UChar;
|
||||
|
||||
return UChar (*tinit_begin++);
|
||||
}
|
||||
|
||||
|
||||
// exercises std::find_end()
|
||||
template <class ForwardIterator1, class ForwardIterator2, class T>
|
||||
void do_test (int line, // line number of test case
|
||||
const char *src, // source sequence
|
||||
const char *fseq, // sequence to be found
|
||||
std::size_t resoff, // offset of result
|
||||
ForwardIterator1 &dummy_iter1,
|
||||
ForwardIterator2 &dummy_iter2,
|
||||
const T*,
|
||||
const char *predicate)
|
||||
{
|
||||
static const char* const it1name = type_name (dummy_iter1, (T*)0);
|
||||
static const char* const it2name = type_name (dummy_iter2, (T*)0);
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
const std::size_t nfseq = std::strlen (fseq);
|
||||
|
||||
if (std::size_t (-1) == resoff)
|
||||
resoff = nsrc;
|
||||
|
||||
// have the T default ctor initialize objects from `src'
|
||||
tinit_begin = src;
|
||||
T::gen_ = tinit;
|
||||
|
||||
T* const tsrc = new T [nsrc];
|
||||
|
||||
T* const src_begin = tsrc;
|
||||
T* const src_end = tsrc + nsrc;
|
||||
|
||||
// have the T default ctor initialize sequence to be found
|
||||
tinit_begin = fseq;
|
||||
|
||||
T* const tfseq = new T [nfseq];
|
||||
|
||||
T* const fseq_begin = tfseq;
|
||||
T* const fseq_end = tfseq + nfseq;
|
||||
|
||||
// create iterators
|
||||
const ForwardIterator1 first1 =
|
||||
make_iter (src_begin, src_begin, src_end, dummy_iter1);
|
||||
|
||||
const ForwardIterator1 last1 =
|
||||
make_iter (src_end, src_begin, src_end, dummy_iter1);
|
||||
|
||||
const ForwardIterator2 first2 =
|
||||
make_iter (fseq_begin, fseq_begin, fseq_end, dummy_iter2);
|
||||
|
||||
const ForwardIterator2 last2 =
|
||||
make_iter (fseq_end, fseq_begin, fseq_end, dummy_iter2);
|
||||
|
||||
// compute the number of invocations of the predicate
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
const ForwardIterator1 res = predicate ?
|
||||
std::find_end (first1, last1, first2, last2, std::equal_to<T>())
|
||||
: std::find_end (first1, last1, first2, last2);
|
||||
|
||||
// silence a bogus EDG eccp remark #550-D:
|
||||
// variable "res" was set but never used
|
||||
_RWSTD_UNUSED (res);
|
||||
|
||||
bool success = res.cur_ == first1.cur_ + resoff;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: find_end<%s, %s>(it = \"%s\", \"%s\")"
|
||||
" == (it + %zu), got (it + %td)",
|
||||
__LINE__, it1name, it2name, src, fseq,
|
||||
resoff, res.cur_ - first1.cur_);
|
||||
|
||||
if (!success) {
|
||||
delete[] tsrc;
|
||||
delete[] tfseq;
|
||||
return;
|
||||
}
|
||||
|
||||
if (res.cur_ != last1.cur_) {
|
||||
std::size_t j = 0;
|
||||
for ( ; j < nfseq; ++j) {
|
||||
success = (res.cur_ + j)->data_.val_ == fseq[j];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: find_end<%s, %s>(it = \"%s\", \"%s\")"
|
||||
" expected value %c got %c at %zu position",
|
||||
__LINE__, it1name, it2name, src, fseq,
|
||||
fseq[j], (res.cur_ + j)->data_.val_, j);
|
||||
|
||||
if (!success) {
|
||||
delete[] tsrc;
|
||||
delete[] tfseq;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
success =
|
||||
T::n_total_op_assign_ - last_n_op_assign <= nfseq * (nsrc - nfseq + 1);
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: find_end<%s, %s>(it = \"%s\", \"%s\")"
|
||||
" %s invoked %zu times, expected no more than %td",
|
||||
__LINE__, it1name, it2name, src, fseq,
|
||||
predicate ? predicate : "comparison operator",
|
||||
T::n_total_op_eq_, nfseq * (nsrc - nfseq + 1));
|
||||
|
||||
delete[] tsrc;
|
||||
delete[] tfseq;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator1, class ForwardIterator2, class T>
|
||||
void run_tests (const ForwardIterator1& dummy_iter1,
|
||||
const ForwardIterator2& dummy_iter2,
|
||||
const T*, const char* predicate)
|
||||
{
|
||||
static const char* const it1name = type_name (dummy_iter1, (T*)0);
|
||||
static const char* const it2name = type_name (dummy_iter2, (T*)0);
|
||||
|
||||
rw_info (0, 0, 0, "%s std::find_end (%1$s, %1$s, %s, %2$s%{?}, %s%{;})",
|
||||
it1name, it2name, 0 != predicate, predicate);
|
||||
|
||||
#define TEST(src, fnd, off_res) \
|
||||
do_test (__LINE__, src, fnd, std::size_t (off_res), \
|
||||
dummy_iter1, dummy_iter2, (UserClass*)0, predicate)
|
||||
|
||||
// +------------------ subject sequence
|
||||
// | +--- sequence to be found
|
||||
// | |
|
||||
// | | +-- offset of returned iterator,
|
||||
// | | | -1 denotes the end of sequence
|
||||
// v v v
|
||||
TEST ("abcdefghijk", "ab", 0);
|
||||
TEST ("abcdefghijk", "bc", 1);
|
||||
TEST ("abcdefghijk", "cd", 2);
|
||||
TEST ("abcdefghijk", "de", 3);
|
||||
TEST ("abcdefghijk", "ef", 4);
|
||||
TEST ("abcdefghijk", "fg", 5);
|
||||
TEST ("abcdefghijk", "gh", 6);
|
||||
TEST ("abcdefghijk", "hi", 7);
|
||||
TEST ("abcdefghijk", "ij", 8);
|
||||
TEST ("abcdefghijk", "jk", 9);
|
||||
|
||||
TEST ("ababcdefghij", "ab", 2);
|
||||
TEST ("abcbcdefghij", "bc", 3);
|
||||
TEST ("abcdcdefghij", "cd", 4);
|
||||
TEST ("abcdedefghij", "de", 5);
|
||||
TEST ("abcdefefghij", "ef", 6);
|
||||
TEST ("abcdefgfghij", "fg", 7);
|
||||
TEST ("abcdefghghij", "gh", 8);
|
||||
TEST ("abcdefghihij", "hi", 9);
|
||||
TEST ("bcdefghijijk", "ij", 9);
|
||||
TEST ("bcdefghijkjk", "jk", 10);
|
||||
|
||||
TEST ("", "a", -1);
|
||||
TEST ("a", "ab", -1);
|
||||
TEST ("ab", "abc", -1);
|
||||
TEST ("abc", "abcd", -1);
|
||||
TEST ("abcd", "abcde", -1);
|
||||
TEST ("abcde", "abcdef", -1);
|
||||
TEST ("abcdef", "abcdefg", -1);
|
||||
TEST ("abcdefg", "abcdefgh", -1);
|
||||
|
||||
TEST ("abcdefghijk", "ba", -1);
|
||||
TEST ("abcdefghijk", "cb", -1);
|
||||
TEST ("abcdefghijk", "dc", -1);
|
||||
TEST ("abcdefghijk", "ed", -1);
|
||||
TEST ("abcdefghijk", "fe", -1);
|
||||
TEST ("abcdefghijk", "gf", -1);
|
||||
TEST ("abcdefghijk", "hg", -1);
|
||||
TEST ("abcdefghijk", "ih", -1);
|
||||
TEST ("abcdefghijk", "ji", -1);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
|
||||
template <class ForwardIterator, class T>
|
||||
void run_test_find_end (const ForwardIterator& dummy, T*,
|
||||
const char* predicate)
|
||||
{
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (dummy, FwdIter<T>(), (T*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (dummy, BidirIter<T>(), (T*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (dummy, RandomAccessIter<T>(), (T*)0, predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_find_end (const char* predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"%1$s std::find_end (%1$s, %1$s, %2$s, %2$s%{?}, %s%{;})",
|
||||
"ForwardIterator1", "ForwardIterator2",
|
||||
0 != predicate, predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_test_find_end (FwdIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_test_find_end (BidirIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_test_find_end (RandomAccessIter<UserClass>(), (UserClass*)0,
|
||||
predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_find_end (0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "Predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_find_end ("std::equal_to<UserClass>");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.find.end",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#"
|
||||
"|-no-Predicate#",
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
367
extern/stdcxx/4.2.1/tests/algorithms/25.find.first.cpp
vendored
Normal file
367
extern/stdcxx/4.2.1/tests/algorithms/25.find.first.cpp
vendored
Normal file
@@ -0,0 +1,367 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* find.first.cpp - test exercising 25.1.4 [lib.alg.find.first.of]
|
||||
*
|
||||
* $Id: 25.find.first.cpp 510071 2007-02-21 15:58:53Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for find_first_of
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
find_first_of (FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
find_first_of (FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >, FwdIter<eq_comp<base<> > >,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class U>
|
||||
struct EqualityPredicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class
|
||||
// from being default constructible
|
||||
EqualityPredicate (T* /* dummy */, U* /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
class ConvertibleToBool {
|
||||
bool result_;
|
||||
public:
|
||||
ConvertibleToBool (bool res): result_ (res) { /* empty */ }
|
||||
operator bool() const { return result_; }
|
||||
};
|
||||
|
||||
ConvertibleToBool operator() (const T &x, const U &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return x == y;
|
||||
}
|
||||
};
|
||||
|
||||
template <class T, class U>
|
||||
std::size_t EqualityPredicate<T, U>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// used to initialize an array of objects of type T
|
||||
static const char *tinit_begin;
|
||||
|
||||
int tinit ()
|
||||
{
|
||||
typedef unsigned char UChar;
|
||||
|
||||
return UChar (*tinit_begin++);
|
||||
}
|
||||
|
||||
|
||||
// exercises std::find_end()
|
||||
template <class ForwardIterator1, class ForwardIterator2,
|
||||
class Predicate, class T>
|
||||
void do_test (int line, // line number of test case
|
||||
const char *src, // source sequence
|
||||
const char *fseq, // sequence to be found
|
||||
std::size_t resoff, // offset of result
|
||||
ForwardIterator1 &dummy_iter1,
|
||||
ForwardIterator2 &dummy_iter2,
|
||||
const T*,
|
||||
const Predicate *pred)
|
||||
{
|
||||
static const char* const it1name = type_name (dummy_iter1, (T*)0);
|
||||
static const char* const it2name = type_name (dummy_iter2, (T*)0);
|
||||
static const char* const pname = pred ? "Predicate" : "operator==";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
const std::size_t nfseq = std::strlen (fseq);
|
||||
|
||||
if (std::size_t (-1) == resoff)
|
||||
resoff = nsrc;
|
||||
|
||||
// have the T default ctor initialize objects from `src'
|
||||
tinit_begin = src;
|
||||
T::gen_ = tinit;
|
||||
|
||||
T* const tsrc = new T [nsrc];
|
||||
|
||||
T* const src_begin = tsrc;
|
||||
T* const src_end = tsrc + nsrc;
|
||||
|
||||
// have the T default ctor initialize sequence to be found
|
||||
tinit_begin = fseq;
|
||||
|
||||
T* const tfseq = new T [nfseq];
|
||||
|
||||
T* const fseq_begin = tfseq;
|
||||
T* const fseq_end = tfseq + nfseq;
|
||||
|
||||
// create iterators
|
||||
const ForwardIterator1 first1 =
|
||||
make_iter (src_begin, src_begin, src_end, dummy_iter1);
|
||||
|
||||
const ForwardIterator1 last1 =
|
||||
make_iter (src_end, src_begin, src_end, dummy_iter1);
|
||||
|
||||
const ForwardIterator2 first2 =
|
||||
make_iter (fseq_begin, fseq_begin, fseq_end, dummy_iter2);
|
||||
|
||||
const ForwardIterator2 last2 =
|
||||
make_iter (fseq_end, fseq_begin, fseq_end, dummy_iter2);
|
||||
|
||||
// compute the number of invocations of the operator==()
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
const Predicate fun((T*)0, (T*)0); // dummy arguments
|
||||
|
||||
const ForwardIterator1 res = pred ?
|
||||
std::find_first_of (first1, last1, first2, last2, fun)
|
||||
: std::find_first_of (first1, last1, first2, last2);
|
||||
|
||||
// silence a bogus EDG eccp remark #550-D:
|
||||
// variable "res" was set but never used
|
||||
_RWSTD_UNUSED (res);
|
||||
|
||||
if (!rw_assert (res.cur_ == first1.cur_ + resoff, 0, line,
|
||||
"line %d: find_first_of<%s, %s>(it = \"%s\", \"%s\")"
|
||||
" == (it + %zu), got (it + %td)",
|
||||
__LINE__, it1name, it2name, src, fseq,
|
||||
resoff, res.cur_ - first1.cur_)) {
|
||||
delete[] tsrc;
|
||||
delete[] tfseq;
|
||||
return;
|
||||
}
|
||||
|
||||
const std::size_t npreds = pred ?
|
||||
fun.funcalls_ : T::n_total_op_assign_ - last_n_op_assign;
|
||||
|
||||
rw_assert (npreds <= nfseq * nsrc, 0, line,
|
||||
"line %d: find_first_of<%s, %s>(it = \"%s\", \"%s\")"
|
||||
"%s invoked %zu times, expected no more than %td",
|
||||
__LINE__, it1name, it2name, src, fseq, pname,
|
||||
npreds, nfseq * nsrc);
|
||||
|
||||
delete[] tsrc;
|
||||
delete[] tfseq;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator1, class ForwardIterator2,
|
||||
class Predicate, class T>
|
||||
void run_tests (const ForwardIterator1 &dummy_iter1,
|
||||
const ForwardIterator2 &dummy_iter2,
|
||||
const T*,
|
||||
const Predicate *pred)
|
||||
{
|
||||
static const char* const it1name = type_name (dummy_iter1, (T*)0);
|
||||
static const char* const it2name = type_name (dummy_iter2, (T*)0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::find_first_of (%1$s, %1$s, %s, %2$s%{?}, %s%{;})",
|
||||
it1name, it2name, 0 != pred, "Predicate");
|
||||
|
||||
#define TEST(src, fnd, off_res) \
|
||||
do_test (__LINE__, src, fnd, std::size_t (off_res), \
|
||||
dummy_iter1, dummy_iter2, (UserClass*)0, pred)
|
||||
|
||||
// +------------------ subject sequence
|
||||
// | +--- sequence to be found
|
||||
// | |
|
||||
// | | +-- offset of returned iterator,
|
||||
// | | | -1 denotes the end of sequence
|
||||
// v v v
|
||||
TEST ("abcdefghijk", "a", 0);
|
||||
TEST ("abcdefghijk", "b", 1);
|
||||
TEST ("abcdefghijk", "c", 2);
|
||||
TEST ("abcdefghijk", "d", 3);
|
||||
TEST ("abcdefghijk", "e", 4);
|
||||
TEST ("abcdefghijk", "f", 5);
|
||||
TEST ("abcdefghijk", "g", 6);
|
||||
TEST ("abcdefghijk", "h", 7);
|
||||
TEST ("abcdefghijk", "i", 8);
|
||||
TEST ("abcdefghijk", "j", 9);
|
||||
TEST ("abcdefghijk", "k", 10);
|
||||
|
||||
TEST ("aabcdefghijk", "a", 0);
|
||||
TEST ("abbcdefghijk", "b", 1);
|
||||
TEST ("abccdefghijk", "c", 2);
|
||||
TEST ("abcddefghijk", "d", 3);
|
||||
TEST ("abcdeefghijk", "e", 4);
|
||||
TEST ("abcdeffghijk", "f", 5);
|
||||
TEST ("abcdefgghijk", "g", 6);
|
||||
TEST ("abcdefghhijk", "h", 7);
|
||||
TEST ("abcdefghijjk", "i", 8);
|
||||
TEST ("abcdefghijjk", "j", 9);
|
||||
TEST ("abcdefghijkk", "k", 10);
|
||||
|
||||
TEST ("bbcdefghijk", "ab", 0);
|
||||
TEST ("accdefghijk", "bc", 1);
|
||||
TEST ("abddefghijk", "cd", 2);
|
||||
TEST ("abceefghijk", "de", 3);
|
||||
TEST ("abcdffghijk", "ef", 4);
|
||||
TEST ("abcdegghijk", "fg", 5);
|
||||
TEST ("abcdefhhijk", "gh", 6);
|
||||
TEST ("abcdefgiijk", "hi", 7);
|
||||
TEST ("abcdefghjjk", "ij", 8);
|
||||
TEST ("abcdefghikk", "jk", 9);
|
||||
|
||||
TEST ("bbcdefghijk", "a", -1);
|
||||
TEST ("accdefghijk", "b", -1);
|
||||
TEST ("abddefghijk", "c", -1);
|
||||
TEST ("abceefghijk", "d", -1);
|
||||
TEST ("abcdffghijk", "e", -1);
|
||||
TEST ("abcdegghijk", "f", -1);
|
||||
TEST ("abcdefhhijk", "g", -1);
|
||||
TEST ("abcdefgiijk", "h", -1);
|
||||
TEST ("abcdefghjjk", "i", -1);
|
||||
TEST ("abcdefghikk", "j", -1);
|
||||
|
||||
TEST ("", "a", -1);
|
||||
TEST ("abcdefghijk", "", -1);
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
|
||||
template <class ForwardIterator, class Predicate, class T>
|
||||
void run_test (const ForwardIterator &dummy, T*, Predicate* pred)
|
||||
{
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (dummy, FwdIter<T>(), (T*)0, pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (dummy, BidirIter<T>(), (T*)0, pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_tests (dummy, RandomAccessIter<T>(), (T*)0, pred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
run_test (bool test_predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"%1$s std::find_first_of (%1$s, %1$s, %2$s, %2$s%{?}, %s%{;})",
|
||||
"ForwardIterator1", "ForwardIterator2",
|
||||
0 != test_predicate, "Predicate");
|
||||
|
||||
typedef EqualityPredicate<UserClass, UserClass> EqPred;
|
||||
const EqPred* const pred = test_predicate ? (EqPred*)1 : (EqPred*)0;
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_test (FwdIter<UserClass>(), (UserClass*)0, pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_test (BidirIter<UserClass>(), (UserClass*)0, pred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
run_test (RandomAccessIter<UserClass>(), (UserClass*)0, pred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
run_test (false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "Predicate test disabled");
|
||||
}
|
||||
else {
|
||||
run_test (true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.find.first.of",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#"
|
||||
"|-no-Predicate#",
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
253
extern/stdcxx/4.2.1/tests/algorithms/25.for.each.cpp
vendored
Normal file
253
extern/stdcxx/4.2.1/tests/algorithms/25.for.each.cpp
vendored
Normal file
@@ -0,0 +1,253 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.for_each.cpp - test exercising 25.1.1 [lib.alg.foreach]
|
||||
*
|
||||
* $Id: 25.for.each.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for for_each
|
||||
#include <cstddef> // for ptrdiff_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test(), ...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct FunctionBase
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
static int sum_;
|
||||
bool is_const_;
|
||||
|
||||
FunctionBase (bool is_const)
|
||||
: is_const_ (is_const) {
|
||||
funcalls_ = 0;
|
||||
sum_ = 0;
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (FunctionBase&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t FunctionBase::funcalls_;
|
||||
int FunctionBase::sum_;
|
||||
|
||||
|
||||
struct ConstFunction: FunctionBase
|
||||
{
|
||||
// dummy arguments provided to prevent the class
|
||||
// from being default constructible
|
||||
ConstFunction (int, int): FunctionBase (true) { }
|
||||
|
||||
void operator() (UserClass val) /* not const */ {
|
||||
++funcalls_;
|
||||
sum_ += val.data_.val_;
|
||||
}
|
||||
|
||||
static const char* name () { return "ConstFunction"; }
|
||||
};
|
||||
|
||||
|
||||
struct MutableFunction: FunctionBase
|
||||
{
|
||||
// dummy arguments provided to prevent the class
|
||||
// from being default constructible
|
||||
MutableFunction (int, int): FunctionBase (false) { }
|
||||
|
||||
void operator() (UserClass &val) /* not const */ {
|
||||
++funcalls_;
|
||||
val.data_.val_ = -val.data_.val_;
|
||||
}
|
||||
|
||||
static const char* name () { return "MutableFunction"; }
|
||||
};
|
||||
|
||||
|
||||
// exercises std::for_each()
|
||||
template <class InputIterator, class T, class Function>
|
||||
void test_for_each (std::size_t N, InputIterator dummy, T*, Function*)
|
||||
{
|
||||
static const char* const itname = type_name (dummy, (T*)0);
|
||||
static const char* const fnname = Function::name ();
|
||||
|
||||
rw_info (0, 0, 0, "std::for_each (%s, %1$s, %s)", itname, fnname);
|
||||
|
||||
// generate sequential values for each default constructed UserClass
|
||||
UserClass::gen_ = gen_seq;
|
||||
|
||||
UserClass *buf = new UserClass [N];
|
||||
|
||||
const int first_val = buf [0].data_.val_;
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
UserClass* const buf_end = buf + i;
|
||||
|
||||
const InputIterator first (buf, buf, buf_end);
|
||||
const InputIterator last (buf_end, buf_end, buf_end);
|
||||
|
||||
// create a const function object and zero out all its counters
|
||||
const Function fun (0, 0);
|
||||
|
||||
std::for_each (first, last, fun);
|
||||
|
||||
// compute the sum of elements in the sequence and check each
|
||||
// element's value against the expected one
|
||||
int sum = 0;
|
||||
|
||||
for (std::size_t j = 0; j != i; ++j) {
|
||||
|
||||
int expect;
|
||||
|
||||
if (fun.is_const_) {
|
||||
// const function object doesn't modify the subject
|
||||
// sequence; the expected value of the element is
|
||||
// the same as the original value
|
||||
expect = first_val + int (j);
|
||||
}
|
||||
else {
|
||||
// non-const function object negates each argument
|
||||
expect = -(first_val + int (j));
|
||||
}
|
||||
|
||||
// compute the sum (computed by the const function object)
|
||||
sum += buf [j].data_.val_;
|
||||
|
||||
// assert the element value as the same as the expected value
|
||||
rw_assert (expect == buf [j].data_.val_, 0, __LINE__,
|
||||
"for_each (%s, %1$s, %s); element [%zu] == %d, got %d",
|
||||
itname, fnname, j, expect, buf [j].data_.val_);
|
||||
|
||||
if (expect != buf [j].data_.val_) {
|
||||
// break out of both loops on failure
|
||||
i = N;
|
||||
break;
|
||||
}
|
||||
|
||||
// restore the original value of the element
|
||||
buf [j].data_.val_ = first_val + int (j);
|
||||
}
|
||||
|
||||
// assert that for_each invoked the function object's operator()
|
||||
// exactly as many times as necessary and required
|
||||
rw_assert (i == fun.funcalls_, 0, __LINE__,
|
||||
"for_each (%s, %1$s, %s); expected %zu invocations of "
|
||||
"Function::operator(), got %zu", itname, fnname,
|
||||
i, fun.funcalls_);
|
||||
|
||||
if (fun.is_const_) {
|
||||
rw_assert (sum == fun.sum_, 0, __LINE__,
|
||||
"for_each (%s, %1$s, %s); sum of %zu elements == %d, "
|
||||
"got %d", itname, fnname, sum, fun.sum_);
|
||||
}
|
||||
}
|
||||
|
||||
delete[] (buf);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int rw_opt_nloops = 32; // --nloops=#
|
||||
static int rw_opt_no_input_iter; // --no-InputIterator
|
||||
static int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
static int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
static int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"%2$s std::for_each (%1$s, %1$s, %2$s)",
|
||||
"InputIterator", "Function");
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_for_each (N, InputIter<UserClass>(0, 0, 0), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_for_each (N, ConstFwdIter<UserClass>(), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
test_for_each (N, FwdIter<UserClass>(), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
test_for_each (N, FwdIter<UserClass>(), (UserClass*)0,
|
||||
(MutableFunction*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_for_each (N, ConstBidirIter<UserClass>(), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
test_for_each (N, BidirIter<UserClass>(), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
test_for_each (N, BidirIter<UserClass>(), (UserClass*)0,
|
||||
(MutableFunction*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_for_each (N, ConstRandomAccessIter<UserClass>(), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
test_for_each (N, RandomAccessIter<UserClass>(), (UserClass*)0,
|
||||
(ConstFunction*)0);
|
||||
test_for_each (N, RandomAccessIter<UserClass>(), (UserClass*)0,
|
||||
(MutableFunction*)0);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.foreach",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops#0 " // must be non-negative
|
||||
"|-no-InputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
356
extern/stdcxx/4.2.1/tests/algorithms/25.generate.cpp
vendored
Normal file
356
extern/stdcxx/4.2.1/tests/algorithms/25.generate.cpp
vendored
Normal file
@@ -0,0 +1,356 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.generate.cpp - test exercising 25.2.6 [lib.alg.generate]
|
||||
*
|
||||
* $Id: 25.generate.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for generate
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Generator
|
||||
{
|
||||
// return a const reference to avoid requiring
|
||||
// that T be copy-constructible
|
||||
const T& operator() () const {
|
||||
static const union {
|
||||
void* align_;
|
||||
unsigned char buf_ [sizeof (T)];
|
||||
} u = { 0 };
|
||||
return *(const T*)(const void*)&u;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
_RWSTD_SPECIALIZED_CLASS
|
||||
struct Generator<UserClass>
|
||||
{
|
||||
// dummy arguments provided to prevent Generator
|
||||
// from being DefaultConstructible
|
||||
Generator (int, int /* dummy */) {
|
||||
// use the generator of sequential values
|
||||
UserClass::gen_ = gen_seq;
|
||||
}
|
||||
|
||||
UserClass operator() () /* non-const */ {
|
||||
// return a default-constructed UserClass intialized
|
||||
// to the next sequential value
|
||||
return UserClass ();
|
||||
}
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void generate (FwdIter<assign<base<> > >, FwdIter<assign<base<> > >,
|
||||
Generator<assign<base<> > >);
|
||||
|
||||
template
|
||||
void generate_n (OutputIter<assign<base<> > >, std::size_t,
|
||||
Generator<assign<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::generate()
|
||||
template <class ForwardIterator, class T>
|
||||
void test_generate (std::size_t N,
|
||||
const ForwardIterator& gen_iter,
|
||||
const T* )
|
||||
{
|
||||
static const char* const itname = type_name (gen_iter, (T*) 0);
|
||||
static const char* const genname = "Generator";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"void std::generate (%s, %1$s, %s)", itname, genname);
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
T *buf = new UserClass [N];
|
||||
|
||||
for (std::size_t i = 0; i < N; ++i) {
|
||||
|
||||
// exercise 25.2.6, std::generate<> ()
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
T* const buf_end = buf + i + 1;
|
||||
|
||||
const ForwardIterator begin =
|
||||
make_iter (buf, buf, buf_end, gen_iter);
|
||||
|
||||
const ForwardIterator end =
|
||||
make_iter (buf_end, buf_end, buf_end, gen_iter);
|
||||
|
||||
const Generator<T> gen (0, 0);
|
||||
|
||||
// store the value of the next element
|
||||
const int last_val = Generator<T>(0, 0)().data_.val_;
|
||||
|
||||
std::generate (begin, end, gen);
|
||||
|
||||
bool success = true;
|
||||
|
||||
// verify 25.2.6, p2
|
||||
std::size_t j = 0;
|
||||
for ( ; j != i; ++j) {
|
||||
success = (begin.cur_ + j)->data_.val_ == int (last_val + j + 1);
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. generate (): buf[%zu]: %d != %d",
|
||||
i + 1, j, last_val + j + 1, (begin.cur_ + j)->data_.val_ );
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// verify 25.2.6, p3
|
||||
success = T::n_total_op_assign_ - last_n_op_assign == i + 1;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. generate (): complexity: %zu != %zu",
|
||||
i + 1, T::n_total_op_assign_ - last_n_op_assign, i + 1);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
delete[] (buf);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::generate_n()
|
||||
template <class ForwardIterator, class Size, class T>
|
||||
void test_generate_n (std::size_t N,
|
||||
const ForwardIterator &gen_iter,
|
||||
const Size*,
|
||||
const T*)
|
||||
{
|
||||
static const char* const itname = type_name (gen_iter, (T*) 0);
|
||||
static const char* const szname = "Size<int>";
|
||||
static const char* const genname = "Generator";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"void std::generate_n (%s, %s, %s)", itname, szname, genname);
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
T *buf = new UserClass [N];
|
||||
|
||||
for (std::size_t i = 0; i <= N; ++i) {
|
||||
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
T* const buf_end = buf + i + 1;
|
||||
|
||||
const ForwardIterator begin =
|
||||
make_iter (buf, buf, buf_end, gen_iter);
|
||||
|
||||
const Size n (i, 0);
|
||||
const Generator<T> gen (0, 0);
|
||||
|
||||
// store the value of the next element
|
||||
const int last_val = Generator<T>(0, 0)().data_.val_;
|
||||
|
||||
std::generate_n (begin, n, gen);
|
||||
|
||||
bool success = true;
|
||||
|
||||
// verify 25.2.6, p2
|
||||
std::size_t j = 0;
|
||||
for ( ; j != i; ++j) {
|
||||
success = (begin.cur_ + j)->data_.val_ == int (last_val + j + 1);
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. generate_n (): buf[%zu]: %d != %d",
|
||||
i + 1, j, last_val + j + 1, (begin.cur_ + j)->data_.val_ );
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// verify 25.2.6, p3
|
||||
success = T::n_total_op_assign_ - last_n_op_assign == i;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. generate_n (): complexity: %zu != %zu",
|
||||
i + 1, T::n_total_op_assign_ - last_n_op_assign, i);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
delete[] (buf);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 32; // --nloops
|
||||
/* extern */ int rw_opt_no_generate; // --no-generate
|
||||
/* extern */ int rw_opt_no_generate_n; // --no-generate_n
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
static void
|
||||
test_generate (const std::size_t N)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"void std::generate (%1$s, %1$s, %2$s&)",
|
||||
"ForwardIterator", "Generator");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate (N, FwdIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate (N, BidirIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate (N, RandomAccessIter<UserClass>(), (UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_generate_n (const std::size_t N)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s> "
|
||||
"void std::generate_n (%1$s, %2$s, const %3$s&)",
|
||||
"OutputIterator", "Size", "Generator");
|
||||
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate_n (N, OutputIter<UserClass>(0, 0, 0), (Size<int>*)0,
|
||||
(UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate_n (N, FwdIter<UserClass>(), (Size<int>*)0, (UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate_n (N, BidirIter<UserClass>(), (Size<int>*)0,
|
||||
(UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate_n (N, RandomAccessIter<UserClass>(), (Size<int>*)0,
|
||||
(UserClass*)0);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
RW_ASSERT (0 <= rw_opt_nloops);
|
||||
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
if (rw_opt_no_generate) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::generate test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate (N);
|
||||
}
|
||||
|
||||
if (rw_opt_no_generate_n) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::generate_n test disabled");
|
||||
}
|
||||
else {
|
||||
test_generate_n (N);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.generate",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops#0 " // argument must be non-negative
|
||||
"|-no-generate# "
|
||||
"|-no-generate_n# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_generate,
|
||||
&rw_opt_no_generate_n,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
479
extern/stdcxx/4.2.1/tests/algorithms/25.heap.cpp
vendored
Normal file
479
extern/stdcxx/4.2.1/tests/algorithms/25.heap.cpp
vendored
Normal file
@@ -0,0 +1,479 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.heap.cpp - test exercising 25.3.6 [lib.alg.heap.operations]
|
||||
*
|
||||
* $Id: 25.heap.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
// MSVC 6.0 gets an ICE in std::__adjust_heap() in <algorithm.cc>
|
||||
#if defined (_MSC_VER) && _MSC_VER <= 1300
|
||||
# define _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
#endif
|
||||
|
||||
#include <algorithm> // for make_heap, sort_heap, push_heap, pop_heap
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
// 25.3.6.1 - push_heap [lib.push.heap]
|
||||
template
|
||||
void
|
||||
push_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
push_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
// 25.3.6.2 - pop_heap [lib.pop.heap]
|
||||
template
|
||||
void
|
||||
pop_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
pop_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
// 25.3.6.3 - make_heap [lib.make.heap]
|
||||
template
|
||||
void
|
||||
make_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
make_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
// 25.3.6.4 - sort_heap [lib.sort.heap]
|
||||
template
|
||||
void
|
||||
sort_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
sort_heap (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// helper function to verify that the sequence is a valid heap
|
||||
template <class T>
|
||||
bool is_heap (const T* seq, const std::size_t len)
|
||||
{
|
||||
std::size_t parent = 0;
|
||||
for (std::size_t child = 1; child < len; ++child) {
|
||||
|
||||
if (seq [parent].data_.val_ < seq [child].data_.val_)
|
||||
return false;
|
||||
|
||||
if ((child & 1) == 0)
|
||||
++parent;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises push_heap, pop_heap, make_heap, sort_heap: 25.3.6.1 - 25.3.6.4
|
||||
template <class T, class Predicate>
|
||||
void test_heap_operation (int line,
|
||||
const char *src,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
const std::size_t finx)
|
||||
{
|
||||
static const char* const fnames[] = {
|
||||
"make_heap", "push_heap", "pop_heap", "sort_heap"
|
||||
};
|
||||
|
||||
typedef RandomAccessIter<T> RandIter;
|
||||
RandIter rand_iter (0, 0, 0);
|
||||
|
||||
const char* const itname = type_name (rand_iter, (T*)0);
|
||||
const char* const fname = fnames[finx];
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
int val = xsrc[0].data_.val_;
|
||||
|
||||
const RandIter first = make_iter (xsrc, xsrc, xsrc_end, rand_iter);
|
||||
const RandIter last = make_iter (xsrc_end, xsrc, xsrc_end, rand_iter);
|
||||
|
||||
const Predicate pred (0, 0);
|
||||
|
||||
const std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
|
||||
// for convenience
|
||||
#define HEAP_OP(opname) \
|
||||
if (ppred) opname (first, last, pred); else opname (first, last)
|
||||
|
||||
std::size_t ops = 0;
|
||||
|
||||
// exercise heap operation and compute the expected complexity
|
||||
switch (finx) {
|
||||
case 0: HEAP_OP (std::make_heap); ops = 3 * nsrc; break;
|
||||
case 1: HEAP_OP (std::push_heap); ops = ilog2 (nsrc); break;
|
||||
case 2: HEAP_OP (std::pop_heap); ops = 2 * ilog2 (nsrc); break;
|
||||
case 3: HEAP_OP (std::sort_heap); ops = nsrc * ilog2 (nsrc); break;
|
||||
}
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
const std::size_t len = 2 != finx ? nsrc : nsrc - 1;
|
||||
|
||||
if (2 == finx) { // pop_heap special verification
|
||||
// verify that the maximal element is in
|
||||
// the end of the sequence: 25.3.6.2, p2
|
||||
rw_assert (val == xsrc[nsrc - 1].data_.val_, 0, line,
|
||||
"line %d std::%s <%s%{?}, %s%{;}> (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\", last is %#c, expected %#c",
|
||||
__LINE__, fname, itname, ppred, funname, src,
|
||||
int (nsrc), -1, xsrc, xsrc [nsrc - 1].data_.val_, val);
|
||||
}
|
||||
|
||||
if (3 == finx) { // sort_heap special verification
|
||||
// verify that we got a sorted sequence: 25.3.6.4, p1
|
||||
rw_assert (is_sorted_lt (xsrc, xsrc_end), 0, line,
|
||||
"line %d std::%s <%s%{?}, %s%{;}> (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\" is not sorted",
|
||||
__LINE__, fname, itname, ppred, funname, src,
|
||||
int (nsrc), -1, xsrc);
|
||||
}
|
||||
else {
|
||||
// verify that we got a heap:
|
||||
// 25.3.6.1, p2; 25.3.6.2, p2; 25.3.6.3, p1
|
||||
rw_assert (is_heap (xsrc, len), 0, line,
|
||||
"line %d std::%s <%s%{?}, %s%{;}> (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\" is not a heap",
|
||||
__LINE__, fname, itname, ppred, funname, src,
|
||||
int (len), -1, xsrc);
|
||||
}
|
||||
|
||||
// verify the complexity:
|
||||
// 25.3.6.1, p3; 25.3.6.2, p3; 25.3.6.3, p2; 25.3.6.4, p2
|
||||
rw_assert (n_ops_lt <= ops, 0, line,
|
||||
"line %d std::%s <%s%{?}, %s%{;}> (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\" complexity: got %zu invocations of %s, "
|
||||
"expected no more %zu",
|
||||
__LINE__, fname, itname, ppred, funname, src,
|
||||
int (nsrc), -1, xsrc, n_ops_lt,
|
||||
ppred ? "predicate" : "operator< ()", ops);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_make_heap (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"std::make_heap (%s, %1$s%{?}, %s%{;})",
|
||||
"RandomAccessIterator", 0 != ppred, Predicate::name ());
|
||||
|
||||
#define TEST(src) \
|
||||
test_heap_operation (__LINE__, src, (T*)0, ppred, 0)
|
||||
|
||||
TEST ("a");
|
||||
TEST ("ab");
|
||||
TEST ("ba");
|
||||
|
||||
TEST ("abcde");
|
||||
TEST ("acbed");
|
||||
TEST ("cbade");
|
||||
TEST ("debca");
|
||||
TEST ("ecace");
|
||||
TEST ("accee");
|
||||
TEST ("caced");
|
||||
|
||||
TEST ("abcdefghij");
|
||||
TEST ("bcdeafghij");
|
||||
TEST ("dcbeafihgj");
|
||||
TEST ("badcfehgji");
|
||||
TEST ("ebadcfhijg");
|
||||
|
||||
TEST ("jihgfedcba");
|
||||
TEST ("ijhgefdcab");
|
||||
|
||||
TEST ("ababababab");
|
||||
TEST ("babbbababb");
|
||||
|
||||
#undef TEST
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_push_heap (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"std::push_heap (%s, %1$s%{?}, %s%{;})",
|
||||
"RandomAccessIterator", 0 != ppred, Predicate::name ());
|
||||
|
||||
#define TEST(src) \
|
||||
test_heap_operation (__LINE__, src, (T*)0, ppred, 1)
|
||||
|
||||
TEST ("a");
|
||||
TEST ("ab");
|
||||
TEST ("ba");
|
||||
|
||||
TEST ("bac");
|
||||
TEST ("cba");
|
||||
TEST ("aac");
|
||||
|
||||
TEST ("ecdaba");
|
||||
TEST ("ecdabc");
|
||||
TEST ("ecdabe");
|
||||
|
||||
TEST ("jighefcadj");
|
||||
TEST ("jighefcada");
|
||||
TEST ("jighefcadh");
|
||||
|
||||
TEST ("jhigcfbeda");
|
||||
TEST ("jhigcfbedj");
|
||||
TEST ("jhigcfbedh");
|
||||
TEST ("jhigcfbedf");
|
||||
TEST ("jhigcfbede");
|
||||
TEST ("jhigcfbedg");
|
||||
|
||||
TEST ("bbbbbaaaaa");
|
||||
TEST ("bbbbbaaaab");
|
||||
|
||||
#undef TEST
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_pop_heap (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"std::pop_heap (%s, %1$s%{?}, %s%{;})",
|
||||
"RandomAccessIterator", 0 != ppred, Predicate::name ());
|
||||
|
||||
#define TEST(src) \
|
||||
test_heap_operation (__LINE__, src, (T*)0, ppred, 2)
|
||||
|
||||
TEST ("a");
|
||||
TEST ("ba");
|
||||
|
||||
TEST ("aaa");
|
||||
TEST ("cba");
|
||||
TEST ("caa");
|
||||
|
||||
TEST ("ecdab");
|
||||
TEST ("ecdab");
|
||||
TEST ("ecdab");
|
||||
|
||||
TEST ("jighefcadb");
|
||||
TEST ("jighcfdbea");
|
||||
TEST ("jhigcfbeda");
|
||||
TEST ("jihgfedacb");
|
||||
TEST ("iihegfabdc");
|
||||
TEST ("iihgfedcba");
|
||||
TEST ("iihgefdcab");
|
||||
|
||||
TEST ("bbbbbaaaaa");
|
||||
|
||||
#undef TEST
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_sort_heap (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"std::sort_heap (%s, %1$s%{?}, %s%{;})",
|
||||
"RandomAccessIterator", 0 != ppred, Predicate::name());
|
||||
|
||||
#define TEST(src) \
|
||||
test_heap_operation (__LINE__, src, (T*)0, ppred, 3)
|
||||
|
||||
TEST ("a");
|
||||
TEST ("ba");
|
||||
|
||||
TEST ("aaa");
|
||||
TEST ("cba");
|
||||
TEST ("caa");
|
||||
|
||||
TEST ("ecdab");
|
||||
TEST ("ecdab");
|
||||
TEST ("ecdab");
|
||||
|
||||
TEST ("jighefcadb");
|
||||
TEST ("jighcfdbea");
|
||||
TEST ("jhigcfbeda");
|
||||
TEST ("jihgfedacb");
|
||||
TEST ("iihegfabdc");
|
||||
TEST ("iihgfedcba");
|
||||
TEST ("iihgefdcab");
|
||||
|
||||
TEST ("bbbbbaaaaa");
|
||||
|
||||
#undef TEST
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_make_heap; // --no-make_heap
|
||||
/* extern */ int rw_opt_no_push_heap; // --no-push_heap
|
||||
/* extern */ int rw_opt_no_pop_heap; // --no-pop_heap
|
||||
/* extern */ int rw_opt_no_sort_heap; // --no-sort_heap
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_heap_operations (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
if (rw_opt_no_make_heap) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::make_heap test disabled");
|
||||
}
|
||||
else {
|
||||
test_make_heap ((T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_push_heap) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::push_heap test disabled");
|
||||
}
|
||||
else {
|
||||
test_push_heap ((T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_pop_heap) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::pop_heap test disabled");
|
||||
}
|
||||
else {
|
||||
test_pop_heap ((T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_sort_heap) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::sort_heap test disabled");
|
||||
}
|
||||
else {
|
||||
test_sort_heap ((T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
test_heap_operations ((UserClass*)0, (Less<UserClass>*)0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"heap operations predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_heap_operations ((UserClass*)0, (Less<UserClass>*)1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.heap.operations",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-make_heap#"
|
||||
"|-no-push_heap#"
|
||||
"|-no-pop_heap#"
|
||||
"|-no-sort_heap#"
|
||||
"|-no-predicate",
|
||||
&rw_opt_no_make_heap,
|
||||
&rw_opt_no_push_heap,
|
||||
&rw_opt_no_pop_heap,
|
||||
&rw_opt_no_sort_heap,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
339
extern/stdcxx/4.2.1/tests/algorithms/25.includes.cpp
vendored
Normal file
339
extern/stdcxx/4.2.1/tests/algorithms/25.includes.cpp
vendored
Normal file
@@ -0,0 +1,339 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.includes.cpp - test exercising 25.3.5.1 [lib.includes]
|
||||
*
|
||||
* $Id: 25.includes.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for includes
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
bool
|
||||
includes (InputIter<lt_comp<base<no_ctor> > >,
|
||||
InputIter<lt_comp<base<no_ctor> > >,
|
||||
InputIter<lt_comp<base<no_ctor> > >,
|
||||
InputIter<lt_comp<base<no_ctor> > > );
|
||||
|
||||
template
|
||||
bool
|
||||
includes (InputIter<lt_comp<base<no_ctor> > >,
|
||||
InputIter<lt_comp<base<no_ctor> > >,
|
||||
InputIter<lt_comp<base<no_ctor> > >,
|
||||
InputIter<lt_comp<base<no_ctor> > >,
|
||||
binary_predicate<lt_comp<base<no_ctor> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template
|
||||
<class T, class InputIterator1, class InputIterator2, class Predicate>
|
||||
void test_includes (int line,
|
||||
const char *src1,
|
||||
const char *src2,
|
||||
const bool res,
|
||||
const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
const char* const it1name = type_name (it1, (T*)0);
|
||||
const char* const it2name = type_name (it2, (T*)0);
|
||||
const char* const fname = "includes";
|
||||
const char* const predname = Predicate::name();
|
||||
|
||||
const std::size_t nsrc1 = std::strlen (src1);
|
||||
const std::size_t nsrc2 = std::strlen (src2);
|
||||
|
||||
T* const xsrc1 = T::from_char (src1, nsrc1);
|
||||
T* const xsrc2 = T::from_char (src2, nsrc2);
|
||||
|
||||
T* const xsrc1_end = xsrc1 + nsrc1;
|
||||
T* const xsrc2_end = xsrc2 + nsrc2;
|
||||
|
||||
const InputIterator1 first1 = make_iter (xsrc1, xsrc1, xsrc1_end, it1);
|
||||
const InputIterator1 last1 = make_iter (xsrc1_end, xsrc1, xsrc1_end, it1);
|
||||
const InputIterator2 first2 = make_iter (xsrc2, xsrc2, xsrc2_end, it2);
|
||||
const InputIterator2 last2 = make_iter (xsrc2_end, xsrc2, xsrc2_end, it2);
|
||||
|
||||
const Predicate pred (0, 0);
|
||||
|
||||
const std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
|
||||
const bool result = ppred ?
|
||||
std::includes (first1, last1, first2, last2, pred)
|
||||
: std::includes (first1, last1, first2, last2);
|
||||
|
||||
// check the returned value
|
||||
rw_assert (res == result, 0, line,
|
||||
"line %d: %s<%s, %s%{?}, %s%{;}>(\"%s\", \"%s\", ...) "
|
||||
"== %b, got %b",
|
||||
__LINE__, fname, it1name, it2name, ppred, predname, src1, src2,
|
||||
res, result);
|
||||
|
||||
std::size_t n_ops_lt = ppred ?
|
||||
Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// check the complexity
|
||||
std::size_t n_exp_ops = nsrc1 + nsrc2 > 0 ? 2 * (nsrc1 + nsrc2) - 1 : 0;
|
||||
rw_assert (n_ops_lt <= n_exp_ops, 0, line,
|
||||
"line %d: %s<%s, %s%{?}, %s%{;}>(\"%s\", \"%s\", ...) "
|
||||
"complexity: got %zu, expected <= %zu",
|
||||
__LINE__, fname, it1name, it2name, ppred, predname, src1, src2,
|
||||
n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template
|
||||
<class T, class InputIterator1, class InputIterator2, class Predicate>
|
||||
void test_includes (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
const char* const it1name = type_name (it1, (T*)0);
|
||||
const char* const it2name = type_name (it2, (T*)0);
|
||||
const char* const fname = "includes";
|
||||
const char* const predname = Predicate::name ();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s(%s, %2$s, %s, %3$s%{?}, %s%{;})",
|
||||
fname, it1name, it2name, ppred, predname);
|
||||
|
||||
#define TEST(src1, src2, res) \
|
||||
test_includes (__LINE__, src1, src2, res, it1, it2, (T*)0, ppred)
|
||||
|
||||
TEST ("", "", true);
|
||||
TEST ("a", "", true);
|
||||
TEST ("", "a", false);
|
||||
|
||||
TEST ("a", "a", true);
|
||||
TEST ("a", "b", false);
|
||||
TEST ("b", "a", false);
|
||||
|
||||
TEST ("aa", "aa", true);
|
||||
TEST ("aa", "ab", false);
|
||||
TEST ("ab", "aa", false);
|
||||
TEST ("ab", "ab", true);
|
||||
|
||||
TEST ("abcdef", "b", true);
|
||||
TEST ("abcdef", "bd", true);
|
||||
TEST ("abcdef", "i", false);
|
||||
TEST ("abcdef", "ei", false);
|
||||
|
||||
TEST ("abcde", "abcde", true);
|
||||
TEST ("abbde", "abbde", true);
|
||||
TEST ("abcce", "abcce", true);
|
||||
TEST ("abcdd", "abcdd", true);
|
||||
|
||||
TEST ("ab", "aaabbbb", false);
|
||||
TEST ("ab", "aaabbbc", false);
|
||||
TEST ("aaabbbb", "ab", true);
|
||||
TEST ("aaabbbc", "ac", true);
|
||||
|
||||
TEST ("a", "aaaaaaaa", false);
|
||||
TEST ("a", "aaaaaaab", false);
|
||||
|
||||
TEST ("aaaaaaaa", "aaaaaaaa", true);
|
||||
TEST ("aaaaaaab", "aaaaaaab", true);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class InputIterator1, class Predicate>
|
||||
void test_includes (const InputIterator1 &it1,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (it1, input_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (it1, fwd_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (it1, bidir_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (it1, rand_iter, (T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_includes (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s%{?}, class %s%{;}> "
|
||||
"bool std::includes (%1$s, %1$s, %2$s, %2$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2", ppred, "Compare",
|
||||
ppred, "Compare");
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (input_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (fwd_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (bidir_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes (rand_iter, (T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
test_includes ((UserClass*)0, (Less<UserClass>*)0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::includes predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_includes ((UserClass*)0, (Less<UserClass>*)1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.includes",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
334
extern/stdcxx/4.2.1/tests/algorithms/25.lex.comparison.cpp
vendored
Normal file
334
extern/stdcxx/4.2.1/tests/algorithms/25.lex.comparison.cpp
vendored
Normal file
@@ -0,0 +1,334 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.lex.comparison.cpp - test exercising 25.3.8 [lib.lex.comparison]
|
||||
*
|
||||
* $Id: 25.lex.comparison.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for lexicographical_compare
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
// explicitly instantiate on types with minimum features
|
||||
// to verify that the algorithm imposes no requirements
|
||||
// beyond those specified
|
||||
template
|
||||
bool lexicographical_compare (InputIter<lt_comp<base<> > >,
|
||||
InputIter<lt_comp<base<> > >,
|
||||
InputIter<lt_comp<base<> > >,
|
||||
InputIter<lt_comp<base<> > >);
|
||||
template
|
||||
bool lexicographical_compare (InputIter<base<> >,
|
||||
InputIter<base<> >,
|
||||
InputIter<base<> >,
|
||||
InputIter<base<> >,
|
||||
binary_predicate<base<> >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercise lexicographical_compare 25.3.8
|
||||
template
|
||||
<class T, class InputIterator1, class InputIterator2, class Predicate>
|
||||
void test_lex_compare (int line,
|
||||
const char *src1,
|
||||
const char *src2,
|
||||
bool res,
|
||||
const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
const char* const it1name = type_name (it1, (T*)0);
|
||||
const char* const it2name = type_name (it2, (T*)0);
|
||||
const char* const fname = "lexicographical_compare";
|
||||
const char* const funname = Predicate::name ();
|
||||
|
||||
const std::size_t nsrc1 = std::strlen (src1);
|
||||
const std::size_t nsrc2 = std::strlen (src2);
|
||||
|
||||
T* const xsrc1 = T::from_char (src1, nsrc1);
|
||||
T* const xsrc2 = T::from_char (src2, nsrc2);
|
||||
|
||||
T* const xsrc1_end = xsrc1 + nsrc1;
|
||||
T* const xsrc2_end = xsrc2 + nsrc2;
|
||||
|
||||
const InputIterator1 first1 = make_iter (xsrc1, xsrc1, xsrc1_end, it1);
|
||||
const InputIterator1 last1 = make_iter (xsrc1_end, xsrc1, xsrc1_end, it1);
|
||||
const InputIterator2 first2 = make_iter (xsrc2, xsrc2, xsrc2_end, it2);
|
||||
const InputIterator2 last2 = make_iter (xsrc2_end, xsrc2, xsrc2_end, it2);
|
||||
|
||||
const Predicate pred (0, 0);
|
||||
|
||||
const std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
|
||||
const bool result = ppred ?
|
||||
std::lexicographical_compare (first1, last1, first2, last2, pred)
|
||||
: std::lexicographical_compare (first1, last1, first2, last2);
|
||||
|
||||
// verify the returned value 25.3.8, p1 and p3: If two sequences have
|
||||
// the same number of elements and their corresponding elements are
|
||||
// equivalent, then neither sequence is lexicographically less than
|
||||
// the other.
|
||||
rw_assert (res == result, 0, line,
|
||||
"line %d: %s<%s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"== %b, got %b",
|
||||
__LINE__, fname, it1name, it2name, 0 != ppred, funname,
|
||||
src1, src2, res, result);
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// verify the complexity 25.3.8, p2
|
||||
const std::size_t n_exp_ops = 2 * (nsrc1 < nsrc2 ? nsrc1 : nsrc2);
|
||||
rw_assert (n_ops_lt <= n_exp_ops, 0, line,
|
||||
"line %d: %s<%s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"complexity: got %zu, expected no more than %zu",
|
||||
__LINE__, fname, it1name, it2name, 0 != ppred, funname,
|
||||
src1, src2, n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
}
|
||||
|
||||
template
|
||||
<class T, class InputIterator1, class InputIterator2, class Predicate>
|
||||
void test_lex_compare (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
const char* const it1name = type_name (it1, (T*)0);
|
||||
const char* const it2name = type_name (it2, (T*)0);
|
||||
const char* const fname = "lexicographical_compare";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s(%s, %2$s, %s, %3$s%{?}, %s%{;})",
|
||||
fname, it1name, it2name, 0 != ppred, funname);
|
||||
|
||||
#define TEST(src1, src2, res) \
|
||||
test_lex_compare (__LINE__, src1, src2, res, it1, it2, (T*)0, ppred)
|
||||
|
||||
TEST ("", "", false);
|
||||
TEST ("a", "", false);
|
||||
TEST ("", "a", true);
|
||||
TEST ("a", "a", false);
|
||||
|
||||
TEST ("aa", "aa", false);
|
||||
TEST ("aa", "ab", true);
|
||||
TEST ("ba", "ab", false);
|
||||
TEST ("ba", "ba", false);
|
||||
TEST ("ba", "bc", true);
|
||||
|
||||
TEST ("a", "abc", true);
|
||||
TEST ("a", "bcd", true);
|
||||
TEST ("a", "baed", true);
|
||||
|
||||
TEST ("abcde", "abcdefghij", true);
|
||||
TEST ("fghij", "fghijabcde", true);
|
||||
TEST ("fghij", "abcdefghij", false);
|
||||
TEST ("cabed", "abcdeabcde", false);
|
||||
|
||||
TEST ("abcdefghij", "abcdefghij", false);
|
||||
TEST ("fghijfghij", "abcdefghij", false);
|
||||
TEST ("fghijabcde", "abcdeabcde", false);
|
||||
|
||||
TEST ("abcdefghij", "bacdfeghji", true);
|
||||
TEST ("bacdefghij", "bacdfeghji", true);
|
||||
TEST ("bacdfeghij", "bacdfeghji", true);
|
||||
TEST ("bacdfeghja", "bacdfeghji", true);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class InputIterator1, class Predicate>
|
||||
void test_lex_compare (const InputIterator1 &it1,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (it1, input_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (it1, fwd_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (it1, bidir_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (it1, rand_iter, (T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_lex_compare (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s%{?}, class %s%{;}> "
|
||||
"bool std::lexicographical_compare (%1$s, %1$s, %2$s, "
|
||||
"%2$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2", ppred, "Compare",
|
||||
0 != ppred, "Compare");
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (input_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (fwd_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (bidir_iter, (T*)0, ppred);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare (rand_iter, (T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
test_lex_compare ((UserClass*)0, (Less<UserClass>*)0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::lexicographical_compare predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_lex_compare ((UserClass*)0, (Less<UserClass>*)1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.lex.comparison",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
420
extern/stdcxx/4.2.1/tests/algorithms/25.libc.cpp
vendored
Normal file
420
extern/stdcxx/4.2.1/tests/algorithms/25.libc.cpp
vendored
Normal file
@@ -0,0 +1,420 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.libc.cpp - test exercising 25.4 [lib.alg.c.library]
|
||||
*
|
||||
* $Id: 25.libc.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
***************************************************************************/
|
||||
|
||||
#include <cstdlib> // for bsearch, qsort
|
||||
#include <csignal> // for signal
|
||||
#include <csetjmp> // for setjmp, longjmp
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// used as a special value in comp below
|
||||
static int global[] = { 0, 0 };
|
||||
|
||||
|
||||
extern "C" {
|
||||
|
||||
static std::jmp_buf jmp_env;
|
||||
|
||||
// SIGABRT handler
|
||||
static void handle_ABRT (int)
|
||||
{
|
||||
// jump outta here to prevent abort() from trying too hard...
|
||||
std::longjmp (jmp_env, 1);
|
||||
}
|
||||
|
||||
|
||||
static int c_comp (const void *x, const void *y)
|
||||
{
|
||||
#ifndef _RWSTD_NO_EXCEPTIONS
|
||||
|
||||
// verify that a thrown exception can be caught
|
||||
if (x >= global && x < global + sizeof global / sizeof *global)
|
||||
throw x;
|
||||
|
||||
#endif // _RWSTD_NO_EXCEPTIONS
|
||||
|
||||
return (*_RWSTD_STATIC_CAST (const UserClass*, x)).data_.val_
|
||||
- (*_RWSTD_STATIC_CAST (const UserClass*, y)).data_.val_;
|
||||
}
|
||||
}
|
||||
|
||||
extern "C++" {
|
||||
|
||||
static int cxx_comp (const void *x, const void *y)
|
||||
{
|
||||
#ifndef _RWSTD_NO_EXCEPTIONS
|
||||
|
||||
// verify that a thrown exception can be caught
|
||||
if (x >= global && x < global + sizeof global / sizeof *global)
|
||||
throw x;
|
||||
|
||||
#endif // _RWSTD_NO_EXCEPTIONS
|
||||
|
||||
return (*_RWSTD_STATIC_CAST (const UserClass*, x)).data_.val_
|
||||
- (*_RWSTD_STATIC_CAST (const UserClass*, y)).data_.val_;
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exrcises std::qqsort (25.4.4)
|
||||
static void
|
||||
test_qsort (int line,
|
||||
const char *src,
|
||||
std::size_t nsrc,
|
||||
bool cxx)
|
||||
{
|
||||
UserClass* const xsrc = UserClass::from_char (src, nsrc);
|
||||
UserClass* const xsrc_end = xsrc + nsrc;
|
||||
RW_ASSERT (0 == nsrc || 0 != xsrc);
|
||||
|
||||
if (cxx)
|
||||
std::qsort (xsrc, nsrc, sizeof *xsrc, cxx_comp);
|
||||
else
|
||||
std::qsort (xsrc, nsrc, sizeof *xsrc, c_comp);
|
||||
|
||||
bool success = is_sorted_lt (xsrc, xsrc_end);
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: extern \"C%{?}++%{;}\" qsort (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\" not sorted",
|
||||
__LINE__, cxx, src, int (nsrc), -1, xsrc);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exrcises std::qsort (25.4.4 Note)
|
||||
static void
|
||||
test_qsort_exception (int line,
|
||||
int *src,
|
||||
std::size_t nsrc,
|
||||
bool cxx)
|
||||
{
|
||||
#ifndef _RWSTD_NO_EXCEPTIONS
|
||||
|
||||
// install a SIGABRT handler in case libc can't throw
|
||||
// exceptions and aborts instead (e.g., glibc/gcc)
|
||||
std::signal (SIGABRT, handle_ABRT);
|
||||
|
||||
bool success = false;
|
||||
try {
|
||||
if (0 == setjmp (jmp_env)) {
|
||||
if (cxx)
|
||||
std::qsort (src, nsrc, sizeof *src, cxx_comp);
|
||||
else
|
||||
std::qsort (src, nsrc, sizeof *src, c_comp);
|
||||
}
|
||||
else {
|
||||
// prevent double assertion
|
||||
success = true;
|
||||
rw_assert (false, 0, line,
|
||||
"line %d: extern \"C%{?}++%{;}\" qsort() aborted "
|
||||
"on exception", __LINE__, cxx);
|
||||
}
|
||||
}
|
||||
catch (const void* x) {
|
||||
success = x >= src && x < src + nsrc;
|
||||
}
|
||||
catch (...) {
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: extern \"C%{?}++%{;}\" qsort() failed to propagate "
|
||||
"exception", __LINE__, cxx);
|
||||
|
||||
#else // if defined (_RWSTD_NO_EXCEPTIONS)
|
||||
|
||||
_RWSTD_UNUSED (line);
|
||||
_RWSTD_UNUSED (src);
|
||||
_RWSTD_UNUSED (nsrc);
|
||||
_RWSTD_UNUSED (key);
|
||||
_RWSTD_UNUSED (cxx);
|
||||
|
||||
#endif // _RWSTD_NO_EXCEPTIONS
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exrcises std::bsearch (25.4.3)
|
||||
static void
|
||||
test_bsearch (int line,
|
||||
const char *src,
|
||||
std::size_t nsrc,
|
||||
const char key_val,
|
||||
std::size_t res,
|
||||
bool cxx)
|
||||
{
|
||||
UserClass* const xsrc = UserClass::from_char (src, nsrc,
|
||||
true); // must be sorted
|
||||
RW_ASSERT (0 == nsrc || 0 != xsrc);
|
||||
|
||||
UserClass key;
|
||||
key.data_.val_ = key_val;
|
||||
|
||||
const void* result = cxx ?
|
||||
std::bsearch (&key, xsrc, nsrc, sizeof *xsrc, cxx_comp)
|
||||
: std::bsearch (&key, xsrc, nsrc, sizeof *xsrc, c_comp);
|
||||
|
||||
const UserClass* exp_res = res == _RWSTD_SIZE_MAX ? 0 : xsrc + res;
|
||||
|
||||
bool success = result == exp_res;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: extern \"C%{?}++%{;}\" bsearch (\"%s\", %#c, ...) "
|
||||
"== %p, got %p, difference is %td elements",
|
||||
__LINE__, cxx, src, key_val, result, exp_res,
|
||||
_RWSTD_STATIC_CAST (const UserClass*, result) - exp_res);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exrcises std::bsearch (25.4.4 Note)
|
||||
static void
|
||||
test_bsearch_exception (int line,
|
||||
const int *src,
|
||||
std::size_t nsrc,
|
||||
const int *key,
|
||||
bool cxx)
|
||||
{
|
||||
#ifndef _RWSTD_NO_EXCEPTIONS
|
||||
|
||||
// install a SIGABRT handler in case libc can't throw
|
||||
// exceptions and aborts instead (e.g., glibc/gcc)
|
||||
std::signal (SIGABRT, handle_ABRT);
|
||||
|
||||
bool success = false;
|
||||
try {
|
||||
if (0 == setjmp (jmp_env)) {
|
||||
if (cxx)
|
||||
std::bsearch (key, src, nsrc, sizeof *src, cxx_comp);
|
||||
else
|
||||
std::bsearch (key, src, nsrc, sizeof *src, c_comp);
|
||||
}
|
||||
else {
|
||||
// prevent double assertion
|
||||
success = true;
|
||||
rw_assert (false, 0, line,
|
||||
"line %d: extern \"C%{?}++%{;}\" bsearch() aborted "
|
||||
"on exception", __LINE__, cxx);
|
||||
}
|
||||
}
|
||||
catch (const void* x) {
|
||||
success = x >= src && x < src + nsrc;
|
||||
}
|
||||
catch (...) {
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: extern \"C%{?}++%{;}\" bsearch() failed to propagate "
|
||||
"exception", __LINE__, cxx);
|
||||
|
||||
#else // if defined (_RWSTD_NO_EXCEPTIONS)
|
||||
|
||||
_RWSTD_UNUSED (line);
|
||||
_RWSTD_UNUSED (src);
|
||||
_RWSTD_UNUSED (nsrc);
|
||||
_RWSTD_UNUSED (key);
|
||||
_RWSTD_UNUSED (cxx);
|
||||
|
||||
#endif // _RWSTD_NO_EXCEPTIONS
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int rw_opt_no_c; // --no-c
|
||||
static int rw_opt_no_cxx; // --no-cpp
|
||||
static int rw_opt_no_bsearch; // --no-bsearch
|
||||
static int rw_opt_no_qsort; // --no-qsort
|
||||
static int rw_opt_no_exceptions; // --no-exceptions
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_qsort (bool cxx)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"extern \"C%{?}++%{;}\" qsort (void*, size_t, size_t, "
|
||||
"int (*compar)(const void*, const void*))", cxx);
|
||||
|
||||
#define TEST(src) \
|
||||
test_qsort (__LINE__, src, sizeof src - 1, cxx)
|
||||
|
||||
TEST ("a");
|
||||
|
||||
TEST ("ba");
|
||||
TEST ("cba");
|
||||
TEST ("dcba");
|
||||
TEST ("edcba");
|
||||
TEST ("fedcba");
|
||||
TEST ("gfedcba");
|
||||
TEST ("hgfedcba");
|
||||
TEST ("ihgfedcba");
|
||||
TEST ("jihgfedcba");
|
||||
|
||||
TEST ("ab");
|
||||
TEST ("abc");
|
||||
TEST ("abcd");
|
||||
TEST ("abcde");
|
||||
TEST ("abcdef");
|
||||
TEST ("abcdefg");
|
||||
TEST ("abcdefgh");
|
||||
TEST ("abcdefghi");
|
||||
TEST ("abcdefghij");
|
||||
|
||||
TEST ("aa");
|
||||
TEST ("aabb");
|
||||
TEST ("bbccaa");
|
||||
TEST ("ddbbccaa");
|
||||
TEST ("ddeebbccaa");
|
||||
|
||||
TEST ("aaaaaaaaaa");
|
||||
TEST ("ababababab");
|
||||
TEST ("bababababa");
|
||||
|
||||
#undef TEST
|
||||
|
||||
if (rw_opt_no_exceptions) {
|
||||
rw_note (0, 0, 0, "extern \"C%{?}++%{;}\" qsort() exceptions tests "
|
||||
"disabled", cxx);
|
||||
}
|
||||
else {
|
||||
test_qsort_exception (__LINE__, global,
|
||||
sizeof global / sizeof *global, cxx);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_bsearch (bool cxx)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"extern \"C%{?}++%{;}\" bsearch (const void*, const void*, "
|
||||
"size_t, size_t, int (*compar)(const void*, const void*))",
|
||||
cxx);
|
||||
|
||||
#define TEST(src, key, res) \
|
||||
test_bsearch (__LINE__, src, sizeof src - 1, key, \
|
||||
std::size_t (res), cxx)
|
||||
|
||||
TEST ("", 'a', -1);
|
||||
TEST ("a", 'a', 0);
|
||||
TEST ("a", 'b', -1);
|
||||
TEST ("b", 'a', -1);
|
||||
|
||||
TEST ("ab", 'a', 0);
|
||||
TEST ("ac", 'a', 0);
|
||||
TEST ("ab", 'b', 1);
|
||||
TEST ("bc", 'a', -1);
|
||||
|
||||
TEST ("acegi", 'i', 4);
|
||||
TEST ("acegi", 'b', -1);
|
||||
TEST ("acegi", 'g', 3);
|
||||
TEST ("acegi", 'f', -1);
|
||||
TEST ("acegi", 'e', 2);
|
||||
TEST ("acegi", 'j', -1);
|
||||
TEST ("acegi", 'c', 1);
|
||||
TEST ("bdfhj", 'a', -1);
|
||||
|
||||
TEST ("abcdefghij", 'a', 0);
|
||||
TEST ("abcdefghij", 'c', 2);
|
||||
TEST ("abcdefghij", 'f', 5);
|
||||
TEST ("abcdefghij", 'h', 7);
|
||||
TEST ("abcdefghij", 'j', 9);
|
||||
|
||||
#undef TEST
|
||||
|
||||
if (rw_opt_no_exceptions) {
|
||||
rw_note (0, 0, 0, "extern \"C%{?}++%{;}\" bsearch() exceptions "
|
||||
"tests disabled", cxx);
|
||||
}
|
||||
else {
|
||||
test_bsearch_exception (__LINE__, global,
|
||||
sizeof global / sizeof *global, global, cxx);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_libc (bool cxx)
|
||||
{
|
||||
if (rw_opt_no_qsort)
|
||||
rw_note (0, 0, 0, "qsort test disabled");
|
||||
else
|
||||
test_qsort (cxx);
|
||||
|
||||
if (rw_opt_no_bsearch)
|
||||
rw_note (0, 0, 0, "bsearch test disabled");
|
||||
else
|
||||
test_bsearch (cxx);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_c)
|
||||
rw_note (0, 0, 0, "tests of extern \"C\" cfunctions disabled");
|
||||
else
|
||||
test_libc (false);
|
||||
|
||||
if (rw_opt_no_cxx)
|
||||
rw_note (0, 0, 0, "tests of extern \"C++\" functions disabled");
|
||||
else
|
||||
test_libc (true);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.c.library",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-extern_c# "
|
||||
"|-no-extern_cxx# "
|
||||
"|-no-bsearch# "
|
||||
"|-no-qsort# "
|
||||
"|-no-exceptions",
|
||||
&rw_opt_no_c,
|
||||
&rw_opt_no_cxx,
|
||||
&rw_opt_no_bsearch,
|
||||
&rw_opt_no_qsort,
|
||||
&rw_opt_no_exceptions);
|
||||
}
|
||||
286
extern/stdcxx/4.2.1/tests/algorithms/25.lower.bound.cpp
vendored
Normal file
286
extern/stdcxx/4.2.1/tests/algorithms/25.lower.bound.cpp
vendored
Normal file
@@ -0,0 +1,286 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.lower.bound.cpp - test exercising 25.3.3.1 [lib.lower.bound]
|
||||
*
|
||||
* $Id: 25.lower.bound.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <rw/_config.h>
|
||||
|
||||
#if defined (__IBMCPP__) && !defined (_RWSTD_NO_IMPLICIT_INCLUSION)
|
||||
// disable implicit inclusion to work around a limitation
|
||||
// of IBM VisualAge 5.0 (see PR #26959)
|
||||
# define _RWSTD_NO_IMPLICIT_INCLUSION
|
||||
#endif
|
||||
|
||||
#include <algorithm>
|
||||
#include <cstring>
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h>
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// distinct and not Less-Than-Comparable with class UserClass (except as
|
||||
// defined below) to detect unwarranted assumptions made by the
|
||||
// implementation of the algorithms
|
||||
struct Y
|
||||
{
|
||||
UserClass xval_;
|
||||
|
||||
// not Default-Constructible
|
||||
Y (int /* dummy */, int /*dummy */): xval_ () { }
|
||||
|
||||
// CopyConstructible
|
||||
Y (const Y &rhs): xval_ (rhs.xval_) { }
|
||||
|
||||
private:
|
||||
|
||||
void operator=(Y&); // not Assignable
|
||||
};
|
||||
|
||||
inline conv_to_bool
|
||||
operator< (const UserClass &lhs, const Y &rhs)
|
||||
{
|
||||
return conv_to_bool::make (lhs < rhs.xval_);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// predicate used as the Compare argument to lower_bound()
|
||||
struct LessThan
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
LessThan (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &lhs, const Y &rhs) {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (lhs < rhs.xval_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (LessThan&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t LessThan::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator>
|
||||
void test_lower_bound (int line,
|
||||
const char *src_str,
|
||||
char val_char,
|
||||
std::size_t result_off,
|
||||
std::size_t ncomp,
|
||||
const ForwardIterator*,
|
||||
const char *itname,
|
||||
bool predicate)
|
||||
{
|
||||
RW_ASSERT (0 != src_str);
|
||||
|
||||
const std::size_t nsrc = std::strlen (src_str);
|
||||
UserClass* const xsrc = UserClass::from_char (src_str, nsrc);
|
||||
|
||||
if (nsrc < result_off)
|
||||
result_off = nsrc;
|
||||
|
||||
// construct the source range to pass to the algorithm
|
||||
const ForwardIterator first (xsrc, xsrc, xsrc + nsrc);
|
||||
const ForwardIterator last (xsrc + nsrc, xsrc + nsrc, xsrc + nsrc);
|
||||
|
||||
// construct the object to pass to the algorithm
|
||||
// the type of the object is distinct from the iterator's value_type
|
||||
// to detect unwarranted assumptions made by the implementation
|
||||
Y value (0, 0 /* dummy arguments */);
|
||||
value.xval_.data_.val_ = val_char;
|
||||
|
||||
// construct the Compare function object to pass to the algorithm
|
||||
// when `predicate' is true
|
||||
const LessThan comp (0, 0 /* dummy arguments */);
|
||||
|
||||
// reset the counter of invocations of UserClass::operator<()
|
||||
UserClass::n_total_op_lt_ = 0;
|
||||
|
||||
// invoke the appropriate form of the algorithm, storing
|
||||
// the resturned value
|
||||
const ForwardIterator result = predicate
|
||||
? std::lower_bound (first, last, value, comp)
|
||||
: std::lower_bound (first, last, value);
|
||||
|
||||
// silence bogus EDG eccp 3.6 remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (result);
|
||||
|
||||
// verify correctness
|
||||
const std::size_t off = std::size_t (result.cur_ - xsrc);
|
||||
|
||||
rw_assert (off == result_off, 0, line,
|
||||
"lower_bound(%s = \"%s\", ...%{?}%#c%{;}) ==> "
|
||||
"first + %zu, got %zu",
|
||||
itname, src_str, !predicate, val_char,
|
||||
off, result_off);
|
||||
|
||||
// verify complexity
|
||||
const std::size_t funcalls = predicate
|
||||
? LessThan::funcalls_ : UserClass::n_total_op_lt_;
|
||||
|
||||
rw_assert (funcalls <= ncomp, 0, line,
|
||||
"lower_bound(%s = \"%s\", ...%{?}%#c%{;}) complexity: "
|
||||
"invoked predicate at most %zu times, got %zu",
|
||||
itname, src_str, !predicate, val_char,
|
||||
ncomp, funcalls);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator>
|
||||
void test_lower_bound (const ForwardIterator*,
|
||||
const char *itname,
|
||||
bool predicate)
|
||||
{
|
||||
#define TEST(str, val, off, comp) \
|
||||
test_lower_bound (__LINE__, str, val, std::size_t (off), \
|
||||
std::size_t (comp), (ForwardIterator*)0, \
|
||||
itname, predicate)
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::lower_bound (%s, %1$s, const UserClass&%{?}, %s%{;})",
|
||||
itname, predicate, "LessThan");
|
||||
|
||||
// +--------------- source sequence
|
||||
// | +--------- value argument
|
||||
// | | +----- offset of the resturned iterator, -1 for end
|
||||
// | | | +-- complexity: at most (log(last - first) + 1)
|
||||
// | | | | comparisons (or applications of the predicate)
|
||||
// | | | |
|
||||
// V V V V
|
||||
TEST ("", 'a', 0, 0);
|
||||
TEST ("a", 'a', 0, 1);
|
||||
TEST ("a", 'b', 1, 1);
|
||||
TEST ("b", 'a', 0, 1);
|
||||
|
||||
TEST ("aa", 'a', 0, 2);
|
||||
TEST ("ab", 'a', 0, 2);
|
||||
TEST ("ab", 'b', 1, 2);
|
||||
TEST ("bb", 'a', 0, 2);
|
||||
|
||||
TEST ("ace", 'a', 0, 3);
|
||||
TEST ("ace", 'b', 1, 3);
|
||||
TEST ("ace", 'c', 1, 3);
|
||||
TEST ("ace", 'd', 2, 3);
|
||||
TEST ("ace", 'e', 2, 3);
|
||||
TEST ("ace", 'f', 3, 3);
|
||||
|
||||
TEST ("aceg", 'a', 0, 3);
|
||||
TEST ("aceg", 'b', 1, 3);
|
||||
TEST ("aceg", 'c', 1, 3);
|
||||
TEST ("aceg", 'd', 2, 3);
|
||||
TEST ("aceg", 'e', 2, 3);
|
||||
TEST ("aceg", 'f', 3, 3);
|
||||
TEST ("aceg", 'g', 3, 3);
|
||||
TEST ("aceg", 'h', 4, 3);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int rw_opt_no_fwd_iter;
|
||||
static int rw_opt_no_bidir_iter;
|
||||
static int rw_opt_no_rnd_iter;
|
||||
static int rw_opt_no_predicate;
|
||||
|
||||
|
||||
static void
|
||||
test_lower_bound (bool predicate)
|
||||
{
|
||||
rw_info (0, 0, 0, "template <class %s, class %s%{?}, class %s%{;}> "
|
||||
"std::lower_bound (%1$s, %1$s, const UserClass&%{?}, %4$s%{;})",
|
||||
"ForwardIterator", "UserClass", predicate, "Compare", predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lower_bound ((FwdIter<UserClass>*)0, "ForwardIterator", predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lower_bound ((BidirIter<UserClass>*)0, "BidirectionalIterator",
|
||||
predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_lower_bound ((RandomAccessIter<UserClass>*)0,
|
||||
"RandomAccessIterator", predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_lower_bound (false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"test of the Predicate form of std::lower_bound disabled");
|
||||
}
|
||||
else {
|
||||
test_lower_bound (true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.lower.bound",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-Predicate# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
576
extern/stdcxx/4.2.1/tests/algorithms/25.merge.cpp
vendored
Normal file
576
extern/stdcxx/4.2.1/tests/algorithms/25.merge.cpp
vendored
Normal file
@@ -0,0 +1,576 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.merge.cpp - test exercising 25.3.4 [lib.alg.merge]
|
||||
*
|
||||
* $Id: 25.merge.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for merge,
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
merge (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
merge (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
inplace_merge (BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
inplace_merge (BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &x,
|
||||
const UserClass &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t Less::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// ordinary (non-template) base to minimize code bloat
|
||||
struct MergeBase
|
||||
{
|
||||
const char* iter_names [3];
|
||||
|
||||
virtual ~MergeBase () { }
|
||||
|
||||
// invokes inplace_merge with iterators initialized
|
||||
// to the specified arguments and (optionally) with
|
||||
// a predicate object
|
||||
virtual void
|
||||
inplace_merge (UserClass*, UserClass*, UserClass*, const Less*) const {
|
||||
RW_ASSERT (!"test logic error");
|
||||
}
|
||||
|
||||
// invokes merge
|
||||
virtual UserClass*
|
||||
merge (const UserClass*, const UserClass*, const UserClass*,
|
||||
const UserClass*, UserClass*, UserClass*, const Less*) const {
|
||||
RW_ASSERT (!"test logic error");
|
||||
return 0;
|
||||
}
|
||||
};
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
struct Merge: MergeBase
|
||||
{
|
||||
Merge () {
|
||||
iter_names [0] = type_name (InputIterator1 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [1] = type_name (InputIterator2 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [2] = type_name (OutputIterator (0, 0, 0), (UserClass*)0);
|
||||
}
|
||||
|
||||
virtual UserClass*
|
||||
merge (const UserClass *xsrc1, const UserClass *xsrc1_end,
|
||||
const UserClass *xsrc2, const UserClass *xsrc2_end,
|
||||
UserClass *xdst, UserClass *xdst_end,
|
||||
const Less *ppred) const {
|
||||
|
||||
const InputIterator1 first1 (xsrc1, xsrc1, xsrc1_end);
|
||||
const InputIterator1 last1 (xsrc1_end, xsrc1, xsrc1_end);
|
||||
const InputIterator2 first2 (xsrc2, xsrc2, xsrc2_end);
|
||||
const InputIterator2 last2 (xsrc2_end, xsrc2, xsrc2_end);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst_end);
|
||||
|
||||
const OutputIterator ret = ppred ?
|
||||
std::merge (first1, last1, first2, last2, result, *ppred)
|
||||
: std::merge (first1, last1, first2, last2, result);
|
||||
|
||||
// silence EDG eccp 3.7 and prior remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (ret);
|
||||
|
||||
return ret.cur_;
|
||||
}
|
||||
};
|
||||
|
||||
template <class BidirectionalIterator>
|
||||
struct InplaceMerge: MergeBase
|
||||
{
|
||||
InplaceMerge () {
|
||||
iter_names [0] = type_name (BidirectionalIterator (0, 0, 0),
|
||||
(UserClass*)0);
|
||||
iter_names [1] = 0;
|
||||
iter_names [2] = 0;
|
||||
}
|
||||
|
||||
virtual void
|
||||
inplace_merge (UserClass *xsrc, UserClass *xsrc_mid, UserClass *xsrc_end,
|
||||
const Less *ppred) const {
|
||||
|
||||
const BidirectionalIterator first (xsrc, xsrc, xsrc_end);
|
||||
const BidirectionalIterator mid (xsrc_mid, xsrc, xsrc_end);
|
||||
const BidirectionalIterator last (xsrc_end, xsrc, xsrc_end);
|
||||
|
||||
if (ppred)
|
||||
std::inplace_merge (first, mid, last, *ppred);
|
||||
else
|
||||
std::inplace_merge (first, mid, last);
|
||||
}
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// ordinary (non-template) function to minimize code bloat
|
||||
void test_merge (int line,
|
||||
const char *src1,
|
||||
const char *src2,
|
||||
const std::size_t midinx,
|
||||
bool predicate,
|
||||
const MergeBase &alg)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const predname = predicate ? "Less" : 0;
|
||||
const bool inplace = 0 == it2name;
|
||||
const char* const algname = inplace ? "inplace_merge" : "merge";
|
||||
|
||||
const std::size_t nsrc1 = std::strlen (src1);
|
||||
const std::size_t nsrc2 = std::strlen (src2);
|
||||
|
||||
UserClass* const xsrc1 = UserClass::from_char (src1, nsrc1);
|
||||
UserClass* const xsrc2 = UserClass::from_char (src2, nsrc2);
|
||||
|
||||
const std::size_t ndst = nsrc1 + nsrc2;
|
||||
UserClass* const xdst = inplace ? xsrc1 : new UserClass [ndst];
|
||||
|
||||
UserClass* const xsrc1_end = xsrc1 + nsrc1;
|
||||
UserClass* const xsrc2_end = xsrc2 + nsrc2;
|
||||
UserClass* const xsrc_mid = xsrc1 + midinx;
|
||||
UserClass* const xdst_end = xdst + ndst;
|
||||
|
||||
const std::size_t last_n_op_lt = UserClass::n_total_op_lt_;
|
||||
|
||||
const Less pred (0, 0);
|
||||
const Less* const ppred = predicate ? &pred : 0;
|
||||
|
||||
UserClass* xdst_res = 0;
|
||||
|
||||
if (inplace) { // inplace_merge
|
||||
alg.inplace_merge (xsrc1, xsrc_mid, xsrc1_end, ppred);
|
||||
}
|
||||
else {
|
||||
xdst_res = alg.merge (xsrc1, xsrc1_end,
|
||||
xsrc2, xsrc2_end, xdst, xdst_end, ppred);
|
||||
}
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Less::funcalls_ : UserClass::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
bool success = true;
|
||||
|
||||
// check output iterator for merge
|
||||
if (!inplace) {
|
||||
success = xdst_res == xdst_end;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...)"
|
||||
" == first + %zu, got first + %td",
|
||||
__LINE__, algname, it1name, it2name, outname, predicate,
|
||||
predname, src1, src2, ndst, xdst_res - xdst);
|
||||
}
|
||||
|
||||
// check that the sequence is sorted
|
||||
success = is_sorted_lt (xdst, xdst_end);
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s, %s%{;}%{?}, %s%{;}> "
|
||||
"(\"%s\", %{?}\"%s\"%{;}%{?}%zu%{;}, ...) ==> \"%{X=*.*}\" "
|
||||
"not sorted",
|
||||
__LINE__, algname, it1name, !inplace, it2name, outname,
|
||||
predicate, predname, src1, !inplace, src2, inplace, midinx,
|
||||
int (ndst), -1, xdst);
|
||||
|
||||
// check that the algorithm is stable
|
||||
std::size_t i = 1;
|
||||
for ( ; i < ndst; i++) {
|
||||
if (xdst [i - 1].data_.val_ == xdst [i].data_.val_) {
|
||||
success = xdst [i - 1].origin_ < xdst [i].origin_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s, %s%{;}%{?}, %s%{;}> "
|
||||
"(\"%s\", %{?}\"%s\"%{;}%{?}%zu%{;}, ...) ==> \"%{X=*.*}\" "
|
||||
"not stable at %zu: got ids %d != %d for values %#c == %#c",
|
||||
__LINE__, algname, it1name, !inplace, it2name, outname,
|
||||
predicate, predname, src1, !inplace, src2, inplace, midinx,
|
||||
int (ndst), i, xdst, i, xdst [i - 1].origin_,
|
||||
xdst [i].origin_, xdst [i - 1].data_.val_, xdst [i].data_.val_);
|
||||
|
||||
// check the complexity
|
||||
success = n_ops_lt <= ndst - 1;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s, %s%{;}%{?}, %s%{;}> "
|
||||
"(\"%s\", %{?}\"%s\"%{;}%{?}%zu%{;}, ...) ==> \"%{X=*.*}\" "
|
||||
"complexity: got %zu, expected <= %zu",
|
||||
__LINE__, algname, it1name, !inplace, it2name, outname,
|
||||
predicate, predname, src1, !inplace, src2, inplace, midinx,
|
||||
int (ndst), -1, xdst, n_ops_lt, ndst - 1);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
|
||||
if (!inplace)
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_merge (const MergeBase &alg, bool predicate)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const predname = predicate ? "Less" : 0;
|
||||
const char* const algname = it2name ? "merge" : "inplace_merge";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::%s(%s, %3$s, %s, %4$s, %1$s%{?}, %s%{;})",
|
||||
outname, algname, it1name, it2name, predicate, predname);
|
||||
|
||||
#define TEST(src1, src2) \
|
||||
test_merge (__LINE__, src1, src2, 0, predicate, alg)
|
||||
|
||||
TEST ("ab", "");
|
||||
TEST ("", "ab");
|
||||
|
||||
TEST ("a", "b");
|
||||
TEST ("b", "a");
|
||||
TEST ("aa", "bb");
|
||||
TEST ("bb", "aa");
|
||||
|
||||
TEST ("acegi", "bdfhj");
|
||||
TEST ("aaegi", "bdfjj");
|
||||
TEST ("accgi", "bdhhj");
|
||||
TEST ("aceei", "bffhj");
|
||||
TEST ("acegg", "ddfhj");
|
||||
TEST ("aceii", "bbfhj");
|
||||
|
||||
TEST ("bdfhj", "acegi");
|
||||
TEST ("bdfjj", "aaegi");
|
||||
TEST ("bdhhj", "accgi");
|
||||
TEST ("bffhj", "aceei");
|
||||
TEST ("ddfhj", "acegg");
|
||||
TEST ("bbfhj", "aceii");
|
||||
|
||||
TEST ("abcde", "abcde");
|
||||
TEST ("aacde", "aacde");
|
||||
TEST ("abbde", "abbde");
|
||||
TEST ("abcce", "abcce");
|
||||
TEST ("abcdd", "abcdd");
|
||||
TEST ("abcee", "abcee");
|
||||
|
||||
TEST ("aaegi", "bdfjj");
|
||||
TEST ("accgi", "bdhhj");
|
||||
TEST ("aceei", "bffhj");
|
||||
TEST ("acegg", "ddfhj");
|
||||
TEST ("aceii", "bbfhj");
|
||||
|
||||
TEST ("a","abcdefghij");
|
||||
TEST ("ac","abcdefghi");
|
||||
TEST ("ace","abcdefgh");
|
||||
TEST ("aceg","abcdefg");
|
||||
|
||||
TEST ("j","abcdefghjj");
|
||||
TEST ("gj","abcdeggjj");
|
||||
TEST ("egj","abeeggjj");
|
||||
|
||||
TEST ("abcdefghij","a");
|
||||
TEST ("abcdefghi","ac");
|
||||
TEST ("abcdefgh","ace");
|
||||
TEST ("abcdefg","aceg");
|
||||
|
||||
TEST ("abcdefghjj","j");
|
||||
TEST ("abcdeggjj","gj");
|
||||
TEST ("abeeggjj","egj");
|
||||
|
||||
TEST ("aaaaa", "aaaaa");
|
||||
TEST ("bbbbb", "bbbbb");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_inplace_merge (const MergeBase &alg, bool predicate)
|
||||
{
|
||||
const char* const itname = alg.iter_names [0];
|
||||
const char* const predname = predicate ? "Less" : 0;
|
||||
const char* const algname = alg.iter_names [1] ?
|
||||
"merge" : "inplace_merge";
|
||||
|
||||
rw_info (0, 0, 0, "std::%s(%s, %2$s, %2$s%{?}, %s%{;})",
|
||||
algname, itname, predicate, predname);
|
||||
|
||||
#undef TEST
|
||||
#define TEST(src, mid) \
|
||||
test_merge (__LINE__, src, "", mid, predicate, alg)
|
||||
|
||||
TEST ("a", 0);
|
||||
TEST ("aa", 0);
|
||||
TEST ("a", 1);
|
||||
TEST ("aa", 2);
|
||||
|
||||
TEST ("aa", 1);
|
||||
TEST ("ab", 1);
|
||||
TEST ("ba", 1);
|
||||
|
||||
TEST ("abcdefghij", 5);
|
||||
TEST ("aacdeffhij", 5);
|
||||
TEST ("abbdefggij", 5);
|
||||
TEST ("abccefghhj", 5);
|
||||
TEST ("abcddfghii", 5);
|
||||
TEST ("abceefghjj", 5);
|
||||
|
||||
TEST ("abcdeabcde", 5);
|
||||
TEST ("aacdeaacde", 5);
|
||||
TEST ("abbdeabbde", 5);
|
||||
TEST ("abcceabcce", 5);
|
||||
TEST ("abcddabcdd", 5);
|
||||
TEST ("abceeabcee", 5);
|
||||
|
||||
TEST ("aabcdefghi", 1);
|
||||
TEST ("aaacdefghi", 1);
|
||||
TEST ("babcdefghi", 1);
|
||||
TEST ("babbdefghi", 1);
|
||||
|
||||
TEST ("abcdefghia", 9);
|
||||
TEST ("aacdefghia", 9);
|
||||
TEST ("abcdefghib", 9);
|
||||
TEST ("abbdefghib", 9);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_merge; // --no-merge
|
||||
/* extern */ int rw_opt_no_inplace_merge; // --no-inplace_merge
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
void gen_merge_test (const InputIterator1&,
|
||||
const InputIterator2&,
|
||||
const OutputIterator&,
|
||||
bool predicate)
|
||||
{
|
||||
const Merge<InputIterator1, InputIterator2, OutputIterator> alg;
|
||||
|
||||
test_merge (alg, predicate);
|
||||
}
|
||||
|
||||
template <class InputIterator1, class InputIterator2>
|
||||
void gen_merge_test (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_output_iter)
|
||||
gen_merge_test (it1, it2, OutputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_merge_test (it1, it2, FwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_merge_test (it1, it2, BidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_merge_test (it1, it2, RandomAccessIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
}
|
||||
|
||||
template <class InputIterator1>
|
||||
void gen_merge_test (const InputIterator1 &it1, bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_input_iter)
|
||||
gen_merge_test (it1, InputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_merge_test (it1, ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_merge_test (it1, ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_merge_test (it1, ConstRandomAccessIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
}
|
||||
|
||||
// generates a specialization of the merge test for each of the required
|
||||
// iterator categopries
|
||||
void gen_merge_test (bool predicate)
|
||||
{
|
||||
if (rw_opt_no_input_iter)
|
||||
rw_note (0, 0, 0, "InputIterator test disabled");
|
||||
else
|
||||
gen_merge_test (InputIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter)
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
else
|
||||
gen_merge_test (ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_bidir_iter)
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
else
|
||||
gen_merge_test (ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_rnd_iter)
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
else
|
||||
gen_merge_test (ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class BidirectionalIterator>
|
||||
void gen_inplace_merge_test (const BidirectionalIterator&, bool predicate)
|
||||
{
|
||||
const InplaceMerge<BidirectionalIterator> alg;
|
||||
|
||||
test_inplace_merge (alg, predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_predicate)
|
||||
rw_note (0, 0, 0, "predicate test disabled");
|
||||
|
||||
const int niters = rw_opt_no_predicate ? 1 : 2;
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_merge)
|
||||
rw_note (0, 0, 0, "merge test disabled");
|
||||
else {
|
||||
for (int i = 0; i != niters; ++i) {
|
||||
gen_merge_test (1 == i);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_inplace_merge) {
|
||||
rw_note (0, 0, 0, "inplace_merge test disabled");
|
||||
}
|
||||
else {
|
||||
for (int i = 0; i != niters; ++i) {
|
||||
|
||||
if (rw_opt_no_bidir_iter)
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
else
|
||||
gen_inplace_merge_test (BidirIter<UserClass> (0, 0, 0), 1 == i);
|
||||
|
||||
if (rw_opt_no_rnd_iter)
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
else
|
||||
gen_inplace_merge_test (RandomAccessIter<UserClass> (0, 0, 0),
|
||||
1 == i);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.merge",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-merge# "
|
||||
"|-no-inplace_merge# "
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_merge,
|
||||
&rw_opt_no_inplace_merge,
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
425
extern/stdcxx/4.2.1/tests/algorithms/25.min.max.cpp
vendored
Normal file
425
extern/stdcxx/4.2.1/tests/algorithms/25.min.max.cpp
vendored
Normal file
@@ -0,0 +1,425 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.min.max.cpp - test exercising 25.3.7 [lib.alg.min.max]
|
||||
*
|
||||
* $Id: 25.min.max.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for min, max, min_element, max_element
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
const lt_comp<base<cpy_ctor> >&
|
||||
min (const lt_comp<base<cpy_ctor> >&,
|
||||
const lt_comp<base<cpy_ctor> >&);
|
||||
|
||||
template
|
||||
const lt_comp<base<cpy_ctor> >&
|
||||
min (const lt_comp<base<cpy_ctor> >&,
|
||||
const lt_comp<base<cpy_ctor> >&,
|
||||
binary_predicate<lt_comp<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
const lt_comp<base<cpy_ctor> >&
|
||||
max (const lt_comp<base<cpy_ctor> >&,
|
||||
const lt_comp<base<cpy_ctor> >&);
|
||||
|
||||
template
|
||||
const lt_comp<base<cpy_ctor> >&
|
||||
max (const lt_comp<base<cpy_ctor> >&,
|
||||
const lt_comp<base<cpy_ctor> >&,
|
||||
binary_predicate<lt_comp<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >
|
||||
min_element (FwdIter<lt_comp<base<cpy_ctor> > >,
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >
|
||||
min_element (FwdIter<lt_comp<base<cpy_ctor> > >,
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >,
|
||||
binary_predicate<lt_comp<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >
|
||||
max_element (FwdIter<lt_comp<base<cpy_ctor> > >,
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >
|
||||
max_element (FwdIter<lt_comp<base<cpy_ctor> > >,
|
||||
FwdIter<lt_comp<base<cpy_ctor> > >,
|
||||
binary_predicate<lt_comp<base<cpy_ctor> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises min, max: 25.3.7
|
||||
template <class T, class Predicate>
|
||||
void test_min_max (int line,
|
||||
const char a,
|
||||
const char b,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool test_min)
|
||||
{
|
||||
const char* const tname = "UserClass";
|
||||
const char* const fname = test_min ? "min" : "max";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
T ta, tb;
|
||||
ta.data_.val_ = a;
|
||||
tb.data_.val_ = b;
|
||||
|
||||
const int exp_id =
|
||||
test_min ? b < a ? tb.id_ : ta.id_ : b > a ? tb.id_ : ta.id_;
|
||||
|
||||
const char exp_res = test_min ? b < a ? b : a : b > a ? b : a;
|
||||
|
||||
const Predicate pred (0, 0); // dummy arguments
|
||||
|
||||
const T& res = ppred ?
|
||||
test_min ? std::min (ta, tb, pred) : std::max (ta, tb, pred)
|
||||
: test_min ? std::min (ta, tb) : std::max (ta, tb);
|
||||
|
||||
// verify 25.3.7 p2, p3, p5, p6
|
||||
rw_assert (exp_res == res.data_.val_ && exp_id == res.origin_, 0, line,
|
||||
"line %d %s <%s%{?}, %s%{;}> (%#c, %#c) returned "
|
||||
"value %#c, id %d; expected value %#c, id %d",
|
||||
__LINE__, fname, tname, 0 != ppred, funname, a, b,
|
||||
res.data_.val_, res.origin_, exp_res, exp_id);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exrcises min_element, max_element: 25.3.7
|
||||
template <class T, class ForwardIterator, class Predicate>
|
||||
void test_min_max_element (int line,
|
||||
const char *src,
|
||||
const std::size_t min_off,
|
||||
const std::size_t max_off,
|
||||
const ForwardIterator &it,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool test_min)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = test_min ? "min_element" : "max_element";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
const ForwardIterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const ForwardIterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
Predicate pred (0, 0);
|
||||
|
||||
const std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
|
||||
ForwardIterator res (0, 0, 0);
|
||||
|
||||
if (ppred) {
|
||||
res = test_min ?
|
||||
std::min_element (first, last, pred)
|
||||
: std::max_element (first, last, pred);
|
||||
}
|
||||
else {
|
||||
res = test_min ?
|
||||
std::min_element (first, last)
|
||||
: std::max_element (first, last);
|
||||
}
|
||||
|
||||
// verify the returned value: 25.3.7 p7, p9
|
||||
const std::size_t off = test_min ? min_off : max_off;
|
||||
rw_assert (res.cur_ == xsrc + off, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (\"%s\", %zu, ...) "
|
||||
"got first + %td, expected first + %zu",
|
||||
__LINE__, fname, itname, 0 != ppred, funname, src, off,
|
||||
res.cur_ - xsrc, off);
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// verify the complexity: 25.3.7 p8, p10
|
||||
std::size_t n_exp_ops = nsrc > 0 ? nsrc - 1 : 0;
|
||||
rw_assert (n_ops_lt == n_exp_ops, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (\"%s\", %zu, ...) "
|
||||
"complexity: got %zu, expected %zu",
|
||||
__LINE__, fname, itname, 0 != ppred, funname, src, off,
|
||||
n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_min_max (const T*,
|
||||
const Predicate *ppred,
|
||||
bool test_min)
|
||||
{
|
||||
const char* const tname = "UserClass";
|
||||
const char* const fname = test_min ? "min" : "max";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"const %s& std::%s(const %1$s&, const %1$s&%{?}, %s%{;})",
|
||||
tname, fname, 0 != ppred, funname);
|
||||
|
||||
#define TEST(a, b) \
|
||||
test_min_max (__LINE__, a, b, (T*)0, ppred, test_min)
|
||||
|
||||
TEST ('a', 'a');
|
||||
TEST ('a', 'b');
|
||||
TEST ('b', 'a');
|
||||
TEST ('b', 'b');
|
||||
|
||||
TEST ('a', 'e');
|
||||
TEST ('e', 'a');
|
||||
|
||||
#undef TEST
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator, class Predicate>
|
||||
void test_min_max_element (const ForwardIterator &it,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool test_min)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = test_min ? "min_element" : "max_element";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::%s(%1$s, %1$s%{?}, %s%{;})",
|
||||
itname, fname, 0 != ppred, funname);
|
||||
|
||||
#define TEST(src, min_off, max_off) \
|
||||
test_min_max_element (__LINE__, src, min_off, max_off, it, \
|
||||
(T*)0, ppred, test_min)
|
||||
|
||||
TEST ("", 0, 0);
|
||||
TEST ("a", 0, 0);
|
||||
TEST ("ab", 0, 1);
|
||||
TEST ("aa", 0, 0);
|
||||
TEST ("ba", 1, 0);
|
||||
|
||||
TEST ("abcdefghij", 0, 9);
|
||||
TEST ("bacdefghji", 1, 8);
|
||||
TEST ("bcadefgjhi", 2, 7);
|
||||
TEST ("bcdaefjghi", 3, 6);
|
||||
TEST ("bcdeajfghi", 4, 5);
|
||||
TEST ("bcdejafghi", 5, 4);
|
||||
TEST ("bcdjefaghi", 6, 3);
|
||||
TEST ("bcjdefgahi", 7, 2);
|
||||
TEST ("bjcdefghai", 8, 1);
|
||||
TEST ("jbcdefghia", 9, 0);
|
||||
|
||||
TEST ("jihgfedcba", 9, 0);
|
||||
|
||||
TEST ("aaaaaaaaaa", 0, 0);
|
||||
TEST ("ababababab", 0, 1);
|
||||
TEST ("bababababa", 1, 0);
|
||||
TEST ("aaaaabaaaa", 0, 5);
|
||||
TEST ("bbbbbabbbb", 5, 0);
|
||||
|
||||
#undef TEST
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_min; // --no-min
|
||||
/* extern */ int rw_opt_no_max; // --no-max
|
||||
/* extern */ int rw_opt_no_min_element; // --no-min_element
|
||||
/* extern */ int rw_opt_no_max_element; // --no-max_element
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_min_max_element (const T*,
|
||||
const Predicate *ppred,
|
||||
bool test_min)
|
||||
{
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s%{?}, class %s%{;}> "
|
||||
"%1$s std::%s (%1$s, %1$s%{?}, %s%{;})",
|
||||
"ForwardIterator", ppred, "Compare",
|
||||
test_min ? "min_element" : "max_element", ppred, "Compare");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max_element (fwd_iter, (T*)0, ppred, test_min);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, 0, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max_element (bidir_iter, (T*)0, ppred, test_min);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, 0, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max_element (rand_iter, (T*)0, ppred, test_min);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_alg_min_max (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
if (rw_opt_no_min) {
|
||||
rw_note (0, 0, __LINE__, "std::min test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max ((T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_max) {
|
||||
rw_note (0, 0, __LINE__, "std::max test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max ((T*)0, ppred, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_min_element) {
|
||||
rw_note (0, 0, __LINE__, "std::min_element test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max_element ((T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_max_element) {
|
||||
rw_note (0, 0, __LINE__, "std::max_element test disabled");
|
||||
}
|
||||
else {
|
||||
test_min_max_element ((T*)0, ppred, false);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
test_alg_min_max ((UserClass*)0, (Less<UserClass>*)0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, 0, __LINE__, "std.alg.min.max predicate tests disabled");
|
||||
}
|
||||
else {
|
||||
test_alg_min_max ((UserClass*)0, (Less<UserClass>*)1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.min.max",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-min#"
|
||||
"|-no-max#"
|
||||
"|-no-min_element#"
|
||||
"|-no-max_element#"
|
||||
"|-no-predicate#"
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator",
|
||||
&rw_opt_no_min,
|
||||
&rw_opt_no_max,
|
||||
&rw_opt_no_min_element,
|
||||
&rw_opt_no_max_element,
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
291
extern/stdcxx/4.2.1/tests/algorithms/25.mismatch.cpp
vendored
Normal file
291
extern/stdcxx/4.2.1/tests/algorithms/25.mismatch.cpp
vendored
Normal file
@@ -0,0 +1,291 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.mismatch.cpp - test exercising 25.1.7 [lib.mismatch]
|
||||
*
|
||||
* $Id: 25.mismatch.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for mismatch
|
||||
#include <functional> // for equal_to
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::mismatch()
|
||||
template <class InputIterator1, class InputIterator2, class T>
|
||||
void test_mismatch (std::size_t N,
|
||||
const InputIterator1 &it1_dummy,
|
||||
const InputIterator2 &it2_dummy,
|
||||
T*,
|
||||
const char *predicate)
|
||||
{
|
||||
static const char* const it1name = type_name (it1_dummy, (T*)0);
|
||||
static const char* const it2name = type_name (it2_dummy, (T*)0);
|
||||
|
||||
rw_info (0, 0, 0, "std::mismatch (%s, %1$s, %s%{?}, %s%{;})",
|
||||
it1name, it2name, 0 != predicate, predicate);
|
||||
|
||||
// generate sequential values for each default constructed UserClass
|
||||
// for both lists
|
||||
UserClass::gen_ = gen_seq_2lists;
|
||||
|
||||
// use ::operator new() to prevent default initialization
|
||||
const std::size_t size = N * sizeof (UserClass);
|
||||
UserClass *buf1 = _RWSTD_STATIC_CAST (UserClass*, ::operator new (size));
|
||||
UserClass *buf2 = _RWSTD_STATIC_CAST (UserClass*, ::operator new (size));
|
||||
|
||||
const std::size_t mid_inx = N / 2;
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
// default-construct a new UserClass at the end of the array
|
||||
new (buf1 + i) UserClass ();
|
||||
|
||||
// build a nearly identical list only missing N/2 (the N/2th
|
||||
// element) from it's list
|
||||
if (i != mid_inx)
|
||||
new (buf2 + i) UserClass ();
|
||||
}
|
||||
|
||||
new (buf2 + mid_inx) UserClass ();
|
||||
|
||||
for (std::size_t i = 0; i != N; ++i) {
|
||||
|
||||
// exercise 25.1.7 - std::mismatch<>()
|
||||
std::size_t last_n_op_eq = UserClass::n_total_op_eq_;
|
||||
|
||||
UserClass* const buf1_end = buf1 + i + 1;
|
||||
UserClass* const buf2_end = buf2 + i + 1;
|
||||
|
||||
const InputIterator1 first1 (buf1, buf1, buf1_end);
|
||||
const InputIterator1 last1 (buf1_end, buf1_end, buf1_end);
|
||||
const InputIterator2 first2 (buf2, buf2, buf2_end);
|
||||
|
||||
const std::equal_to<UserClass> pred = std::equal_to<UserClass>();
|
||||
|
||||
const std::pair<InputIterator1, InputIterator2> result =
|
||||
predicate ? std::mismatch (first1, last1, first2, pred)
|
||||
: std::mismatch (first1, last1, first2);
|
||||
|
||||
// verify 25.1.7, p2
|
||||
UserClass* const expected_buf1_end =
|
||||
(i < mid_inx) ? buf1_end : buf1 + mid_inx;
|
||||
|
||||
UserClass* const expected_buf2_end =
|
||||
(i < mid_inx) ? buf2_end : buf2 + mid_inx;
|
||||
|
||||
UserClass* const res_buf1_end =
|
||||
buf1 + (result.first.cur_ - first1.cur_);
|
||||
|
||||
UserClass* const res_buf2_end =
|
||||
buf2 + (result.second.cur_ - first2.cur_);
|
||||
|
||||
// check that the returned iterators are valid
|
||||
bool success =
|
||||
buf1 <= res_buf1_end && res_buf1_end <= buf1_end &&
|
||||
buf2 <= res_buf2_end && res_buf2_end <= buf2_end;
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. mismatch (%s, %2$s, %s%{?}, %s%{;}): "
|
||||
"result { %d, %d } out of range: expected "
|
||||
"{ [0, %d], [0, %d] }",
|
||||
i, it1name, it2name, 0 != predicate, predicate,
|
||||
res_buf1_end - buf1, res_buf2_end - buf2,
|
||||
buf1_end - buf1, buf2_end - buf2);
|
||||
|
||||
// iterators are valid check that the algorithm works correctly
|
||||
success =
|
||||
res_buf1_end->data_.val_ == expected_buf1_end->data_.val_
|
||||
&& res_buf2_end->data_.val_ == expected_buf2_end->data_.val_;
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. mismatch (%s, %2$s, %s%{?}, %s%{;}): "
|
||||
"correctness: got: %d "
|
||||
"expected: %d, got: %d expected: %d",
|
||||
i, it1name, it2name, 0 != predicate, predicate,
|
||||
res_buf1_end->data_.val_, expected_buf1_end->data_.val_,
|
||||
res_buf2_end->data_.val_, expected_buf2_end->data_.val_);
|
||||
|
||||
// verify 25.1.7, p3
|
||||
success = UserClass::n_total_op_eq_ - last_n_op_eq <= (N + 1);
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. mismatch (%s, %2$s, %s%{?}, %s%{;}): "
|
||||
"complexity: %zu <= %zu",
|
||||
i, it1name, it2name, 0 != predicate, predicate,
|
||||
UserClass::n_total_op_eq_, i + 1);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
::operator delete (buf1);
|
||||
::operator delete (buf2);
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 32; // --nloops
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
|
||||
template <class InputIterator, class T>
|
||||
void test_mismatch (const InputIterator &dummy, T*, const char *predicate)
|
||||
{
|
||||
// check that the number of loops is non-negative
|
||||
rw_fatal (-1 < rw_opt_nloops, 0, 0,
|
||||
"number of loops must be non-negative, got %d",
|
||||
rw_opt_nloops);
|
||||
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (N, dummy, InputIter<UserClass>(0, 0, 0),
|
||||
(UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (N, dummy, FwdIter<UserClass>(),
|
||||
(UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (N, dummy, BidirIter<UserClass>(),
|
||||
(UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (N, dummy, RandomAccessIter<UserClass>(),
|
||||
(UserClass*)0, predicate);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static void
|
||||
test_mismatch (const char *predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"std::pair<%1$s, %2$s> "
|
||||
"std::mismatch (%1$s, %1$s, %2$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2",
|
||||
0 != predicate, predicate);
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (InputIter<UserClass>(0, 0, 0), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (ConstFwdIter<UserClass>(), (UserClass*)0, predicate);
|
||||
test_mismatch (FwdIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (ConstBidirIter<UserClass>(), (UserClass*)0, predicate);
|
||||
test_mismatch (BidirIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch (ConstRandomAccessIter<UserClass>(),
|
||||
(UserClass*)0, predicate);
|
||||
test_mismatch (RandomAccessIter<UserClass>(), (UserClass*)0, predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_mismatch (0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "Predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_mismatch ("std::equal_to<UserClass>");
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.mismatch",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops#"
|
||||
"|-no-InputIterator#"
|
||||
"|-no-ForwardIterator#"
|
||||
"|-no-BidirectionalIterator#"
|
||||
"|-no-RandomAccessIterator#"
|
||||
"|-no-Predicate",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
313
extern/stdcxx/4.2.1/tests/algorithms/25.nth.element.cpp
vendored
Normal file
313
extern/stdcxx/4.2.1/tests/algorithms/25.nth.element.cpp
vendored
Normal file
@@ -0,0 +1,313 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.nth.element.cpp - test exercising 25.3.2 [lib.alg.nth.element]
|
||||
*
|
||||
* $Id: 25.nth.element.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for nth_element,
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
nth_element (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
nth_element (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct StrictWeakLess
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
StrictWeakLess (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "StrictWeakLess"; }
|
||||
|
||||
private:
|
||||
void operator= (StrictWeakLess&); // not assignable
|
||||
};
|
||||
|
||||
template<class T>
|
||||
std::size_t StrictWeakLess<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exrcises nth_element
|
||||
template <class T, class Predicate>
|
||||
void test_nth_element (int line,
|
||||
const char *src,
|
||||
const std::size_t N,
|
||||
const std::size_t nth,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
_RWSTD_UNUSED (ppred);
|
||||
|
||||
typedef RandomAccessIter<T> RandIter;
|
||||
|
||||
const RandIter it(0, 0, 0);
|
||||
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = "nth_element";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
const std::size_t nsrc = src ? std::strlen (src) : N;
|
||||
|
||||
T::gen_ = gen_rnd;
|
||||
T* const xsrc = src ? T::from_char (src, nsrc) : new T[nsrc];
|
||||
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
// current, first, last
|
||||
const RandIter first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const RandIter nth_it = make_iter (xsrc + nth, xsrc, xsrc_end, it);
|
||||
const RandIter last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
Predicate pred (0, 0);
|
||||
|
||||
const std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
|
||||
if (ppred)
|
||||
std::nth_element (first, nth_it, last, pred);
|
||||
else
|
||||
std::nth_element (first, nth_it, last);
|
||||
|
||||
// check the results, 25.3.2, p1
|
||||
bool success = true;
|
||||
std::size_t i = 0;
|
||||
std::size_t j = 0;
|
||||
|
||||
for (i = 0; i < nth; i++) {
|
||||
for (j = nth; j < nsrc; j++) {
|
||||
success = xsrc[i].data_.val_ <= xsrc[j].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < nth ? i : nth - 1;
|
||||
j = j < nsrc ? j : nsrc - 1;
|
||||
|
||||
if (src) {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}>(\"%s\", %zu, ...) ==> "
|
||||
"\"%{X=*.*}\", got %#c at %zu !< %#c at %zu",
|
||||
__LINE__, fname, itname, ppred, funname, src, nth,
|
||||
int (nsrc), -1, xsrc, xsrc[i].data_.val_, i,
|
||||
xsrc[j].data_.val_, j);
|
||||
}
|
||||
else {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}>(%zu, %zu, ...) "
|
||||
"got %d at %zu !< %d at %zu",
|
||||
__LINE__, fname, itname, ppred, funname, N, nth,
|
||||
xsrc[i].data_.val_, i, xsrc[j].data_.val_, j);
|
||||
}
|
||||
|
||||
// check the complexity, 25.3.2, p2
|
||||
// it should be linear, i.e. <= K * N, there K << N
|
||||
// after tests on random sequences use K == 8 as upper bound
|
||||
std::size_t n_ops =
|
||||
ppred ? Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
std::size_t exp_ops = 8 * nsrc;
|
||||
|
||||
success = n_ops <= exp_ops;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}>(%{?}\"%s\"%{;}%{?}%zu%{;}, "
|
||||
"%zu, ...): complexity: got %zu, expected no more than %zu",
|
||||
__LINE__, fname, itname, ppred, funname,
|
||||
src, src, !src, N, nth, n_ops, exp_ops);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 256; // --nloops=#
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_complexity; // --no-complexity
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_nth_element (const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
typedef RandomAccessIter<T> RandIter;
|
||||
|
||||
const char* const itname = type_name (RandIter (0, 0, 0), (T*)0);
|
||||
const char* const fname = "nth_element";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s, %2$s%{?}, %s%{;})",
|
||||
fname, itname, ppred, funname);
|
||||
|
||||
#define TEST(src, nth) \
|
||||
test_nth_element (__LINE__, src, 0, nth, (T*)0, ppred)
|
||||
|
||||
TEST ("a", 0);
|
||||
TEST ("aa", 1);
|
||||
TEST ("ab", 0);
|
||||
|
||||
TEST ("jihgfedcba", 0);
|
||||
TEST ("jihgfedcba", 1);
|
||||
TEST ("jihgfedcba", 2);
|
||||
TEST ("jihgfedcba", 3);
|
||||
TEST ("jihgfedcba", 4);
|
||||
TEST ("jihgfedcba", 5);
|
||||
TEST ("jihgfedcba", 6);
|
||||
TEST ("jihgfedcba", 7);
|
||||
TEST ("jihgfedcba", 8);
|
||||
TEST ("jihgfedcba", 9);
|
||||
|
||||
TEST ("abcdefghij", 0);
|
||||
TEST ("abcdefghij", 1);
|
||||
TEST ("abcdefghij", 2);
|
||||
TEST ("abcdefghij", 3);
|
||||
TEST ("abcdefghij", 4);
|
||||
TEST ("abcdefghij", 5);
|
||||
TEST ("abcdefghij", 6);
|
||||
TEST ("abcdefghij", 7);
|
||||
TEST ("abcdefghij", 8);
|
||||
TEST ("abcdefghij", 9);
|
||||
|
||||
TEST ("jijgfgdcda", 5);
|
||||
TEST ("jihifefcbc", 5);
|
||||
TEST ("jiigffdcca", 5);
|
||||
TEST ("jihhfeecbb", 5);
|
||||
|
||||
TEST ("cbbbbbbbba", 5);
|
||||
TEST ("ccbbbbbbaa", 5);
|
||||
|
||||
TEST ("abadedghgj", 5);
|
||||
TEST ("abcbefehih", 5);
|
||||
TEST ("abbdeeghhj", 5);
|
||||
TEST ("abcceffhii", 5);
|
||||
|
||||
TEST ("abbbbbbbbc", 5);
|
||||
TEST ("aabbbbbbcc", 5);
|
||||
|
||||
#undef TEST
|
||||
|
||||
if (rw_opt_no_complexity) {
|
||||
rw_note (0, 0, 0,
|
||||
"std::%s (%s, %2$s, %2$s%{?}, %s%{;}): "
|
||||
"complexity test disabled",
|
||||
fname, itname, ppred, funname);
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s, %2$s%{?}, %s%{;}): complexity test",
|
||||
fname, itname, ppred, funname);
|
||||
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
for (std::size_t i = 1; i < N; i++)
|
||||
test_nth_element (__LINE__, 0, i, i / 2, (T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s> "
|
||||
"void std::nth_element (%1$s, %1$s, %1$s)",
|
||||
"RandomAccessIterator");
|
||||
|
||||
test_nth_element ((UserClass*)0, (StrictWeakLess<UserClass>*)0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::nth_element predicate test disabled");
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"void std::nth_element (%1$s, %1$s, %1$s, %2$s)",
|
||||
"RandomAccessIterator", "StrictWeakLess");
|
||||
|
||||
const StrictWeakLess<UserClass> pred(0, 0);
|
||||
test_nth_element ((UserClass*)0, &pred);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.nth_element",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-nloops#0 " // must be non-negative
|
||||
"|-no-predicate#"
|
||||
"|-no-complexity",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_complexity);
|
||||
}
|
||||
487
extern/stdcxx/4.2.1/tests/algorithms/25.partial.sort.cpp
vendored
Normal file
487
extern/stdcxx/4.2.1/tests/algorithms/25.partial.sort.cpp
vendored
Normal file
@@ -0,0 +1,487 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.partial.sort.cpp - test exercising [lib.partial.sort]
|
||||
*
|
||||
* $Id: 25.partial.sort.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for partial_sort, partial_sort_copy
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
partial_sort (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
partial_sort (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
partial_sort_copy (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
partial_sort_copy (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class Iterator, class CopyIterator, class T, class Predicate>
|
||||
void test_partial_sort (int line,
|
||||
const char *src,
|
||||
const std::size_t N,
|
||||
const std::size_t mid,
|
||||
const Iterator &it,
|
||||
const CopyIterator &itc,
|
||||
const T* ,
|
||||
const Predicate *ppred,
|
||||
bool copy)
|
||||
{
|
||||
typedef RandomAccessIter<T> RandIter;
|
||||
const RandIter rand_it(0, 0, 0);
|
||||
|
||||
const char* const itname =
|
||||
copy ? type_name (itc, (T*)0) : type_name (it, (T*)0);
|
||||
const char* const outname = "RandomAccessIterator";
|
||||
const char* const fname = copy ? "partial_sort_copy" : "partial_sort";
|
||||
const char* const funname = ppred ? Predicate::name() : "operator<()";
|
||||
|
||||
// generate random values for each default constructed T
|
||||
T::gen_ = gen_rnd;
|
||||
|
||||
const std::size_t nsrc = src ? std::strlen (src) : N;
|
||||
|
||||
T* const xsrc = src ? T::from_char (src, nsrc) : new T[nsrc];
|
||||
T* const xdst = new T [mid];
|
||||
T* res_x = copy ? xdst : xsrc;
|
||||
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
T* const xdst_end = xdst + mid;
|
||||
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const Iterator middle = make_iter (xsrc + mid, xsrc, xsrc_end, it);
|
||||
const Iterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
CopyIterator first_c = make_iter (xsrc, xsrc, xsrc_end, itc);
|
||||
CopyIterator last_c = make_iter (xsrc_end, xsrc, xsrc_end, itc);
|
||||
|
||||
RandIter res_first = make_iter (xdst, xdst, xdst_end, rand_it);
|
||||
RandIter res_last = make_iter (xdst_end, xdst, xdst_end, rand_it);
|
||||
|
||||
const Predicate pred (0, 0);
|
||||
RandIter result (0, 0, 0);
|
||||
|
||||
std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
|
||||
if (copy) {
|
||||
if (ppred)
|
||||
result = std::partial_sort_copy (
|
||||
first_c, last_c, res_first, res_last, pred);
|
||||
else
|
||||
result = std::partial_sort_copy (
|
||||
first_c, last_c, res_first, res_last);
|
||||
}
|
||||
else {
|
||||
if (ppred)
|
||||
std::partial_sort (first, middle, last, pred);
|
||||
else
|
||||
std::partial_sort (first, middle, last);
|
||||
}
|
||||
|
||||
bool success = true;
|
||||
// check the returned iterator for copy version
|
||||
if (copy) {
|
||||
success = result.cur_ == res_first.cur_ + mid;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}%{?}, %s%{;}> (): "
|
||||
"returned iterator it is invalid: got result + %td, "
|
||||
"expected result + %zu",
|
||||
__LINE__, fname, itname, copy, outname, ppred, funname,
|
||||
result.cur_ - res_first.cur_, mid);
|
||||
}
|
||||
|
||||
// check that the array is sorted
|
||||
success = is_sorted_lt (res_x, res_x + mid);
|
||||
if (src) {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}%{?}, %s%{;}> "
|
||||
"(\"%s\", %zu, ...): ==> \"%{X=*.*}\" not sorted",
|
||||
__LINE__, fname, itname, copy, outname, ppred, funname,
|
||||
src, mid, int (mid), -1, res_x);
|
||||
}
|
||||
else {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}%{?}, %s%{;}> "
|
||||
"(%zu, %zu, ...): not sorted",
|
||||
__LINE__, fname, itname, copy, outname, ppred, funname,
|
||||
nsrc, mid);
|
||||
}
|
||||
|
||||
// check that any element in the sorted range <= that any element
|
||||
// in the rest part of the array
|
||||
int max_el = res_x[0].data_.val_;
|
||||
std::size_t j = 1;
|
||||
for ( ; j < mid; j++)
|
||||
max_el = max_el < res_x[j].data_.val_ ? res_x[j].data_.val_ : max_el;
|
||||
|
||||
if (copy) {
|
||||
std::size_t tmp = 0;
|
||||
for (j = 0; j < nsrc; j++)
|
||||
if (max_el > xsrc[j].data_.val_)
|
||||
tmp++;
|
||||
|
||||
success = tmp <= mid;
|
||||
}
|
||||
else {
|
||||
for (j = mid; j < nsrc; j++) {
|
||||
success = max_el <= xsrc[j].data_.val_;
|
||||
if (! success)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// to avoid error in trace mode
|
||||
j = j < nsrc ? j : nsrc - 1;
|
||||
|
||||
if (src) {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}%{?}, %s%{;}> "
|
||||
"(\"%s\", %zu, ...): ==> \"%{X=*.*}\" got less element "
|
||||
"%{?}%#c%{;} in the unsorted part",
|
||||
__LINE__, fname, itname, copy, outname, ppred, funname,
|
||||
src, mid, int (copy ? mid : nsrc), -1, res_x,
|
||||
!copy, xsrc[j].data_.val_);
|
||||
}
|
||||
else {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}%{?}, %s%{;}> "
|
||||
"(%zu, %zu, ...): got less element in the unsorted part",
|
||||
__LINE__, fname, itname, copy, outname, ppred, funname,
|
||||
nsrc, mid);
|
||||
}
|
||||
|
||||
// verify 25.3.1.1, p2 and 25.3.1.2, p3
|
||||
// the complexity of our implementation is no worse than
|
||||
// 3.33 * N * log (N) (hence the magic 7 and 2)
|
||||
std::size_t n_ops =
|
||||
ppred ? Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
std::size_t exp_ops = 7 * nsrc * ::ilog2 (mid > 1 ? mid : 2);
|
||||
success = 2 * n_ops <= exp_ops;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}%{?}, %s%{;}> (): complexity "
|
||||
"for length %zu is %zu, expected no more than %zu",
|
||||
__LINE__, fname, itname, copy, outname, ppred, funname,
|
||||
nsrc, n_ops, exp_ops / 2);
|
||||
|
||||
delete[] xsrc;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 256; // --nloops=#
|
||||
/* extern */ int rw_opt_no_partial_sort; // --no-partial_sort
|
||||
/* extern */ int rw_opt_no_partial_sort_copy; // --no-partial_sort_copy
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_complexity; // --no-complexity
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class Iterator, class CopyIterator, class T, class Predicate>
|
||||
void test_partial_sort (const std::size_t N,
|
||||
const Iterator &it,
|
||||
const CopyIterator &itc,
|
||||
const T* ,
|
||||
const Predicate *ppred,
|
||||
bool copy)
|
||||
{
|
||||
const char* const itname =
|
||||
copy ? type_name (itc, (T*)0) : type_name (it, (T*)0);
|
||||
const char* const outname = "RandomAccessIterator";
|
||||
const char* const fname = copy ? "partial_sort_copy" : "partial_sort";
|
||||
const char* const funname = ppred ? Predicate::name() : "operator<()";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%{?}%s %{;}std::%s (%s, %4$s, %s%{?}, %2$s%{;}%{?}, %s%{;})",
|
||||
copy, outname, fname, itname, copy ? outname : itname,
|
||||
copy, ppred, funname);
|
||||
|
||||
#define TEST(src, mid) \
|
||||
test_partial_sort (__LINE__, src, 0, mid, it, itc, (T*)0, ppred, copy)
|
||||
|
||||
TEST ("a", 1);
|
||||
|
||||
TEST ("ba", 1);
|
||||
TEST ("cba", 1);
|
||||
TEST ("dcba", 2);
|
||||
TEST ("edcba", 2);
|
||||
TEST ("fedcba", 3);
|
||||
TEST ("gfedcba", 3);
|
||||
TEST ("hgfedcba", 4);
|
||||
TEST ("ihgfedcba", 4);
|
||||
TEST ("jihgfedcba", 5);
|
||||
|
||||
TEST ("ab", 1);
|
||||
TEST ("abc", 1);
|
||||
TEST ("abcd", 2);
|
||||
TEST ("abcde", 2);
|
||||
TEST ("abcdef", 3);
|
||||
TEST ("abcdefg", 3);
|
||||
TEST ("abcdefgh", 4);
|
||||
TEST ("abcdefghi", 4);
|
||||
TEST ("abcdefghij", 5);
|
||||
|
||||
TEST ("aa", 1);
|
||||
TEST ("aabb", 2);
|
||||
TEST ("bbccaa", 3);
|
||||
TEST ("ddbbccaa", 4);
|
||||
TEST ("ddeebbccaa", 5);
|
||||
|
||||
TEST ("aa", 2);
|
||||
TEST ("aabb", 4);
|
||||
TEST ("bbccaa", 6);
|
||||
TEST ("ddbbccaa", 8);
|
||||
TEST ("ddeebbccaa", 10);
|
||||
|
||||
TEST ("aaaaaaaaaa", 5);
|
||||
TEST ("ababababab", 4);
|
||||
TEST ("bababababa", 4);
|
||||
|
||||
#undef TEST
|
||||
|
||||
if (rw_opt_no_complexity) {
|
||||
rw_note (0, 0, 0,
|
||||
"%{?}%s %{;}std::%s (%s, %4$s, %s%{?}, %2$s%{;}%{?}, %s%{;})"
|
||||
": complexity test disabled",
|
||||
copy, outname, fname, itname, copy ? outname : itname,
|
||||
copy, ppred, funname);
|
||||
}
|
||||
else {
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%{?}%s %{;}std::%s (%s, %4$s, %s%{?}, %2$s%{;}%{?}, %s%{;})"
|
||||
": complexity test",
|
||||
copy, outname, fname, itname, copy ? outname : itname,
|
||||
copy, ppred, funname);
|
||||
|
||||
for (std::size_t i = 1; i < N; i++)
|
||||
test_partial_sort (__LINE__, 0, i, i > 1 ? i / 2 : 1, it, itc,
|
||||
(T*)0, ppred, copy);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_partial_sort (const std::size_t N,
|
||||
const T* ,
|
||||
const Predicate *ppred,
|
||||
bool copy)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s%{?}, class %s%{;}%{?}, class %s%{;}> "
|
||||
"%s std::partial_sort%{?}_copy%{;} (%1$s%{?}, %1$s%{;}, %1$s"
|
||||
"%{?}, %3$s, %3$s%{;}%{?}, %5$s%{;})",
|
||||
copy ? "InputIterator" : "RandomAccessIterator",
|
||||
copy, "RandomAccessIterator", ppred, "StrictWeakComp",
|
||||
copy ? "RandomAccessIterator" : "void",
|
||||
copy, !copy, copy, ppred);
|
||||
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
if (! copy) {
|
||||
test_partial_sort (N, rand_iter, rand_iter,
|
||||
(T*)0, ppred, false);
|
||||
return;
|
||||
}
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_partial_sort (N, rand_iter, input_iter,
|
||||
(T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_partial_sort (N, rand_iter, fwd_iter,
|
||||
(T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_partial_sort (N, rand_iter, bidir_iter,
|
||||
(T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_partial_sort (N, rand_iter, rand_iter,
|
||||
(T*)0, ppred, true);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_partial_sort (const std::size_t N,
|
||||
const T* ,
|
||||
bool copy)
|
||||
{
|
||||
test_partial_sort (N, (T*)0, (Less<T>*)0, copy);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::partial_sort%{?}_copy%{;} predicate test disabled",
|
||||
copy);
|
||||
}
|
||||
else {
|
||||
const Less<T> pred(0, 0);
|
||||
test_partial_sort (N, (T*)0, &pred, copy);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
if (rw_opt_no_partial_sort) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::partial_sort test disabled");
|
||||
}
|
||||
else {
|
||||
test_partial_sort (N, (UserClass*)0, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_partial_sort_copy) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::partial_sort_copy test disabled");
|
||||
}
|
||||
else {
|
||||
test_partial_sort (N, (UserClass*)0, true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.partial.sort",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-nloops#0 " // must be non-negative
|
||||
"|-no-partial_sort# "
|
||||
"|-no-partial_sort_copy# "
|
||||
"|-no-InputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator# "
|
||||
"|-no-predicate",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_partial_sort,
|
||||
&rw_opt_no_partial_sort_copy,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_complexity);
|
||||
}
|
||||
350
extern/stdcxx/4.2.1/tests/algorithms/25.partitions.cpp
vendored
Normal file
350
extern/stdcxx/4.2.1/tests/algorithms/25.partitions.cpp
vendored
Normal file
@@ -0,0 +1,350 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.partitions.cpp - test exercising 25.2.12 [lib.alg.partitions]
|
||||
*
|
||||
* $Id: 25.partitions.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for partition, stable_partition
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
BidirIter<assign<base<cpy_ctor> > >
|
||||
partition (BidirIter<assign<base<cpy_ctor> > >,
|
||||
BidirIter<assign<base<cpy_ctor> > >,
|
||||
predicate<assign<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
BidirIter<assign<base<cpy_ctor> > >
|
||||
stable_partition (BidirIter<assign<base<cpy_ctor> > >,
|
||||
BidirIter<assign<base<cpy_ctor> > >,
|
||||
predicate<assign<base<cpy_ctor> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct GreaterThanPredicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy argument provide to prevent implicit conversions
|
||||
GreaterThanPredicate (int value, int /* dummy */)
|
||||
: value_(value) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &arg) {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (value_ < arg.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "GreaterThanPredicate"; }
|
||||
|
||||
private:
|
||||
const int value_;
|
||||
void operator= (GreaterThanPredicate&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t GreaterThanPredicate<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::partition() and std::stable_partition()
|
||||
template <class T, class Iterator, class Predicate>
|
||||
void test_partitions (int line,
|
||||
const char *src,
|
||||
const char *dst,
|
||||
const int value,
|
||||
const std::size_t offset,
|
||||
const Iterator &it,
|
||||
const Predicate *,
|
||||
const T*,
|
||||
bool stable)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = stable ? "stable_partition" : "partition";
|
||||
const char* const funname = Predicate::name();
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
const std::size_t ndst = std::strlen (dst);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xdst = T::from_char (dst, ndst);
|
||||
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const Iterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
const std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
const std::size_t t_n_ctors = T::n_total_def_ctor_ + T::n_total_copy_ctor_;
|
||||
const std::size_t t_n_dtors = T::n_total_dtor_;
|
||||
|
||||
const Predicate pred (value, 0 /* dummy */);
|
||||
|
||||
const Iterator res =
|
||||
stable ? std::stable_partition (first, last, pred)
|
||||
: std::partition (first, last, pred);
|
||||
|
||||
// check that there is no leaked objects
|
||||
const std::size_t t_n_objs_diff =
|
||||
T::n_total_def_ctor_ + T::n_total_copy_ctor_
|
||||
- t_n_ctors - T::n_total_dtor_ + t_n_dtors;
|
||||
|
||||
bool success = 0 == t_n_objs_diff;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...) ==> \"%{X=*.*}\", "
|
||||
"number of objects changed on %d: %s detected",
|
||||
__LINE__, fname, itname, funname, src,
|
||||
int (nsrc), -1, xsrc, t_n_objs_diff,
|
||||
t_n_objs_diff > 0 ? "memory leak" : "unexpected dtor call");
|
||||
|
||||
// check that the returned iterator points to the expected element
|
||||
success = res.cur_ == first.cur_ + offset;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...) ==> \"%{X=*.*}\", "
|
||||
"returned iterator it = first + %td, expected first + %zu",
|
||||
__LINE__, fname, itname, funname, src, int (nsrc),
|
||||
-1, xsrc, res.cur_ - first.cur_, offset);
|
||||
|
||||
// check 25.2.12, p2 & p5
|
||||
// "left" part of the array there the predicate should be true
|
||||
std::size_t i = 0;
|
||||
for ( ; i < offset; i++) {
|
||||
success = xsrc[i].data_.val_ > value;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...) "
|
||||
"==> \"%{X=*.*}\", at %zu got: %#c !> %#c",
|
||||
__LINE__, fname, itname, funname, src, int (nsrc),
|
||||
-1, xsrc, i + 1, xsrc[i].data_.val_, value);
|
||||
|
||||
|
||||
// "right" part of the array there the predicate should be false
|
||||
for ( ; i < nsrc; i++) {
|
||||
success = xsrc[i].data_.val_ <= value;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...) "
|
||||
"==> \"%{X=*.*}\", at %zu got: %#c !<= %#c",
|
||||
__LINE__, fname, itname, funname, src, int (nsrc),
|
||||
-1, xsrc, i + 1, xsrc[i].data_.val_, value);
|
||||
|
||||
|
||||
// check the complexity, 25.2.12 p3 & p6
|
||||
// first check number of swaps, 2 assignments per swap
|
||||
|
||||
// add 1 in case of stable_partition to avoid the assertion failing
|
||||
// when i == 0 (only one element presents in the sequence)
|
||||
// is this one extra assignment an algorithm bug??
|
||||
// the standard talks about swaps only, not about assignments
|
||||
// and there are 0 swaps (1 swap equals 2 assignments) in this case...
|
||||
std::size_t exp_assigns = stable ? 2 * nsrc * ::ilog2 (nsrc) + 1 : nsrc;
|
||||
std::size_t op_assigns = T::n_total_op_assign_ - last_n_op_assign;
|
||||
|
||||
success = op_assigns <= exp_assigns;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...): complexity: "
|
||||
"got %zu assignments, expected no more than %zu",
|
||||
__LINE__, fname, itname, funname, src,
|
||||
op_assigns, exp_assigns);
|
||||
|
||||
// second check the number of the predicate calls
|
||||
success = Predicate::funcalls_ == nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...): complexity: "
|
||||
"got %zu applications of the predicate, "
|
||||
"expected no more than %zu",
|
||||
__LINE__, fname, itname, funname, src,
|
||||
Predicate::funcalls_, nsrc);
|
||||
|
||||
if (stable) {
|
||||
|
||||
// check the stable_partition is really stable 25.2.12, p5
|
||||
for (i = 0; i < nsrc; i++) {
|
||||
success = xsrc[i].data_.val_ == xdst[i].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s, %s>(\"%s\", ...) ==> \"%{X=*.*}\", "
|
||||
"expected \"%{X=*.*}\", realtive order broken at %zu, "
|
||||
"%#c != %#c",
|
||||
__LINE__, fname, itname, funname, src,
|
||||
int (nsrc), int (i), xsrc, int (ndst), int (i), xdst,
|
||||
i, xsrc[i].data_.val_, xdst[i].data_.val_);
|
||||
}
|
||||
|
||||
delete[] xsrc;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Iterator>
|
||||
void test_partitions (const Iterator &it,
|
||||
const T* ,
|
||||
bool stable)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname =
|
||||
stable ? "stable_partition" : "partition";
|
||||
const char* const funname = GreaterThanPredicate<T>::name();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s %s (%1$s, %1$s, %s)",
|
||||
itname, fname, funname);
|
||||
|
||||
#define TEST(src, dest, mid, offet) \
|
||||
test_partitions (__LINE__, src, dest, mid, offet, it, \
|
||||
(GreaterThanPredicate<T>*)0, (T*)0, stable)
|
||||
|
||||
// stable_partition fails this test
|
||||
TEST ("abcdefghij", "abcdefghij", 0, 10);
|
||||
|
||||
TEST ("abcdefghij", "bcdefghija", 'a', 9);
|
||||
TEST ("abcdefghij", "cdefghijab", 'b', 8);
|
||||
TEST ("abcdefghij", "defghijabc", 'c', 7);
|
||||
TEST ("abcdefghij", "efghijabcd", 'd', 6);
|
||||
TEST ("abcdefghij", "fghijabcde", 'e', 5);
|
||||
TEST ("abcdefghij", "ghijabcdef", 'f', 4);
|
||||
TEST ("abcdefghij", "hijabcdefg", 'g', 3);
|
||||
TEST ("abcdefghij", "ijabcdefgh", 'h', 2);
|
||||
TEST ("abcdefghij", "jabcdefghi", 'i', 1);
|
||||
TEST ("abcdefghij", "abcdefghij", 'j', 0);
|
||||
|
||||
// stable_partition fails this test
|
||||
TEST ("jihgfedcba", "jihgfedcba", 0, 10);
|
||||
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'a', 9);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'b', 8);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'c', 7);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'd', 6);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'e', 5);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'f', 4);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'g', 3);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'h', 2);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'i', 1);
|
||||
TEST ("jihgfedcba", "jihgfedcba", 'j', 0);
|
||||
|
||||
// stable_partition fails this test
|
||||
TEST ("a", "a", 0, 1);
|
||||
|
||||
TEST ("a", "a", 'a', 0);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_partition; // --no-partition
|
||||
/* extern */ int rw_opt_no_stable_partition; // --no-stable_partition
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
|
||||
template <class T>
|
||||
void test_partitions (const T*, bool stable)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> %1$s %s (%1$s, %1$s, %2$s)",
|
||||
"BidirectionalIterator", "Predicate",
|
||||
stable ? "stable_partition" : "partition");
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_partitions (BidirIter<T>(), (T*)0, stable);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_partitions (RandomAccessIter<T>(), (T*)0, stable);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_partition) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::partition test disabled");
|
||||
}
|
||||
else {
|
||||
test_partitions ((UserClass*)0, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_stable_partition) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::stable_partition test disabled");
|
||||
}
|
||||
else {
|
||||
test_partitions ((UserClass*)0, true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.partitions",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-partition# "
|
||||
"|-no-stable_partition# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator",
|
||||
&rw_opt_no_partition,
|
||||
&rw_opt_no_stable_partition,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
338
extern/stdcxx/4.2.1/tests/algorithms/25.permutation.cpp
vendored
Normal file
338
extern/stdcxx/4.2.1/tests/algorithms/25.permutation.cpp
vendored
Normal file
@@ -0,0 +1,338 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.permutation.cpp - test exercising lib.alg.permutation.generators
|
||||
*
|
||||
* $Id: 25.permutation.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for prev_permutation, next_permutation
|
||||
#include <cstring> // for strlen, size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
bool
|
||||
prev_permutation (BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
bool
|
||||
prev_permutation (BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
bool
|
||||
next_permutation (BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
bool
|
||||
next_permutation (BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
BidirIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercise prev_permutation and next_permutation 25.3.9
|
||||
template <class T, class BidirectIterator, class Predicate>
|
||||
void test_permutations (int line,
|
||||
const char *src,
|
||||
const char *dst,
|
||||
bool res,
|
||||
const BidirectIterator &it,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool prev)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const algname = prev ? "prev_permutation" : "next_permutation";
|
||||
const char* const predname = Predicate::name ();
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
const BidirectIterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const BidirectIterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
const Predicate pred (0, 0);
|
||||
|
||||
const std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
bool result = false;
|
||||
|
||||
if (ppred) {
|
||||
result = prev ?
|
||||
std::prev_permutation (first, last, pred)
|
||||
: std::next_permutation (first, last, pred);
|
||||
}
|
||||
else {
|
||||
result = prev ?
|
||||
std::prev_permutation (first, last)
|
||||
: std::next_permutation (first, last);
|
||||
}
|
||||
|
||||
std::size_t n_ops_assign = T::n_total_op_assign_ - last_n_op_assign;
|
||||
|
||||
// verify the returned value: 25.3.9, p1 and p4
|
||||
bool success = result == res;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d. %s <%s%{?}, %s%{;}> (\"%s\", ...) == %b, got %b",
|
||||
__LINE__, algname, itname, 0 != ppred, predname,
|
||||
src, result, res);
|
||||
|
||||
// verify the permutation result
|
||||
std::size_t i = 0;
|
||||
for ( ; i < nsrc; i++) {
|
||||
success = xsrc [i].data_.val_ == dst [i];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < nsrc ? i : nsrc - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d. %s <%s%{?}, %s%{;}> (\"%s\", ...) "
|
||||
"==> got \"%{X=*.*}\", expected \"%s\"",
|
||||
__LINE__, algname, itname, 0 != ppred, predname, src,
|
||||
int (nsrc), int (i), xsrc, dst);
|
||||
|
||||
// verify the complexity: 25.3.9 p2 and p5.
|
||||
// (last - first) / 2 swaps, 2 assign per swap
|
||||
success = n_ops_assign <= nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d. %s <%s%{?}, %s%{;}> (\"%s\", ...) "
|
||||
"complexity: got %zu assigns, expected no more than %zu",
|
||||
__LINE__, algname, itname, 0 != ppred, predname, src,
|
||||
n_ops_assign, nsrc);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class BidirectIterator, class Predicate>
|
||||
void test_permutations (const BidirectIterator &it,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool prev)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const algname = prev ? "prev_permutation" : "next_permutation";
|
||||
const char* const predname = Predicate::name();
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s(%s, %2$s%{?}, %s%{;})",
|
||||
algname, itname, 0 != ppred, predname);
|
||||
|
||||
#define TEST(src, dst, res) \
|
||||
test_permutations (__LINE__, src, dst, res, it, (T*)0, ppred, prev)
|
||||
|
||||
if (prev) {
|
||||
// +------------- initial (source) sequence
|
||||
// | +------- final (destination) sequence
|
||||
// | | +-- expected return value
|
||||
// | | |
|
||||
// V V V
|
||||
TEST ("a", "a", false);
|
||||
TEST ("aa", "aa", false);
|
||||
TEST ("ab", "ba", false);
|
||||
TEST ("ba", "ab", true);
|
||||
|
||||
TEST ("bcaefigjhd", "bcaefigjdh", true);
|
||||
TEST ("bcaefihdgj", "bcaefigjhd", true);
|
||||
|
||||
TEST ("hefdiacjbg", "hefdiacgjb", true);
|
||||
TEST ("hefdiacjgb", "hefdiacjbg", true);
|
||||
|
||||
TEST ("aaaaaaaaaa", "aaaaaaaaaa", false);
|
||||
TEST ("aaaaabbbbb", "bbbbbaaaaa", false);
|
||||
TEST ("ababababab", "abababaabb", true);
|
||||
TEST ("bbbbbaaaaa", "bbbbabaaaa", true);
|
||||
|
||||
TEST ("abcdefghij", "jihgfedcba", false);
|
||||
TEST ("jihgfedcba", "jihgfedcab", true);
|
||||
}
|
||||
else {
|
||||
TEST ("a", "a", false);
|
||||
TEST ("aa", "aa", false);
|
||||
TEST ("ab", "ba", true);
|
||||
TEST ("ba", "ab", false);
|
||||
|
||||
TEST ("bcaefigjhd", "bcaefihdgj", true);
|
||||
TEST ("bcaefigjdh", "bcaefigjhd", true);
|
||||
|
||||
TEST ("hefdiacjbg", "hefdiacjgb", true);
|
||||
TEST ("hefdiacgjb", "hefdiacjbg", true);
|
||||
|
||||
TEST ("aaaaaaaaaa", "aaaaaaaaaa", false);
|
||||
TEST ("aaaaabbbbb", "aaaababbbb", true);
|
||||
TEST ("ababababab", "ababababba", true);
|
||||
TEST ("bbbbbaaaaa", "aaaaabbbbb", false);
|
||||
|
||||
TEST ("abcdefghij", "abcdefghji", true);
|
||||
TEST ("jihgfedcba", "abcdefghij", false);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_prev_permutation; // --no-prev_permutation
|
||||
/* extern */ int rw_opt_no_next_permutation; // --no-next_permutation
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_permutations (const T*,
|
||||
const Predicate* ppred,
|
||||
bool prev)
|
||||
{
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s%{?}, class %s%{;}> "
|
||||
"bool %s (%1$s, %1$s%{?}, %s%{;})",
|
||||
"BidirectionalIterator", 0 != ppred, "Compare",
|
||||
prev ? "prev_permutation" : "next_permutation",
|
||||
0 != ppred, "Compare");
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, 0, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_permutations (bidir_iter, (T*)0, ppred, prev);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, 0, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_permutations (rand_iter, (T*)0, ppred, prev);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_permutations (const T*,
|
||||
const Predicate* ppred)
|
||||
{
|
||||
if (rw_opt_no_prev_permutation) {
|
||||
rw_note (0, 0, __LINE__, "std::prev_permutation test disabled");
|
||||
}
|
||||
else {
|
||||
test_permutations ((UserClass*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_next_permutation) {
|
||||
rw_note (0, 0, __LINE__, "std::next_permutation test disabled");
|
||||
}
|
||||
else {
|
||||
test_permutations ((UserClass*)0, ppred, false);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
test_permutations ((UserClass*)0, (Less<UserClass>*)0);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, 0, __LINE__, "predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_permutations ((UserClass*)0, (Less<UserClass>*)1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.permutation.generators",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-prev_permutation# "
|
||||
"|-no-next_permutation# "
|
||||
"|-no-predicate# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_prev_permutation,
|
||||
&rw_opt_no_next_permutation,
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
394
extern/stdcxx/4.2.1/tests/algorithms/25.random.shuffle.cpp
vendored
Normal file
394
extern/stdcxx/4.2.1/tests/algorithms/25.random.shuffle.cpp
vendored
Normal file
@@ -0,0 +1,394 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.random.shuffle.cpp - test exercising 25.2.11 [lib.alg.random.shuffle]
|
||||
*
|
||||
* $Id: 25.random.shuffle.cpp 650944 2008-04-23 17:27:06Z sebor $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2008 Rogue Wave Software, Inc.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for random_shuffle
|
||||
#include <cstring> // for memset(), size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
random_shuffle (RandomAccessIter<assign<base<cpy_ctor> > >,
|
||||
RandomAccessIter<assign<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
void
|
||||
random_shuffle (RandomAccessIter<assign<base<cpy_ctor> > >,
|
||||
RandomAccessIter<assign<base<cpy_ctor> > >,
|
||||
func<const long>&);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// 25.2.11, p3 requires that a RandomNumberGenerator take
|
||||
// and return a value convertible from and to, respectively,
|
||||
// iterator::difference_type
|
||||
|
||||
template <class DifferenceType>
|
||||
struct Convertible
|
||||
{
|
||||
Convertible (DifferenceType val): val_ (val) { }
|
||||
operator DifferenceType () /* non-const */ { return val_; }
|
||||
|
||||
private:
|
||||
const DifferenceType val_;
|
||||
|
||||
template <class T>
|
||||
Convertible (T);
|
||||
};
|
||||
|
||||
// detect assumptions made by the algorithm about the return value
|
||||
// from RandomGenerator::operator() being anything but convertible
|
||||
// to the iterator's difference type
|
||||
template <class DifferenceType, class T>
|
||||
void operator+ (Convertible<DifferenceType>, T);
|
||||
|
||||
template <class DifferenceType, class T>
|
||||
void operator+ (T, Convertible<DifferenceType>);
|
||||
|
||||
template <class DifferenceType>
|
||||
struct RandomGenerator
|
||||
{
|
||||
// dummy arguments to prevent the class from being default
|
||||
// constructible or construtible by conversion from an int
|
||||
RandomGenerator (int, int) {
|
||||
ncalls_ = 0;
|
||||
}
|
||||
|
||||
// non-const in order to detect unwarranted assumptions
|
||||
// in the algorithm(s)
|
||||
Convertible<DifferenceType>
|
||||
operator() (DifferenceType n) /* non-const */ {
|
||||
|
||||
++ncalls_;
|
||||
|
||||
gen_ = (gen_ << 7) + gen_ % 128;
|
||||
|
||||
// prevent the number from going negative(!)
|
||||
if (gen_ < 0)
|
||||
gen_ = -gen_;
|
||||
|
||||
return gen_ % n;
|
||||
}
|
||||
|
||||
static std::size_t ncalls_;
|
||||
|
||||
private:
|
||||
|
||||
template <class T>
|
||||
void operator() (T) /* non-const */;
|
||||
|
||||
static DifferenceType gen_;
|
||||
};
|
||||
|
||||
template <class DifferenceType>
|
||||
std::size_t RandomGenerator<DifferenceType>::ncalls_ = 0;
|
||||
|
||||
template <class DifferenceType>
|
||||
DifferenceType RandomGenerator<DifferenceType>::gen_ = 12345;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int sequence_start;
|
||||
|
||||
int sequence_generator ()
|
||||
{
|
||||
return sequence_start++;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises 25.2.11 -- std::random_shuffle()
|
||||
template <class T, class Iterator, class RandomNumberGenerator>
|
||||
void test_random_shuffle (const std::size_t line,
|
||||
const std::size_t N,
|
||||
const Iterator &it,
|
||||
const RandomNumberGenerator*,
|
||||
const T*,
|
||||
bool rnd_gen)
|
||||
{
|
||||
const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = "random_shuffle";
|
||||
const char* const funname = rnd_gen ? "random_generator" : "";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s%{?}, %s%{;})",
|
||||
fname, itname, rnd_gen, funname);
|
||||
|
||||
// generate a sequential value for each default-constructed T
|
||||
// starting with 0 (i.e., T::val_ will be 0 for the first T)
|
||||
sequence_start = 0;
|
||||
T::gen_ = sequence_generator;
|
||||
|
||||
T *buf = new T [N + 1];
|
||||
char *missing = new char [N + 1];
|
||||
|
||||
for (std::size_t i = 0; i < N; ++i) {
|
||||
|
||||
// create a pair of safe iterator to pass to random_shuffle
|
||||
// in order to test that the function doesn't write past
|
||||
// the end of the sequence [first, last)
|
||||
const Iterator first = make_iter (buf, buf, buf + i, it);
|
||||
const Iterator last = make_iter (buf + i, buf, buf + i, it);
|
||||
|
||||
/* non-const */ RandomNumberGenerator rnd (0, 0); // dummy args
|
||||
|
||||
// exercise 25.2.11 - std::random_shuffle<>()
|
||||
std::size_t n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
// shuffle buffer elements
|
||||
if (rnd_gen)
|
||||
std::random_shuffle (first, last, rnd);
|
||||
else
|
||||
std::random_shuffle (first, last);
|
||||
|
||||
n_op_assign = T::n_total_op_assign_ - n_op_assign;
|
||||
|
||||
// verify 25.2.11, p1
|
||||
// iterate over elements of the missing array clearing those
|
||||
// at the index given by T::val_ to true to verify that the
|
||||
// algorithm didn't drop any elements
|
||||
std::size_t j;
|
||||
std::memset (missing, 1, N);
|
||||
for (j = 0; j != i; ++j) {
|
||||
const std::size_t inx = std::size_t (buf [j].data_.val_);
|
||||
if (inx < N)
|
||||
missing [inx] = 0;
|
||||
}
|
||||
|
||||
// find the first missing element (if any)
|
||||
const char* const first_missing = (char*)std::memchr (missing, 1, i);
|
||||
|
||||
bool success = 0 == first_missing;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"%zu. std::%s<%s%{?}, %s%{;}>(): can't find element "
|
||||
"with value %td: got \"%{X=*.*}\"",
|
||||
i, fname, itname, rnd_gen, funname,
|
||||
first_missing - missing,
|
||||
int (i), -1, buf);
|
||||
|
||||
|
||||
// verify 25.2.11, p2, complexity:
|
||||
// exactly K = ((last - first) - 1) swaps
|
||||
// i.e., K * 2 assignments (at 2 assignment per swap
|
||||
// plus one copy construction)
|
||||
success = n_op_assign == 2 * (i ? i - 1 : i);
|
||||
rw_assert (success, 0, line,
|
||||
"%zu. std::%s<%s%{?}, %s%{;}>(): complexity: "
|
||||
"expected %zu swaps, got %zu",
|
||||
i, fname, itname, rnd_gen, funname,
|
||||
2 * i, n_op_assign);
|
||||
}
|
||||
|
||||
delete[] buf;
|
||||
delete[] missing;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_random_shuffle (const std::size_t line)
|
||||
{
|
||||
#ifndef _RWSTD_NO_EXT_PORTABLE_RANDOM_SEQUENCE
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"verify that the randomly shuffled sequence "
|
||||
"matches the expected result, this "
|
||||
"depends on the implementation of the random "
|
||||
"number generator used by random_shuffle()");
|
||||
|
||||
int array[] = {
|
||||
0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
|
||||
0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
|
||||
0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
|
||||
0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
|
||||
0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
|
||||
0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,
|
||||
0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
|
||||
0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
|
||||
0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
|
||||
0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,
|
||||
0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
|
||||
0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,
|
||||
0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
|
||||
0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,
|
||||
0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
|
||||
0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f,
|
||||
0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
|
||||
0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f,
|
||||
0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
|
||||
0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f,
|
||||
0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
|
||||
0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf,
|
||||
0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7,
|
||||
0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf,
|
||||
0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7,
|
||||
0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf,
|
||||
0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7,
|
||||
0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf,
|
||||
0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7,
|
||||
0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef,
|
||||
0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
|
||||
0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
|
||||
};
|
||||
|
||||
std::random_shuffle (array, array + sizeof array / sizeof *array);
|
||||
|
||||
const int result[] = {
|
||||
0xdc, 0x98, 0x6c, 0xcc, 0x1c, 0xb1, 0x2f, 0x13,
|
||||
0xa4, 0x8b, 0x96, 0x87, 0x95, 0xd8, 0x5e, 0xd5,
|
||||
0xb6, 0xee, 0xc3, 0x07, 0x68, 0xe4, 0x4e, 0xc0,
|
||||
0xb7, 0x40, 0x15, 0x55, 0x31, 0x5f, 0xaf, 0xce,
|
||||
0x01, 0x51, 0x09, 0x4f, 0x0b, 0x80, 0x28, 0x0f,
|
||||
0xec, 0x43, 0x8a, 0x14, 0x90, 0x9a, 0x7b, 0x3e,
|
||||
0x81, 0x1e, 0xab, 0xff, 0xed, 0xf6, 0xca, 0x0c,
|
||||
0x6a, 0x9c, 0x91, 0x60, 0x27, 0xb2, 0x04, 0xd3,
|
||||
0x72, 0xd7, 0x08, 0x8c, 0x8e, 0x1b, 0x35, 0x49,
|
||||
0xba, 0x7a, 0xfd, 0x53, 0x22, 0xaa, 0xf5, 0x93,
|
||||
0xf2, 0x63, 0x05, 0xb4, 0x33, 0x9b, 0xea, 0xc8,
|
||||
0xc5, 0x39, 0xfc, 0x5d, 0x56, 0x50, 0xe2, 0xf4,
|
||||
0xc1, 0xa9, 0x76, 0x99, 0xe7, 0xd0, 0xc6, 0x83,
|
||||
0x11, 0x77, 0x70, 0xa6, 0x46, 0x38, 0x1d, 0x74,
|
||||
0x6b, 0xdf, 0x30, 0xcf, 0xd1, 0x29, 0x7f, 0x4b,
|
||||
0xe8, 0x1f, 0xc4, 0xa1, 0x75, 0xae, 0x3f, 0xf1,
|
||||
0xad, 0x42, 0x2d, 0xfe, 0x62, 0x61, 0x6d, 0x3d,
|
||||
0xa7, 0x0a, 0x6e, 0xde, 0x16, 0x36, 0xd2, 0xcb,
|
||||
0x5c, 0xc2, 0x7c, 0xd6, 0x37, 0xa0, 0x20, 0xb5,
|
||||
0xf3, 0xac, 0x71, 0x64, 0x26, 0x66, 0x88, 0x23,
|
||||
0x52, 0xdb, 0x2e, 0x10, 0x84, 0x0e, 0x6f, 0x89,
|
||||
0xb3, 0x86, 0xe5, 0xe6, 0x25, 0x78, 0xd4, 0x2a,
|
||||
0xa8, 0x5b, 0xc9, 0x44, 0x24, 0x17, 0x1a, 0xf0,
|
||||
0x69, 0x7e, 0xbf, 0x8d, 0x5a, 0x82, 0x9e, 0xf9,
|
||||
0xc7, 0xf7, 0x4c, 0x92, 0x9d, 0x34, 0x02, 0x45,
|
||||
0x59, 0xe1, 0x48, 0x7d, 0xb9, 0x94, 0x41, 0x47,
|
||||
0x54, 0x00, 0x3c, 0x65, 0xf8, 0xb8, 0xcd, 0x0d,
|
||||
0xe9, 0x9f, 0x8f, 0x79, 0x3a, 0xda, 0x4a, 0x97,
|
||||
0xef, 0xa2, 0x21, 0x58, 0x67, 0x32, 0xb0, 0x3b,
|
||||
0xe0, 0x85, 0x19, 0x12, 0x2c, 0xbc, 0x4d, 0xe3,
|
||||
0x2b, 0x03, 0xbe, 0xfb, 0xbd, 0x57, 0xeb, 0x06,
|
||||
0xfa, 0xbb, 0xdd, 0xa5, 0xa3, 0x73, 0x18, 0xd9
|
||||
};
|
||||
|
||||
for (std::size_t i = 0; i != sizeof array / sizeof *array; ++i) {
|
||||
const bool success = array [i] == result [i];
|
||||
if (!success) {
|
||||
rw_assert (0, 0, line,
|
||||
"randomly shuffled sequence failed to match "
|
||||
"the expected result (data portability failure) "
|
||||
"%d != %d at %zu",
|
||||
array [i], result [i], i + 1);
|
||||
}
|
||||
}
|
||||
|
||||
#else
|
||||
rw_note (0, 0, 0,
|
||||
"_RWSTD_NO_EXT_PORTABLE_RANDOM_SEQUENCE is defined, "
|
||||
"no random_test available");
|
||||
#endif // _RWSTD_NO_EXT_PORTABLE_RANDOM_SEQUENCE
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 1024; // --nloops=#
|
||||
/* extern */ int rw_opt_no_random; // --no-random
|
||||
/* extern */ int rw_opt_no_random_generator; // --no-random_generator
|
||||
/* extern */ int rw_opt_no_rand_test; // --no-rand_test
|
||||
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
typedef RandomAccessIter<UserClass>::difference_type DiffT;
|
||||
typedef RandomGenerator<DiffT> RandGenT;
|
||||
|
||||
if (rw_opt_no_random) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::random test disabled");
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s> "
|
||||
"std::random_shuffle (%1$s, %1$s)",
|
||||
"RandomAccessIterator");
|
||||
|
||||
test_random_shuffle (__LINE__, N, RandomAccessIter<UserClass>(),
|
||||
(RandGenT*)0, (UserClass*)0, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rand_test) {
|
||||
rw_note (0, __FILE__, __LINE__, "random algorithm test disabled");
|
||||
}
|
||||
else {
|
||||
test_random_shuffle (__LINE__);
|
||||
}
|
||||
|
||||
if (rw_opt_no_random_generator) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::random with random_generator test disabled");
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> "
|
||||
"std::random_shuffle (%1$s, %1$s, %2$s)",
|
||||
"RandomAccessIterator", "RandomNumberGenerator");
|
||||
|
||||
test_random_shuffle (__LINE__, N, RandomAccessIter<UserClass>(),
|
||||
(RandGenT*)0, (UserClass*)0, true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.random_shuffle",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops#0 " // must be non-negative
|
||||
"|-no-random# "
|
||||
"|-no-random_generator# "
|
||||
"|-no-rand_test",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_random,
|
||||
&rw_opt_no_random_generator,
|
||||
&rw_opt_no_rand_test);
|
||||
}
|
||||
609
extern/stdcxx/4.2.1/tests/algorithms/25.remove.cpp
vendored
Normal file
609
extern/stdcxx/4.2.1/tests/algorithms/25.remove.cpp
vendored
Normal file
@@ -0,0 +1,609 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.remove.cpp - test exercising 25.2.7 [lib.alg.remove]
|
||||
*
|
||||
* $Id: 25.remove.cpp 588637 2007-10-26 13:31:06Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for remove(), remove_copy(), ...
|
||||
#include <cstring> // for strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<assign<base<> > > >
|
||||
remove (FwdIter<eq_comp<assign<base<> > > >,
|
||||
FwdIter<eq_comp<assign<base<> > > >,
|
||||
const eq_comp<assign<base<> > >&);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<assign<base<> > > >
|
||||
remove_if (FwdIter<eq_comp<assign<base<> > > >,
|
||||
FwdIter<eq_comp<assign<base<> > > >,
|
||||
predicate<eq_comp<assign<base<> > > >);
|
||||
|
||||
template
|
||||
OutputIter<eq_comp<assign<base<> > > >
|
||||
remove_copy (InputIter<eq_comp<assign<base<> > > >,
|
||||
InputIter<eq_comp<assign<base<> > > >,
|
||||
OutputIter<eq_comp<assign<base<> > > >,
|
||||
const eq_comp<assign<base<> > >&);
|
||||
|
||||
template
|
||||
OutputIter<eq_comp<assign<base<> > > >
|
||||
remove_copy_if (InputIter<eq_comp<assign<base<> > > >,
|
||||
InputIter<eq_comp<assign<base<> > > >,
|
||||
OutputIter<eq_comp<assign<base<> > > >,
|
||||
predicate<eq_comp<assign<base<> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// names of tested functions
|
||||
const char* const fnames[] = { "remove", "remove_copy" };
|
||||
const char* const fnames_if[] = { "remove_if", "remove_copy_if" };
|
||||
|
||||
// tags to select remove or remove_copy at compile time
|
||||
struct RemoveTag {
|
||||
enum { fname_inx = 0 };
|
||||
int use_predicate;
|
||||
};
|
||||
|
||||
struct RemoveCopyTag {
|
||||
enum { fname_inx = 1 };
|
||||
int use_predicate;
|
||||
};
|
||||
|
||||
// used as a dummy template argument to test functions exercising remove()
|
||||
// and remove_if() (to differentiate from remove_copy() and remove_copy_if())
|
||||
struct NoIterator { };
|
||||
const char* type_name (NoIterator, const UserClass*)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
typedef unsigned char UChar;
|
||||
|
||||
|
||||
// predicate used as an argument to remove_if() and remove_copy_if()
|
||||
template <class T>
|
||||
struct EqualityPredicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
EqualityPredicate (const T &val, int /* dummy */)
|
||||
: val_ (val) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
class ConvertibleToBool {
|
||||
bool result_;
|
||||
public:
|
||||
ConvertibleToBool (bool res): result_ (res) { /* empty */ }
|
||||
operator bool() const { return result_; }
|
||||
};
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
ConvertibleToBool operator() (const T &arg) {
|
||||
++funcalls_;
|
||||
return ConvertibleToBool (arg == val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (EqualityPredicate&);
|
||||
const T &val_;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
std::size_t EqualityPredicate<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::remove() and std::remove_if()
|
||||
template <class Iterator, class T, class Predicate>
|
||||
void test_remove (int line,
|
||||
const char *src, const char val, std::size_t nrem,
|
||||
Iterator, NoIterator, const T*,
|
||||
const Predicate*, RemoveTag tag)
|
||||
{
|
||||
static const char* const itname = type_name (Iterator (), (T*)0);
|
||||
static const char* const fname = tag.use_predicate ?
|
||||
fnames_if [tag.fname_inx] : fnames [tag.fname_inx];
|
||||
|
||||
// compute the length of the source sequence
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to remove
|
||||
T* const xsrc = T::from_char (src, nsrc + 1);
|
||||
|
||||
// construct an element to remove
|
||||
T to_remove;
|
||||
to_remove.data_.val_ = val;
|
||||
|
||||
// construct a predicate object (used with remove_if() only)
|
||||
const Predicate pred (to_remove, 0);
|
||||
|
||||
// construct iterators pointing to the beginning and end
|
||||
// of the source sequence
|
||||
const Iterator first =
|
||||
make_iter (xsrc, xsrc, xsrc + nsrc, Iterator ());
|
||||
|
||||
const Iterator last =
|
||||
make_iter (xsrc + nsrc, xsrc, xsrc + nsrc, Iterator ());
|
||||
|
||||
// zero out predicate counters
|
||||
T::n_total_op_eq_ = 0;
|
||||
|
||||
// call remove() or remove_if()
|
||||
const Iterator end = tag.use_predicate
|
||||
? std::remove_if (first, last, pred)
|
||||
: std::remove (first, last, to_remove);
|
||||
|
||||
// silence a bogus EDG eccp remark #550-D:
|
||||
// variable "res" was set but never used
|
||||
_RWSTD_UNUSED (end);
|
||||
|
||||
// verify that the returned iterator is set as expected
|
||||
bool success = end.cur_ == first.cur_ + (nsrc - nrem);
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) == first + %zu, got %zd",
|
||||
__LINE__, fname, itname, src, val,
|
||||
nsrc - nrem, end.cur_ - xsrc);
|
||||
|
||||
// verify that the value to be removed does not appear
|
||||
// anywhere in the range [first, end) : p 25.2.7.2
|
||||
success = true;
|
||||
for (std::size_t i = 0; i != nsrc - nrem && success; ++i) {
|
||||
success = UChar (val) != xsrc [i].data_.val_;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) ==> "
|
||||
"\"%{X=*.*}\"; expected element value %#c",
|
||||
__LINE__, fname, itname, src, val,
|
||||
int (nsrc), int (i), xsrc, src [i]);
|
||||
}
|
||||
|
||||
|
||||
// verify that the algorithm is stable: the relative order of the elements
|
||||
// that are not removed remains unchanged : p 25.2.7.4
|
||||
success = true;
|
||||
for (std::size_t i = 1; i < nsrc - nrem && success; ++i) {
|
||||
success = xsrc [i - 1].id_ < xsrc [i].id_;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) ==> \"%{X=#*.*}\"; "
|
||||
"unstable at offset %zu element ids: %d and %d",
|
||||
__LINE__, fname, itname, src, val,
|
||||
int (nsrc), int (i - 1), xsrc,
|
||||
i - 1, xsrc [i - 1].id_, xsrc [i].id_);
|
||||
}
|
||||
|
||||
|
||||
// verify that the values of elements in the range [end, last)
|
||||
// are unchanged
|
||||
success = true;
|
||||
for (std::size_t i = nsrc - nrem; i != nsrc && success; ++i) {
|
||||
success = src [i] == xsrc [i].data_.val_;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) ==> "
|
||||
"\"%{X=*.*}\"; expected element value %#c",
|
||||
__LINE__, fname, itname, src, val,
|
||||
int (nsrc), int (i), xsrc, val);
|
||||
}
|
||||
|
||||
|
||||
// verify the number of applications of the predicate: p 25.2.7.5
|
||||
if (tag.use_predicate) {
|
||||
rw_assert (pred.funcalls_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"Predicate::operator() %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
pred.funcalls_, nsrc);
|
||||
}
|
||||
else {
|
||||
rw_assert (T::n_total_op_eq_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"T::operator< %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
T::n_total_op_eq_, nsrc);
|
||||
}
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::remove_copy()
|
||||
template <class Iterator, class OutputIterator, class Predicate, class T>
|
||||
void test_remove (int line,
|
||||
const char *src, const char val, std::size_t nrem,
|
||||
Iterator it, OutputIterator dummy, const T*,
|
||||
const Predicate*, RemoveCopyTag tag)
|
||||
{
|
||||
static const char* const itname = type_name (it, (T*)0);
|
||||
static const char* const fname = tag.use_predicate ?
|
||||
fnames_if [tag.fname_inx] : fnames [tag.fname_inx];
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xdst = T::from_char (src, nsrc);
|
||||
|
||||
T to_remove;
|
||||
to_remove.data_.val_ = val;
|
||||
|
||||
const Predicate pred (to_remove, 0);
|
||||
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc + nsrc, it);
|
||||
const Iterator last = make_iter (xsrc + nsrc, xsrc, xsrc + nsrc, it);
|
||||
const OutputIterator result = make_iter (xdst, xdst, xdst + nsrc, dummy);
|
||||
|
||||
// zero out predicate counters
|
||||
T::n_total_op_eq_ = 0;
|
||||
|
||||
const OutputIterator end = tag.use_predicate
|
||||
? std::remove_copy_if (first, last, result, pred)
|
||||
: std::remove_copy (first, last, result, to_remove);
|
||||
|
||||
// silence a bogus EDG eccp remark #550-D:
|
||||
// variable "res" was set but never used
|
||||
_RWSTD_UNUSED (end);
|
||||
|
||||
// verify that the returned iterator is set as expected p 25.2.7.8
|
||||
bool success = end.cur_ == result.cur_ + (nsrc - nrem);
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) == first + %zu, got %zd",
|
||||
__LINE__, fname, itname, src, val, nsrc - nrem, end.cur_ - xsrc);
|
||||
|
||||
// verify that the value to be removed does not appear anywhere
|
||||
// in the range [result, end)
|
||||
success = true;
|
||||
for (std::size_t i = 0; i != nsrc - nrem && success; ++i) {
|
||||
success = UChar (val) != xdst [i].data_.val_;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) ==> "
|
||||
"\"%{X=*.*}\"; expected element value %#c",
|
||||
__LINE__, fname, itname, src, val,
|
||||
int (nsrc - nrem), int (i), xdst, src [i]);
|
||||
}
|
||||
|
||||
// verify that the algorithm is stable: the relative order of the elements
|
||||
// that are not removed remains unchanged : p 25.2.7.10
|
||||
success = true;
|
||||
for (std::size_t i = 1; i < nsrc - nrem && success; ++i) {
|
||||
success = xdst [i - 1].id_ < xdst [i].id_;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) ==> \"%{X=#*.*}\"; "
|
||||
"unstable at offset %zu: element ids: %d and %d",
|
||||
__LINE__, fname, itname, src, val,
|
||||
int (nsrc - nrem), int (i - 1), xdst,
|
||||
i - 1, xdst [i - 1].id_, xdst [i].id_);
|
||||
}
|
||||
|
||||
// verify the number of applications of the predicate p 25.2.7.9
|
||||
if (tag.use_predicate) {
|
||||
rw_assert (pred.funcalls_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"Predicate::operator() %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
pred.funcalls_, nsrc);
|
||||
}
|
||||
else {
|
||||
rw_assert (T::n_total_op_eq_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"T::operator< %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
T::n_total_op_eq_, nsrc);
|
||||
}
|
||||
|
||||
delete[] xsrc;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises all four function templates
|
||||
template <class Iterator1, class Iterator2, class T,
|
||||
class Predicate, class Tag>
|
||||
void test_remove (Iterator1 it1, Iterator2 it2,
|
||||
const T*, const Predicate* pred, Tag tag)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
|
||||
if (tag.fname_inx) { // remove_copy(), remove_copy_if()
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s, %s, %s)",
|
||||
tag.use_predicate ? "remove_copy_if" : "remove_copy",
|
||||
it1name, it2name,
|
||||
tag.use_predicate ? "UnaryPredicate" : "const T&");
|
||||
}
|
||||
else { // remove, remove_if()
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s, %s)",
|
||||
tag.use_predicate ? "remove_if" : "remove",
|
||||
it1name,
|
||||
tag.use_predicate ? "UnaryPredicate" : "const T&");
|
||||
}
|
||||
|
||||
#define TEST(src, val, nremoved) \
|
||||
test_remove (__LINE__, src, val, nremoved, it1, it2, (T*)0, pred, tag)
|
||||
|
||||
// +---------------------- original sequence
|
||||
// | +------ element to remove
|
||||
// | | +- number of removals
|
||||
// | | |
|
||||
// v v v
|
||||
TEST ("", 'a', 0);
|
||||
TEST ("a", 'a', 1);
|
||||
TEST ("aa", 'a', 2);
|
||||
TEST ("aaa", 'a', 3);
|
||||
TEST ("aaaa", 'a', 4);
|
||||
TEST ("aaaaa", 'a', 5);
|
||||
TEST ("aaaaaa", 'a', 6);
|
||||
TEST ("aaaaaaa", 'a', 7);
|
||||
TEST ("aaaaaaaa", 'a', 8);
|
||||
TEST ("aaaaaaaaa", 'a', 9);
|
||||
TEST ("aaaaaaaaaa", 'a', 10);
|
||||
|
||||
TEST ("b", 'a', 0);
|
||||
TEST ("bb", 'a', 0);
|
||||
TEST ("ba", 'a', 1);
|
||||
TEST ("ab", 'a', 1);
|
||||
TEST ("abc", 'a', 1);
|
||||
TEST ("bac", 'a', 1);
|
||||
TEST ("bca", 'a', 1);
|
||||
TEST ("aba", 'a', 2);
|
||||
TEST ("abab", 'a', 2);
|
||||
TEST ("ababa", 'a', 3);
|
||||
TEST ("bababa", 'a', 3);
|
||||
TEST ("bababab", 'a', 3);
|
||||
TEST ("babababa", 'a', 4);
|
||||
TEST ("baacaadaaeaa",'a', 8);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_remove; // --no-remove
|
||||
/* extern */ int rw_opt_no_remove_if; // --no-remove_if
|
||||
/* extern */ int rw_opt_no_remove_copy; // --no-remove_copy
|
||||
/* extern */ int rw_opt_no_remove_copy_if; // --no-remove_copy_if
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate, class Tag>
|
||||
void test_remove (const T*, const Predicate* pred, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class T> "
|
||||
"std::%s (%1$s, %1$s, %s)",
|
||||
"ForwardIterator",
|
||||
tag.use_predicate ? "remove_if" : "remove",
|
||||
tag.use_predicate ? "Predicate" : "const T&");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (FwdIter<T>(), NoIterator (), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (BidirIter<T>(), NoIterator (), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (RandomAccessIter<T>(), NoIterator (), (T*)0, pred, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_remove (const T*)
|
||||
{
|
||||
const RemoveTag remove_tag = { false };
|
||||
const RemoveTag remove_if_tag = { true };
|
||||
|
||||
if (rw_opt_no_remove) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::remove test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 0;
|
||||
test_remove((T*)0, pred, remove_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_remove_if) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::remove_if test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 1;
|
||||
test_remove((T*)0, pred, remove_if_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator, class T, class Predicate, class Tag>
|
||||
void test_remove_copy (const InputIterator& iter, const T*,
|
||||
const Predicate* pred, Tag tag)
|
||||
{
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (iter, OutputIter<T>(0, 0, 0), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (iter, FwdIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (iter, BidirIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove (iter, RandomAccessIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate, class Tag>
|
||||
void test_remove_copy (const T*, const Predicate* pred, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template "
|
||||
"<class InputIterator, class OutputIterator, class T> "
|
||||
"std::%s (InputIterator, InputIterator, "
|
||||
"OutputIterator, %s)",
|
||||
tag.use_predicate ? "remove_copy_if" : "remove_copy",
|
||||
tag.use_predicate ? "Predicate" : "const T&");
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove_copy (InputIter<T>(0, 0, 0), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove_copy (FwdIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove_copy (BidirIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_remove_copy (RandomAccessIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_remove_copy (const T* )
|
||||
{
|
||||
const RemoveCopyTag remove_copy_tag = { false };
|
||||
const RemoveCopyTag remove_copy_if_tag = { true };
|
||||
|
||||
if (rw_opt_no_remove_copy) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::remove_copy test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 0;
|
||||
test_remove_copy((T*)0, pred, remove_copy_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_remove_copy_if) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::remove_copy_if test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 1;
|
||||
test_remove_copy((T*)0, pred, remove_copy_if_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_remove ((UserClass*)0);
|
||||
|
||||
test_remove_copy ((UserClass*)0);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.remove",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-remove# "
|
||||
"|-no-remove_if# "
|
||||
"|-no-remove_copy# "
|
||||
"|-no-remove_copy_if# "
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_remove,
|
||||
&rw_opt_no_remove_if,
|
||||
&rw_opt_no_remove_copy,
|
||||
&rw_opt_no_remove_copy_if,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
631
extern/stdcxx/4.2.1/tests/algorithms/25.replace.cpp
vendored
Normal file
631
extern/stdcxx/4.2.1/tests/algorithms/25.replace.cpp
vendored
Normal file
@@ -0,0 +1,631 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.replace.cpp - test exercising 25.2.4 [lib.alg.replace]
|
||||
*
|
||||
* $Id: 25.replace.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for replace(), replace_copy()
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void replace (FwdIter<eq_comp<assign<base<> > > >,
|
||||
FwdIter<eq_comp<assign<base<> > > >,
|
||||
const eq_comp<assign<base<> > >&,
|
||||
const eq_comp<assign<base<> > >&);
|
||||
|
||||
template
|
||||
void replace_if (FwdIter<assign<base<> > > ,
|
||||
FwdIter<assign<base<> > > ,
|
||||
predicate<assign<base<> > > ,
|
||||
const assign<base<> > &);
|
||||
|
||||
template
|
||||
OutputIter<eq_comp<assign<base<> > > >
|
||||
replace_copy (InputIter<eq_comp<assign<base<> > > >,
|
||||
InputIter<eq_comp<assign<base<> > > >,
|
||||
OutputIter<eq_comp<assign<base<> > > >,
|
||||
const eq_comp<assign<base<> > >&,
|
||||
const eq_comp<assign<base<> > >&);
|
||||
|
||||
template
|
||||
OutputIter<assign<base<> > >
|
||||
replace_copy_if (InputIter<assign<base<> > > ,
|
||||
InputIter<assign<base<> > > ,
|
||||
OutputIter<assign<base<> > > ,
|
||||
predicate<assign<base<> > > ,
|
||||
const assign<base<> > &);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// names of tested functions
|
||||
const char* const fnames[] = { "replace", "replace_copy" };
|
||||
const char* const fnames_if[] = { "replace_if", "replace_copy_if" };
|
||||
|
||||
// tags to select replace or replace_copy at compile time
|
||||
struct ReplaceTag {
|
||||
enum { fname_inx = 0 };
|
||||
int use_predicate;
|
||||
};
|
||||
|
||||
struct ReplaceCopyTag {
|
||||
enum { fname_inx = 1 };
|
||||
int use_predicate;
|
||||
};
|
||||
|
||||
// used as a dummy template argument to test functions exercising replace()
|
||||
// and replace_if() (to differentiate from replace_copy() and replace_copy_if())
|
||||
struct NoIterator { };
|
||||
const char* type_name (NoIterator, const UserClass*)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// predicate used as an argument to replace_if() and replace_copy_if()
|
||||
template <class T>
|
||||
struct EqualityPredicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
EqualityPredicate (const T &val, int /* dummy */)
|
||||
: val_ (val) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
class ConvertibleToBool {
|
||||
bool result_;
|
||||
public:
|
||||
ConvertibleToBool (bool res): result_ (res) { /* empty */ }
|
||||
operator bool() const { return result_; }
|
||||
};
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
ConvertibleToBool operator() (const T &arg) {
|
||||
++funcalls_;
|
||||
return ConvertibleToBool (arg == val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (EqualityPredicate&);
|
||||
const T &val_;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
std::size_t EqualityPredicate<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::replace() and std::replace_if()
|
||||
template <class Iterator, class T, class Predicate>
|
||||
void test_replace (int line,
|
||||
const char *src, // source sequence
|
||||
char val, // value to replace
|
||||
char new_val, // value to replace it with
|
||||
Iterator dummy, // not used
|
||||
NoIterator,
|
||||
const T*,
|
||||
const Predicate*,
|
||||
ReplaceTag tag) // replace() or replace_if()
|
||||
{
|
||||
static const char* const itname = type_name (Iterator (), (T*)0);
|
||||
static const char* const fname = tag.use_predicate ?
|
||||
fnames_if [tag.fname_inx] : fnames [tag.fname_inx];
|
||||
|
||||
// compute the length of the source sequence
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to replace
|
||||
// (make sure there's always at least 1 element, even if the
|
||||
// sequence is otherwise empty, to avoid undefined behavior
|
||||
// when de-referencing xsrc[0] in inactive diagnostic messages)
|
||||
T* const xsrc = T::from_char (src, nsrc + 1);
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
// construct an element to replace
|
||||
T to_replace;
|
||||
to_replace.data_.val_ = val;
|
||||
|
||||
// construct an element to replace it with
|
||||
T replace_with;
|
||||
replace_with.data_.val_ = new_val;
|
||||
|
||||
// construct a predicate object (used with replace_if() only)
|
||||
const Predicate pred (to_replace, 0);
|
||||
|
||||
// construct iterators pointing to the beginning and end
|
||||
// of the source sequence
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc_end, dummy);
|
||||
const Iterator last = make_iter (xsrc_end, xsrc_end, xsrc_end, dummy);
|
||||
|
||||
// zero out predicate counters
|
||||
T::n_total_op_eq_ = 0;
|
||||
|
||||
// call replace() or replace_if()
|
||||
if (tag.use_predicate)
|
||||
std::replace_if (first, last, pred, replace_with);
|
||||
else
|
||||
std::replace (first, last, to_replace, replace_with);
|
||||
|
||||
// verify that the value to be replaced has been replaced
|
||||
// with the replacement value
|
||||
bool success = true;
|
||||
std::size_t i = 0;
|
||||
for ( ; i != nsrc; ++i) {
|
||||
success = to_replace.data_.val_ != xsrc [i].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c, %#c) ==> "
|
||||
"\"%{X=*.*}\"; unexpected element value %#c",
|
||||
__LINE__, fname, itname, src, val, new_val,
|
||||
int (nsrc), int (i), xsrc, src [i]);
|
||||
|
||||
// check the id (not just the value) of the matching element
|
||||
// to make sure it has really been replaced
|
||||
for (i = 0; i != nsrc; ++i) {
|
||||
|
||||
success =
|
||||
val != src [i]
|
||||
|| val == src [i]
|
||||
&& replace_with.origin_ == xsrc [i].origin_;
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c, %#c) ==> "
|
||||
"\"%{X=#*.*}\"; failed to replace element %zu: "
|
||||
"origin %d (%d, %d), expected %d (%d)",
|
||||
__LINE__, fname, itname, src, val, new_val,
|
||||
int (nsrc), int (i), xsrc,
|
||||
i, xsrc [i].origin_, xsrc [i].id_, xsrc [i].src_id_,
|
||||
replace_with.origin_, replace_with.id_);
|
||||
|
||||
// verify the number of applications of the predicate: p 25.2.4.3
|
||||
if (tag.use_predicate) {
|
||||
rw_assert (pred.funcalls_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"Predicate::operator() %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
pred.funcalls_, nsrc);
|
||||
}
|
||||
else {
|
||||
rw_assert (T::n_total_op_eq_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"T::operator< %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
T::n_total_op_eq_, nsrc);
|
||||
}
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::replace_copy()
|
||||
template <class Iterator, class OutputIterator, class T, class Predicate>
|
||||
void test_replace (int line,
|
||||
const char *src, // source sequence
|
||||
char val, // value to replace
|
||||
char new_val, // value to replace it with
|
||||
Iterator it,
|
||||
OutputIterator dummy,
|
||||
const T*,
|
||||
const Predicate*,
|
||||
ReplaceCopyTag tag) // replace_copy or replace_copy_if
|
||||
{
|
||||
static const char* const itname = type_name (it, (T*)0);
|
||||
static const char* const fname = tag.use_predicate ?
|
||||
fnames_if [tag.fname_inx] : fnames [tag.fname_inx];
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to replace
|
||||
// (make sure there's always at least 1 element, even if the
|
||||
// sequence is otherwise empty, to avoid undefined behavior
|
||||
// when de-referencing xsrc[0] in inactive diagnostic messages)
|
||||
T* const xsrc = T::from_char (src, nsrc + 1);
|
||||
T* const xdst = T::from_char (src, nsrc + 1);
|
||||
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
T* const xdst_end = xdst + nsrc;
|
||||
|
||||
T to_replace;
|
||||
to_replace.data_.val_ = val;
|
||||
|
||||
T replace_with;
|
||||
replace_with.data_.val_ = new_val;
|
||||
|
||||
const Predicate pred (to_replace, 0);
|
||||
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const Iterator last = make_iter (xsrc_end, xsrc_end, xsrc_end, it);
|
||||
|
||||
const OutputIterator result = make_iter (xdst, xdst, xdst_end, dummy);
|
||||
|
||||
// zero out predicate counters
|
||||
T::n_total_op_eq_ = 0;
|
||||
|
||||
const OutputIterator end = tag.use_predicate
|
||||
? std::replace_copy_if (first, last, result, pred, replace_with)
|
||||
: std::replace_copy (first, last, result, to_replace, replace_with);
|
||||
|
||||
// verify that the returned iterator is set as expected
|
||||
rw_assert (end.cur_ == result.cur_ + nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) == result + %zu, got %td",
|
||||
__LINE__, fname, itname, src, val, nsrc, end.cur_ - xdst);
|
||||
|
||||
// verify that the value to be replaced does not appear anywhere
|
||||
// in the range [result, end)
|
||||
bool success = true;
|
||||
std::size_t i = 0;
|
||||
for ( ; i != nsrc; ++i) {
|
||||
typedef unsigned char UChar;
|
||||
success = UChar (val) != xdst [i].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) ==> "
|
||||
"\"%{X=*.*}\"; unexpected element value %#c",
|
||||
__LINE__, fname, itname, src, val,
|
||||
int (nsrc), int (i), xdst, src [i]);
|
||||
|
||||
// check the id (not just the value) of the matching element
|
||||
// to make sure it has really been copied
|
||||
for (i = 0; i != nsrc; ++i) {
|
||||
success =
|
||||
val != src [i]
|
||||
|| val == src [i]
|
||||
&& replace_with.origin_ == xdst [i].origin_;
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c, %#c) ==> "
|
||||
"\"%{X=*.*}\"; failed to copy and replace element %zu: "
|
||||
"origin %d (%d, %d), expected %d (%d)",
|
||||
__LINE__, fname, itname, src, val, new_val,
|
||||
int (nsrc), int (i), xdst,
|
||||
i, xdst [i].origin_, xdst [i].id_, xdst [i].src_id_,
|
||||
replace_with.origin_, replace_with.id_);
|
||||
|
||||
// verify the number of applications of the predicate: p 25.2.4.7
|
||||
if (tag.use_predicate) {
|
||||
rw_assert (pred.funcalls_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"Predicate::operator() %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
pred.funcalls_, nsrc);
|
||||
}
|
||||
else {
|
||||
rw_assert (T::n_total_op_eq_ == nsrc, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ..., %#c) called "
|
||||
"T::operator< %zu times, %zu expected",
|
||||
__LINE__, fname, itname, src, val,
|
||||
T::n_total_op_eq_, nsrc);
|
||||
}
|
||||
|
||||
delete[] xsrc;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises all four function templates
|
||||
template <class Iterator1, class Iterator2, class T,
|
||||
class Predicate, class Tag>
|
||||
void test_replace (Iterator1 it1, Iterator2 it2, const T*,
|
||||
const Predicate* pred, Tag tag)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
|
||||
if (tag.fname_inx) { // replace_copy(), replace_copy_if()
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %s, %s, %s, const T&)",
|
||||
tag.use_predicate ? "replace_copy_if" : "replace_copy",
|
||||
it1name, it1name, it2name,
|
||||
tag.use_predicate ? "UnaryPredicate" : "const T&");
|
||||
}
|
||||
else { // replace, replace_if()
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %s, %s, const T&)",
|
||||
tag.use_predicate ? "replace_if" : "replace",
|
||||
it1name, it1name,
|
||||
tag.use_predicate ? "UnaryPredicate" : "const T&");
|
||||
}
|
||||
|
||||
|
||||
#define TEST(src, val, new_val) \
|
||||
test_replace (__LINE__, src, val, new_val, it1, it2, (T*)0, pred, tag)
|
||||
|
||||
// +----------------------- original sequence
|
||||
// | +------- value to replace
|
||||
// | | +- value to replace it with
|
||||
// | | |
|
||||
// v v v
|
||||
TEST ("", 'a', 'b');
|
||||
TEST ("a", 'a', 'b');
|
||||
TEST ("aa", 'a', 'b');
|
||||
TEST ("aaa", 'a', 'b');
|
||||
TEST ("aaaa", 'a', 'b');
|
||||
TEST ("aaaaa", 'a', 'b');
|
||||
TEST ("aaaaaa", 'a', 'b');
|
||||
TEST ("aaaaaaa", 'a', 'b');
|
||||
TEST ("aaaaaaaa", 'a', 'b');
|
||||
TEST ("aaaaaaaaa", 'a', 'b');
|
||||
TEST ("aaaaaaaaaa", 'a', 'b');
|
||||
|
||||
TEST ("b", 'a', 'b');
|
||||
TEST ("bb", 'a', 'b');
|
||||
TEST ("ba", 'a', 'b');
|
||||
TEST ("ab", 'a', 'b');
|
||||
TEST ("abc", 'a', 'b');
|
||||
TEST ("bac", 'a', 'b');
|
||||
TEST ("bca", 'a', 'b');
|
||||
TEST ("aba", 'a', 'b');
|
||||
TEST ("abab", 'a', 'b');
|
||||
TEST ("ababa", 'a', 'b');
|
||||
TEST ("bababa", 'a', 'b');
|
||||
TEST ("bababab", 'a', 'b');
|
||||
TEST ("babababa", 'a', 'b');
|
||||
TEST ("bbbbbbbbb", 'a', 'b');
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_replace; // --no-replace
|
||||
/* extern */ int rw_opt_no_replace_if; // --no-replace_if
|
||||
/* extern */ int rw_opt_no_replace_copy; // --no-replace_copy
|
||||
/* extern */ int rw_opt_no_replace_copy_if; // --no-replace_copy_if
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
template <class T, class Predicate, class Tag>
|
||||
void test_replace (const T* , const Predicate* pred, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class ForwardIterator, class T> "
|
||||
"std::%s (ForwardIterator, ForwardIterator, "
|
||||
"%s, const T&)",
|
||||
tag.use_predicate ? "replace_if" : "replace",
|
||||
tag.use_predicate ? "Predicate" : "const T&");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (FwdIter<T>(), NoIterator (), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (BidirIter<T>(), NoIterator (), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (RandomAccessIter<T>(), NoIterator (), (T*)0, pred, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_replace (const T* )
|
||||
{
|
||||
const ReplaceTag replace_tag = { false };
|
||||
const ReplaceTag replace_if_tag = { true };
|
||||
|
||||
if (rw_opt_no_replace) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::replace test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 0;
|
||||
test_replace((T*)0, pred, replace_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_replace_if) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::replace_if test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 1;
|
||||
test_replace((T*)0, pred, replace_if_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator, class T, class Predicate, class Tag>
|
||||
void test_replace_copy (const InputIterator& iter, const T*,
|
||||
const Predicate* pred, Tag tag)
|
||||
{
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (iter, OutputIter<T>(0, 0, 0), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (iter, FwdIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (iter, BidirIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace (iter, RandomAccessIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate, class Tag>
|
||||
void test_replace_copy (const T*, const Predicate* pred, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template "
|
||||
"<class InputIterator, class OutputIterator, class T> "
|
||||
"std::%s (InputIterator, InputIterator, "
|
||||
"OutputIterator, %s, const T&)",
|
||||
tag.use_predicate ? "replace_copy_if" : "replace_copy",
|
||||
tag.use_predicate ? "Predicate" : "const T&");
|
||||
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace_copy (InputIter<T>(0, 0, 0), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace_copy (FwdIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace_copy (BidirIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_replace_copy (RandomAccessIter<T>(), (T*)0, pred, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_replace_copy (const T* )
|
||||
{
|
||||
const ReplaceCopyTag replace_copy_tag = { false };
|
||||
const ReplaceCopyTag replace_copy_if_tag = { true };
|
||||
|
||||
if (rw_opt_no_replace_copy) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::replace_copy test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*) 0;
|
||||
test_replace_copy ((T*)0, pred, replace_copy_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_replace_copy_if) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::replace_copy_if test disabled");
|
||||
}
|
||||
else {
|
||||
const EqualityPredicate<T>* const pred = (EqualityPredicate<T>*)1;
|
||||
test_replace_copy ((T*)0, pred, replace_copy_if_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_replace ((UserClass*)0);
|
||||
|
||||
test_replace_copy ((UserClass*)0);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.replace",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-replace# "
|
||||
"|-no-replace_if# "
|
||||
"|-no-replace_copy# "
|
||||
"|-no-replace_copy_if# "
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_replace,
|
||||
&rw_opt_no_replace_if,
|
||||
&rw_opt_no_replace_copy,
|
||||
&rw_opt_no_replace_copy_if,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
415
extern/stdcxx/4.2.1/tests/algorithms/25.reverse.cpp
vendored
Normal file
415
extern/stdcxx/4.2.1/tests/algorithms/25.reverse.cpp
vendored
Normal file
@@ -0,0 +1,415 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.reverse.cpp - test exercising 25.2.9 [lib.alg.reverse]
|
||||
*
|
||||
* $Id: 25.reverse.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for reverse, reverse_copy
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void reverse (BidirIter<assign<base<cpy_ctor> > >,
|
||||
BidirIter<assign<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
OutputIter<eq_comp<assign<base<> > > >
|
||||
reverse_copy (BidirIter<eq_comp<assign<base<> > > >,
|
||||
BidirIter<eq_comp<assign<base<> > > >,
|
||||
OutputIter<eq_comp<assign<base<> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// tags to select reverse or reverse_copy at compile time
|
||||
struct ReverseTag {
|
||||
enum { fname_inx = 0 };
|
||||
int dummy;
|
||||
};
|
||||
|
||||
struct ReverseCopyTag {
|
||||
enum { fname_inx = 1 };
|
||||
int dummy;
|
||||
};
|
||||
|
||||
// used as a dummy template argument to test functions exercising reverse()
|
||||
// and reverse_if() (to differentiate from reverse_copy() and reverse_copy_if())
|
||||
struct NoIterator { };
|
||||
const char* type_name (NoIterator, const UserClass*)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
unsigned iter_swap_calls;
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
_RWSTD_SPECIALIZED_FUNCTION
|
||||
void iter_swap (BidirIter<UserClass> i, BidirIter<UserClass> j)
|
||||
{
|
||||
++iter_swap_calls;
|
||||
|
||||
const int tmp = (*i).data_.val_;
|
||||
|
||||
(*i).data_.val_ = (*j).data_.val_;
|
||||
(*j).data_.val_ = tmp;
|
||||
}
|
||||
|
||||
_RWSTD_SPECIALIZED_FUNCTION
|
||||
void iter_swap (RandomAccessIter<UserClass> i, RandomAccessIter<UserClass> j)
|
||||
{
|
||||
++iter_swap_calls;
|
||||
|
||||
const int tmp = (*i).data_.val_;
|
||||
|
||||
(*i).data_.val_ = (*j).data_.val_;
|
||||
(*j).data_.val_ = tmp;
|
||||
}
|
||||
|
||||
} // namespace std
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::reverse()
|
||||
template <class Iterator, class T>
|
||||
void test_reverse (int line,
|
||||
const char *src,
|
||||
Iterator dummy, NoIterator, const T*, ReverseTag)
|
||||
{
|
||||
static const char* const itname = type_name (dummy, (T*)0);
|
||||
const char* const fname = "reverse";
|
||||
|
||||
// compute the length of the source sequence
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to reverse
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
|
||||
// construct iterators pointing to the beginning and end
|
||||
// of the source sequence
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc + nsrc, dummy);
|
||||
const Iterator last = make_iter (xsrc + nsrc, xsrc, xsrc + nsrc, dummy);
|
||||
|
||||
// zero out the iter_swap() call counter
|
||||
iter_swap_calls = 0;
|
||||
|
||||
// call reverse()
|
||||
std::reverse (first, last);
|
||||
|
||||
bool success = true;
|
||||
std::size_t i = 0;
|
||||
|
||||
// verify that the sequence was correctly reversed and that it was
|
||||
// done by swapping elements i.e., not simply by copying them over
|
||||
for ( ; i != nsrc; ++i) {
|
||||
|
||||
typedef unsigned char UChar;
|
||||
|
||||
success = UChar (src [i]) == xsrc [nsrc - i - 1].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\"; unexpected element value %#c at offset %zu",
|
||||
__LINE__, fname, itname, src,
|
||||
int (nsrc), int (i), xsrc,
|
||||
xsrc [nsrc - i - 1].data_.val_, i);
|
||||
|
||||
const std::size_t iter_swap_expect = nsrc / 2;
|
||||
success = iter_swap_calls == iter_swap_expect;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ...); called iter_swap() "
|
||||
"%zu times, %zu expected",
|
||||
__LINE__, fname, itname, src,
|
||||
iter_swap_calls, iter_swap_expect);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::reverse_copy()
|
||||
template <class Iterator, class OutputIterator, class T>
|
||||
void test_reverse (int line,
|
||||
const char *src,
|
||||
Iterator& it, OutputIterator& ,
|
||||
const T*, ReverseCopyTag)
|
||||
{
|
||||
static const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = "reverse_copy";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xdst = T::from_char (src, nsrc);
|
||||
|
||||
const Iterator first (xsrc, xsrc, xsrc + nsrc);
|
||||
const Iterator last (xsrc + nsrc, xsrc, xsrc + nsrc);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst + nsrc);
|
||||
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
const OutputIterator end = std::reverse_copy (first, last, result);
|
||||
|
||||
// verify that the returned iterator is set as expected
|
||||
bool success = end.cur_ == result.cur_ + nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ...) == result + %zu, got %td",
|
||||
__LINE__, fname, itname, src, nsrc, end.cur_ - xdst);
|
||||
|
||||
// verify that the sequence was correctly reversed
|
||||
std::size_t i = 0;
|
||||
for ( ; i != nsrc; ++i) {
|
||||
|
||||
typedef unsigned char UChar;
|
||||
|
||||
success = UChar (src [i]) == xdst [nsrc - i - 1].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\"; unexpected element value %#c at offset %zu",
|
||||
__LINE__, fname, itname, src,
|
||||
int (nsrc), int (i), xsrc,
|
||||
xdst [nsrc - i - 1].data_.val_, i);
|
||||
|
||||
success = T::n_total_op_assign_ - last_n_op_assign == nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", ...); called operator=() "
|
||||
"%zu times, %zu expected",
|
||||
__LINE__, fname, itname, src,
|
||||
T::n_total_op_assign_ - last_n_op_assign, nsrc);
|
||||
|
||||
delete[] xsrc;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises all four function templates
|
||||
template <class Iterator1, class Iterator2, class T, class Tag>
|
||||
void test_reverse (Iterator1 it1, Iterator2 it2, const T*, Tag tag)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
|
||||
if (tag.fname_inx) { // reverse_copy()
|
||||
rw_info (0, 0, 0, "std::reverse_copy (%s, %1$s, %s)", it1name, it2name);
|
||||
}
|
||||
else { // reverse()
|
||||
rw_info (0, 0, 0, "std::reverse (%s, %1$s)", it1name);
|
||||
}
|
||||
|
||||
|
||||
#define TEST(src) \
|
||||
test_reverse (__LINE__, src, it1, it2, (T*)0, tag)
|
||||
|
||||
TEST ("");
|
||||
TEST ("a");
|
||||
TEST ("ab");
|
||||
TEST ("abc");
|
||||
TEST ("abcd");
|
||||
TEST ("abcde");
|
||||
TEST ("abcdef");
|
||||
TEST ("abcdefg");
|
||||
TEST ("abcdefgh");
|
||||
TEST ("abcdefghi");
|
||||
TEST ("abcdefghij");
|
||||
TEST ("abcdefghijk");
|
||||
TEST ("abcdefghijkl");
|
||||
TEST ("abcdefghijklm");
|
||||
TEST ("abcdefghijklmn");
|
||||
TEST ("abcdefghijklmno");
|
||||
TEST ("abcdefghijklmnop");
|
||||
TEST ("abcdefghijklmnopq");
|
||||
TEST ("abcdefghijklmnopqr");
|
||||
TEST ("abcdefghijklmnopqrs");
|
||||
TEST ("abcdefghijklmnopqrst");
|
||||
TEST ("abcdefghijklmnopqrstu");
|
||||
TEST ("abcdefghijklmnopqrstuv");
|
||||
TEST ("abcdefghijklmnopqrstuvw");
|
||||
TEST ("abcdefghijklmnopqrstuvwx");
|
||||
TEST ("abcdefghijklmnopqrstuvwxy");
|
||||
TEST ("abcdefghijklmnopqrstuvwxyz");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_reverse; // --no-reverse
|
||||
/* extern */ int rw_opt_no_reverse_copy; // --no-reverse_copy
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
|
||||
template <class T, class Tag>
|
||||
void test_reverse(const T*, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s> %1$s std::reverse (%1$s, %1$s)",
|
||||
"BidirectionalIterator");
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse (BidirIter<T>(), NoIterator (), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse (RandomAccessIter<T>(), NoIterator (), (T*)0, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ReverseIterator, class T, class Tag>
|
||||
void test_reverse_copy (ReverseIterator it, const T*, Tag tag)
|
||||
{
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse (it, OutputIter<T>(0, 0, 0), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse (it, FwdIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse (it, BidirIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse (it, RandomAccessIter<T>(), (T*)0, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Tag>
|
||||
void test_reverse_copy (const T*, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> %2$s "
|
||||
"std::reverse_copy (%1$s, %1$s, %2$s)",
|
||||
"BidirectionalIterator", "OutputIterator");
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse_copy (ConstBidirIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse_copy (ConstRandomAccessIter<T>(), (T*)0, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
const ReverseTag reverse_tag = { false };
|
||||
const ReverseCopyTag reverse_copy_tag = { true };
|
||||
|
||||
if (rw_opt_no_reverse) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::reverse test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse((UserClass*)0, reverse_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_reverse_copy) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::reverse_copy test disabled");
|
||||
}
|
||||
else {
|
||||
test_reverse_copy((UserClass*)0, reverse_copy_tag);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.reverse",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-reverse# "
|
||||
"|-no-reverse_copy# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_reverse,
|
||||
&rw_opt_no_reverse_copy,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
453
extern/stdcxx/4.2.1/tests/algorithms/25.rotate.cpp
vendored
Normal file
453
extern/stdcxx/4.2.1/tests/algorithms/25.rotate.cpp
vendored
Normal file
@@ -0,0 +1,453 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.rotate.cpp - test exercising 25.2.10 [lib.alg.rotate]
|
||||
*
|
||||
* $Id: 25.rotate.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for rotate, rotate_copy
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
rotate (FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
OutputIter<assign<base<cpy_ctor> > >
|
||||
rotate_copy (FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >,
|
||||
OutputIter<assign<base<cpy_ctor> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// tags to select rotate or rotate_copy at compile time
|
||||
struct RotateTag {
|
||||
enum { fname_inx = 0 };
|
||||
int dummy;
|
||||
};
|
||||
|
||||
struct RotateCopyTag {
|
||||
enum { fname_inx = 1 };
|
||||
int dummy;
|
||||
};
|
||||
|
||||
// used as a dummy template argument to test functions exercising rotate()
|
||||
// (to differentiate from rotate_copy())
|
||||
struct NoIterator { };
|
||||
const char* type_name (NoIterator, const UserClass*)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
unsigned iter_swap_calls;
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
_RWSTD_SPECIALIZED_FUNCTION
|
||||
void iter_swap (FwdIter<UserClass> i, FwdIter<UserClass> j)
|
||||
{
|
||||
++iter_swap_calls;
|
||||
|
||||
const int tmp = (*i).data_.val_;
|
||||
|
||||
(*i).data_.val_ = (*j).data_.val_;
|
||||
(*j).data_.val_ = tmp;
|
||||
}
|
||||
|
||||
|
||||
_RWSTD_SPECIALIZED_FUNCTION
|
||||
void iter_swap (BidirIter<UserClass> i, BidirIter<UserClass> j)
|
||||
{
|
||||
++iter_swap_calls;
|
||||
|
||||
const int tmp = (*i).data_.val_;
|
||||
|
||||
(*i).data_.val_ = (*j).data_.val_;
|
||||
(*j).data_.val_ = tmp;
|
||||
}
|
||||
|
||||
|
||||
_RWSTD_SPECIALIZED_FUNCTION
|
||||
void iter_swap (RandomAccessIter<UserClass> i, RandomAccessIter<UserClass> j)
|
||||
{
|
||||
++iter_swap_calls;
|
||||
|
||||
const int tmp = (*i).data_.val_;
|
||||
|
||||
(*i).data_.val_ = (*j).data_.val_;
|
||||
(*j).data_.val_ = tmp;
|
||||
}
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::rotate()
|
||||
template <class Iterator, class T>
|
||||
void test_rotate (int line,
|
||||
const char *src,
|
||||
std::size_t midnsrc,
|
||||
Iterator it, NoIterator, const T*, RotateTag)
|
||||
{
|
||||
static const char* const itname = type_name (it, (T*)0);
|
||||
const char* const fname = "rotate";
|
||||
|
||||
// compute the length of the source sequence
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to reverse
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
|
||||
// construct iterators pointing to the beginning and end
|
||||
// of the source sequence
|
||||
const Iterator first = make_iter (xsrc, xsrc, xsrc + nsrc, it);
|
||||
const Iterator middle = make_iter (xsrc + midnsrc, xsrc, xsrc + nsrc, it);
|
||||
const Iterator last = make_iter (xsrc + nsrc, xsrc, xsrc + nsrc, it);
|
||||
|
||||
// zero out the iter_swap() call counter
|
||||
iter_swap_calls = 0;
|
||||
|
||||
// call rotate()
|
||||
std::rotate (first, middle, last);
|
||||
|
||||
bool success = true;
|
||||
std::size_t i = 0;
|
||||
std::size_t xpos = 0;
|
||||
|
||||
// verify that the sequence was correctly reversed and that it was
|
||||
// done by swapping elements i.e., not simply by copying them over
|
||||
for ( ; i != nsrc; ++i) {
|
||||
|
||||
xpos = (i + (nsrc - midnsrc)) % nsrc;
|
||||
|
||||
typedef unsigned char UChar;
|
||||
|
||||
success = UChar (src [i]) == xsrc [xpos].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", %zu, ...) ==> "
|
||||
"\"%{X=*.*}\"; unexpected element value %#c at %zu",
|
||||
__LINE__, fname, itname, src, midnsrc,
|
||||
int (nsrc), int (i), xsrc, xsrc [xpos].data_.val_, i);
|
||||
|
||||
success = iter_swap_calls <= nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s>(\"%s\", %zu, ...); called iter_swap() "
|
||||
"%zu times, expected no more than %zu",
|
||||
__LINE__, fname, itname, src, midnsrc,
|
||||
iter_swap_calls, nsrc);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::rotate_copy()
|
||||
template <class Iterator, class OutputIterator, class T>
|
||||
void test_rotate (int line,
|
||||
const char *src,
|
||||
std::size_t midnsrc,
|
||||
Iterator it, OutputIterator dummy,
|
||||
const T*, RotateCopyTag)
|
||||
{
|
||||
static const char* const it1name = type_name (it, (T*)0);
|
||||
static const char* const it2name = type_name (dummy, (T*)0);
|
||||
const char* const fname = "rotate_copy";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* const xdst = T::from_char (src, nsrc);
|
||||
|
||||
const Iterator first (xsrc, xsrc, xsrc + nsrc);
|
||||
const Iterator middle (xsrc + midnsrc, xsrc, xsrc + nsrc);
|
||||
const Iterator last (xsrc + nsrc, xsrc, xsrc + nsrc);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst + nsrc);
|
||||
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
const OutputIterator end = std::rotate_copy (first, middle, last, result);
|
||||
|
||||
// verify that the returned iterator is set as expected
|
||||
bool success = end.cur_ == result.cur_ + nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s>(\"%s\", %zu, ...) == result + %zu, got %td",
|
||||
__LINE__, fname, it1name, it2name, src, midnsrc,
|
||||
nsrc, end.cur_ - xdst);
|
||||
|
||||
// verify that the sequence was correctly rotated
|
||||
std::size_t i = 0;
|
||||
std::size_t xpos = 0;
|
||||
for ( ; i != nsrc; ++i) {
|
||||
|
||||
xpos = (i + (nsrc - midnsrc)) % nsrc;
|
||||
|
||||
typedef unsigned char UChar;
|
||||
|
||||
success = UChar (src [i]) == xdst [xpos].data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s>(\"%s\", %zu, ...) ==> "
|
||||
"\"%{X=*.*}\"; unexpected element value %#c at %zu",
|
||||
__LINE__, fname, it1name, it2name, src, midnsrc,
|
||||
int (nsrc), int (i), xsrc, xdst [xpos].data_.val_, i);
|
||||
|
||||
success = T::n_total_op_assign_ - last_n_op_assign == nsrc;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s>(\"%s\", %zu, ...); called operator=() "
|
||||
"%zu times, %zu expected",
|
||||
__LINE__, fname, it1name, it2name, src, midnsrc,
|
||||
T::n_total_op_assign_ - last_n_op_assign, nsrc);
|
||||
|
||||
delete[] xsrc;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises all two function templates
|
||||
template <class Iterator1, class Iterator2, class T, class Tag>
|
||||
void test_rotate (Iterator1 it1, Iterator2 it2, const T*, Tag tag)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
|
||||
if (tag.fname_inx) { // rotate_copy()
|
||||
rw_info (0, 0, 0,
|
||||
"std::rotate_copy (%s, %1$s, %1$s, %s)",
|
||||
it1name, it2name);
|
||||
}
|
||||
else { // reverse, rotate()
|
||||
rw_info (0, 0, 0,
|
||||
"std::rotate (%s, %1$s, %1$s)",
|
||||
it1name);
|
||||
}
|
||||
|
||||
|
||||
#define TEST(src, middle) \
|
||||
test_rotate (__LINE__, src, middle, it1, it2, (T*)0, tag)
|
||||
|
||||
TEST ("", 0);
|
||||
TEST ("a", 0);
|
||||
TEST ("ab", 1);
|
||||
TEST ("abc", 1);
|
||||
TEST ("abcd", 2);
|
||||
TEST ("abcde", 2);
|
||||
TEST ("abcdef", 3);
|
||||
TEST ("abcdefg", 3);
|
||||
TEST ("abcdefgh", 4);
|
||||
TEST ("abcdefghi", 4);
|
||||
TEST ("abcdefghij", 5);
|
||||
|
||||
TEST ("abcdefghijk", 0);
|
||||
TEST ("abcdefghijk", 1);
|
||||
TEST ("abcdefghijk", 2);
|
||||
TEST ("abcdefghijk", 3);
|
||||
TEST ("abcdefghijk", 4);
|
||||
TEST ("abcdefghijk", 5);
|
||||
TEST ("abcdefghijk", 6);
|
||||
TEST ("abcdefghijk", 7);
|
||||
TEST ("abcdefghijk", 8);
|
||||
TEST ("abcdefghijk", 9);
|
||||
TEST ("abcdefghijk", 10);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_rotate; // --no-rotate
|
||||
/* extern */ int rw_opt_no_rotate_copy; // --no-rotate_copy
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
|
||||
template <class T, class Tag>
|
||||
void test_rotate (const T*, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s> std::rotate (%1$s, %1$s, %1$s)",
|
||||
"ForwardIterator");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (FwdIter<T>(), NoIterator (), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (BidirIter<T>(), NoIterator (), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (RandomAccessIter<T>(), NoIterator (), (T*)0, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class RotateIterator, class T, class Tag>
|
||||
void test_rotate_copy (RotateIterator it, const T*, Tag tag)
|
||||
{
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (it, OutputIter<T>(0, 0, 0), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (it, FwdIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (it, BidirIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate (it, RandomAccessIter<T>(), (T*)0, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Tag>
|
||||
void test_rotate_copy(const T*, Tag tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> %2$s "
|
||||
"std::rotate_copy (%1$s, %1$s, %1$s, %2$s)",
|
||||
"ForwardIterator", "OutputIterator");
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate_copy (ConstFwdIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate_copy (ConstBidirIter<T>(), (T*)0, tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate_copy (ConstRandomAccessIter<T>(), (T*)0, tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
const RotateTag rotate_tag = { false };
|
||||
const RotateCopyTag rotate_copy_tag = { true };
|
||||
|
||||
if (rw_opt_no_rotate) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::rotate test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate((UserClass*)0, rotate_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rotate_copy) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::rotate_copy test disabled");
|
||||
}
|
||||
else {
|
||||
test_rotate_copy((UserClass*)0, rotate_copy_tag);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.rotate",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-rotate# "
|
||||
"|-no-rotate_copy# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_rotate,
|
||||
&rw_opt_no_rotate_copy,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
710
extern/stdcxx/4.2.1/tests/algorithms/25.search.cpp
vendored
Normal file
710
extern/stdcxx/4.2.1/tests/algorithms/25.search.cpp
vendored
Normal file
@@ -0,0 +1,710 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.search.cpp - test exercising 25.1.9 [lib.alg.search]
|
||||
*
|
||||
* $Id: 25.search.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2005 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for search, search_n
|
||||
#include <cstring> // for strlen
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
// instantiate each algorithm on all kinds of iterators
|
||||
// it is required to work with (the algorithm may delegate
|
||||
// to different implementations specialized for each kind
|
||||
// of iterator)
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
search (FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
BidirIter<eq_comp<base<> > >
|
||||
search (BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
RandomAccessIter<eq_comp<base<> > >
|
||||
search (RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
search (FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
BidirIter<eq_comp<base<> > >
|
||||
search (BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
RandomAccessIter<eq_comp<base<> > >
|
||||
search (RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
search_n (FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
Size<int>, const eq_comp<base<> >&);
|
||||
|
||||
template
|
||||
BidirIter<eq_comp<base<> > >
|
||||
search_n (BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
Size<int>, const eq_comp<base<> >&);
|
||||
|
||||
template
|
||||
RandomAccessIter<eq_comp<base<> > >
|
||||
search_n (RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
Size<int>, const eq_comp<base<> >&);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<base<> > >
|
||||
search_n (FwdIter<eq_comp<base<> > >,
|
||||
FwdIter<eq_comp<base<> > >,
|
||||
Size<int>, const eq_comp<base<> >&,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
BidirIter<eq_comp<base<> > >
|
||||
search_n (BidirIter<eq_comp<base<> > >,
|
||||
BidirIter<eq_comp<base<> > >,
|
||||
Size<int>, const eq_comp<base<> >&,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
template
|
||||
RandomAccessIter<eq_comp<base<> > >
|
||||
search_n (RandomAccessIter<eq_comp<base<> > >,
|
||||
RandomAccessIter<eq_comp<base<> > >,
|
||||
Size<int>, const eq_comp<base<> >&,
|
||||
binary_predicate<eq_comp<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class U>
|
||||
struct EqualityPredicate
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class
|
||||
// from being default constructible
|
||||
EqualityPredicate (T* /* dummy */, U* /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
class ConvertibleToBool {
|
||||
bool result_;
|
||||
public:
|
||||
ConvertibleToBool (bool res): result_ (res) { /* empty */ }
|
||||
operator bool() const { return result_; }
|
||||
};
|
||||
|
||||
ConvertibleToBool operator() (const T &x, const U &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return x == y;
|
||||
}
|
||||
};
|
||||
|
||||
template <class T, class U>
|
||||
std::size_t EqualityPredicate<T, U>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// tags to select predicate or non-predicate versions
|
||||
template <class T>
|
||||
struct PredicateTag {
|
||||
enum { pred_inx = 1 };
|
||||
int dummy;
|
||||
|
||||
typedef EqualityPredicate<T, T> Predicate;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
struct NonPredicateTag {
|
||||
enum { pred_inx = 0 };
|
||||
int dummy;
|
||||
|
||||
// dummy predicate to be used for non-predicate
|
||||
// versions as a placeholder
|
||||
struct DummyPredicate {
|
||||
DummyPredicate(T*, T*) {}
|
||||
|
||||
bool operator() (const T& , const T& ) {
|
||||
return false;
|
||||
}
|
||||
|
||||
static std::size_t funcalls_;
|
||||
};
|
||||
|
||||
typedef DummyPredicate Predicate;
|
||||
};
|
||||
|
||||
template <class T>
|
||||
std::size_t NonPredicateTag<T>::DummyPredicate::funcalls_;
|
||||
|
||||
|
||||
#if defined (_MSC_VER) && _MSC_VER <= 1300
|
||||
// to prevent MSVC 7.0 error LNK2001: unresolved external symbol "public:
|
||||
// static unsigned int
|
||||
// NonPredicateTag<struct UserClass>::DummyPredicate::funcalls_"
|
||||
std::size_t NonPredicateTag<UserClass>::DummyPredicate::funcalls_;
|
||||
#endif
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::search()
|
||||
template
|
||||
<class ForwardIterator1, class ForwardIterator2, class T, class PredTag>
|
||||
void test_search (int line,
|
||||
const char *seq1, const char *seq2,
|
||||
std::size_t off,
|
||||
ForwardIterator1 it1, ForwardIterator2 it2,
|
||||
const T* , PredTag pred_tag)
|
||||
{
|
||||
const char* const fname = "search";
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
static const char* const predname =
|
||||
pred_tag.pred_inx ? "BinaryPredicate" : "operator <()";
|
||||
|
||||
const std::size_t nseq1 = std::strlen (seq1);
|
||||
const std::size_t nseq2 = std::strlen (seq2);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to search
|
||||
T* const xseq1 = T::from_char (seq1, nseq1);
|
||||
T* const xseq2 = T::from_char (seq2, nseq2);
|
||||
|
||||
// construct iterators pointing to the beginning and end
|
||||
// of the source sequences
|
||||
const ForwardIterator1 first1 =
|
||||
make_iter (xseq1, xseq1, xseq1 + nseq1, it1);
|
||||
const ForwardIterator1 last1 =
|
||||
make_iter (xseq1 + nseq1, xseq1, xseq1 + nseq1, it1);
|
||||
|
||||
const ForwardIterator1 expected = _RWSTD_SIZE_MAX == off ?
|
||||
last1
|
||||
: make_iter (xseq1 + off, xseq1, xseq1 + off, it1);
|
||||
|
||||
_RWSTD_UNUSED (expected);
|
||||
|
||||
const ForwardIterator2 first2 =
|
||||
make_iter (xseq2, xseq2, xseq2 + nseq2, it2);
|
||||
const ForwardIterator2 last2 =
|
||||
make_iter (xseq2 + nseq2, xseq2, xseq2 + nseq2, it2);
|
||||
|
||||
T::n_total_op_eq_ = 0;
|
||||
PredTag::Predicate::funcalls_ = 0;
|
||||
|
||||
typename PredTag::Predicate pred(0, 0);
|
||||
|
||||
const ForwardIterator1 result = pred_tag.pred_inx ?
|
||||
std::search (first1, last1, first2, last2, pred)
|
||||
: std::search (first1, last1, first2, last2);
|
||||
|
||||
_RWSTD_UNUSED (result);
|
||||
|
||||
// 25.1.9, p2:
|
||||
// check the returned iterator
|
||||
rw_assert (result.cur_ == expected.cur_, 0, line,
|
||||
"std::%s<%s, %s%{?}, %s%{;}> (\"%s\", ..., \"%s\") "
|
||||
"found subsequence at %td, expected at %{?}end%{;}%zu%{;}",
|
||||
fname, it1name, it2name, pred_tag.pred_inx, predname,
|
||||
seq1, seq2, result.cur_ - first1.cur_,
|
||||
_RWSTD_SIZE_MAX == off, off);
|
||||
|
||||
// 25.1.9, p3:
|
||||
// Complexity: At most (last1 <20> first1) * (last2 <20> first2)
|
||||
// applications of the corresponding predicate or operator
|
||||
const std::size_t max_op_eq = nseq1 * nseq2;
|
||||
const std::size_t op_called = pred_tag.pred_inx ?
|
||||
PredTag::Predicate::funcalls_
|
||||
: T::n_total_op_eq_;
|
||||
|
||||
rw_assert (op_called <= max_op_eq, 0, line,
|
||||
"std::%s<%s, %s%{?}, %s%{;}> (\"%s\", ..., \"%s\") "
|
||||
"called %s %zu times, expected no more than %zu",
|
||||
fname, it1name, it2name, pred_tag.pred_inx, predname,
|
||||
seq1, seq2, predname, op_called, max_op_eq);
|
||||
|
||||
delete[] xseq1;
|
||||
delete[] xseq2;
|
||||
}
|
||||
|
||||
template
|
||||
<class ForwardIterator1, class ForwardIterator2, class T, class PredTag>
|
||||
void test_search (ForwardIterator1 it1, ForwardIterator2 it2,
|
||||
const T* , PredTag pred_tag)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
static const char* const predname = "EqualityPredicate";
|
||||
|
||||
if (pred_tag.pred_inx) { // use predicate
|
||||
rw_info (0, 0, 0,
|
||||
"std::search (%s, %1$s, %s, %2$s, %s)",
|
||||
it1name, it2name, predname);
|
||||
}
|
||||
else { // not use predicate
|
||||
rw_info (0, 0, 0,
|
||||
"std::search (%s, %1$s, %s, %2$s)",
|
||||
it1name, it2name);
|
||||
}
|
||||
|
||||
#define TEST(seq1, seq2, off) \
|
||||
test_search (__LINE__, seq1, seq2, std::size_t (off), \
|
||||
it1, it2, (T*)0, pred_tag)
|
||||
|
||||
//
|
||||
// +--------------- sequence to search through
|
||||
// | +---------- subsequence to search for
|
||||
// | | +--- match found at offset
|
||||
// v v v
|
||||
TEST ("", "", 0);
|
||||
TEST ("", "a", -1);
|
||||
TEST ("", "ab", -1);
|
||||
TEST ("", "abc", -1);
|
||||
|
||||
TEST ("a", "ab", -1);
|
||||
TEST ("a", "a", 0);
|
||||
TEST ("ab", "b", 1);
|
||||
TEST ("ab", "bb", -1);
|
||||
|
||||
TEST ("abc", "a", 0);
|
||||
TEST ("abc", "b", 1);
|
||||
TEST ("abc", "c", 2);
|
||||
|
||||
TEST ("abc", "ac", -1);
|
||||
TEST ("abc", "ab", 0);
|
||||
TEST ("abc", "bc", 1);
|
||||
TEST ("abc", "cd", -1);
|
||||
TEST ("abc", "abc", 0);
|
||||
|
||||
TEST ("abcd", "ab", 0);
|
||||
TEST ("abcd", "bc", 1);
|
||||
TEST ("abcd", "cd", 2);
|
||||
TEST ("abcd", "abc", 0);
|
||||
TEST ("abcd", "bcd", 1);
|
||||
TEST ("abcd", "bce", -1);
|
||||
|
||||
TEST ("abcde", "", 0);
|
||||
TEST ("abcde", "a", 0);
|
||||
TEST ("abcde", "b", 1);
|
||||
TEST ("abcde", "c", 2);
|
||||
TEST ("abcde", "d", 3);
|
||||
TEST ("abcde", "e", 4);
|
||||
|
||||
TEST ("abcde", "ab", 0);
|
||||
TEST ("abcde", "bc", 1);
|
||||
TEST ("abcde", "cd", 2);
|
||||
TEST ("abcde", "de", 3);
|
||||
TEST ("abcde", "ef", -1);
|
||||
|
||||
TEST ("abcde", "abc", 0);
|
||||
TEST ("abcde", "bcd", 1);
|
||||
TEST ("abcde", "cde", 2);
|
||||
TEST ("abcde", "def", -1);
|
||||
|
||||
TEST ("abcde", "abcd", 0);
|
||||
TEST ("abcde", "bcde", 1);
|
||||
TEST ("abcde", "cdef", -1);
|
||||
|
||||
TEST ("abcde", "abcde", 0);
|
||||
TEST ("abcde", "bcdef", -1);
|
||||
|
||||
TEST ("abcabfg", "ab", 0);
|
||||
TEST ("abcbcfg", "bc", 1);
|
||||
TEST ("abcdecd", "cd", 2);
|
||||
TEST ("abcdede", "de", 3);
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::search_n()
|
||||
template <class ForwardIterator, class T, class Size, class PredTag>
|
||||
void test_search_n (int line, const char *seq, Size cnt, const char val,
|
||||
std::size_t off, ForwardIterator it,
|
||||
const T* , PredTag pred_tag)
|
||||
{
|
||||
const char* const fname = "search_n";
|
||||
static const char* const itname = type_name (it, (T*)0);
|
||||
static const char* const szname = "Size";
|
||||
static const char* const tname = "UserClass";
|
||||
static const char* const predname =
|
||||
pred_tag.pred_inx ? "BinaryPredicate" : "operator <()";
|
||||
|
||||
const std::size_t nseq = std::strlen (seq);
|
||||
|
||||
// construct a sequence of `nsrc' elements to pass to search_n
|
||||
T* const xseq = T::from_char (seq, nseq);
|
||||
|
||||
// construct iterators pointing to the beginning and end
|
||||
// of the source sequence
|
||||
const ForwardIterator first =
|
||||
make_iter (xseq, xseq, xseq + nseq, it);
|
||||
const ForwardIterator last =
|
||||
make_iter (xseq + nseq, xseq, xseq + nseq, it);
|
||||
|
||||
const ForwardIterator expected = _RWSTD_SIZE_MAX == off ?
|
||||
last
|
||||
: make_iter (xseq + off, xseq, xseq + off, it);
|
||||
|
||||
_RWSTD_UNUSED (expected);
|
||||
|
||||
T value;
|
||||
value.data_.val_ = val;
|
||||
|
||||
T::n_total_op_eq_ = 0;
|
||||
PredTag::Predicate::funcalls_ = 0;
|
||||
|
||||
typename PredTag::Predicate pred(0, 0);
|
||||
|
||||
const ForwardIterator result = pred_tag.pred_inx ?
|
||||
std::search_n (first, last, cnt, value, pred)
|
||||
: std::search_n (first, last, cnt, value);
|
||||
|
||||
_RWSTD_UNUSED (result);
|
||||
|
||||
// 25.1.9, p6:
|
||||
// check the returned iterator
|
||||
rw_assert (result.cur_ == expected.cur_, 0, line,
|
||||
"std::%s<%s, %s, %s%{?}, %s%{;}> (\"%s\", ..., %d, '%c') "
|
||||
"found subsequence at %td, expected at %{?}end%{:}%zu%{;}",
|
||||
fname, itname, szname, tname, pred_tag.pred_inx, predname,
|
||||
seq, int (cnt), val, result.cur_ - first.cur_,
|
||||
_RWSTD_SIZE_MAX == off, off);
|
||||
|
||||
// 25.1.9, p7:
|
||||
// Complexity: At most (last <20> first) * count
|
||||
// applications of the corresponding predicate or operator.
|
||||
// In real cases the complexity should be at most (last <20> first)
|
||||
const std::size_t max_op_eq = nseq * cnt;
|
||||
const std::size_t op_called = pred_tag.pred_inx ?
|
||||
PredTag::Predicate::funcalls_
|
||||
: T::n_total_op_eq_;
|
||||
|
||||
rw_assert (op_called <= max_op_eq, 0, line,
|
||||
"std::%s<%s, %s, %s%{?}, %s%{;}> (\"%s\", ..., %d, '%c') "
|
||||
"called %s %zu times, expected no more than %zu",
|
||||
fname, itname, szname, tname, pred_tag.pred_inx, predname,
|
||||
seq, int (cnt), val, predname, op_called, max_op_eq);
|
||||
|
||||
delete[] xseq;
|
||||
}
|
||||
|
||||
template <class ForwardIterator, class T, class Size, class PredTag>
|
||||
void test_search_n (ForwardIterator it, const T* ,
|
||||
const Size* , PredTag pred_tag)
|
||||
{
|
||||
static const char* const itname = type_name (it, (T*)0);
|
||||
static const char* const szname = "Size";
|
||||
static const char* const tname = "UserClass";
|
||||
static const char* const predname = "EqualityPredicate";
|
||||
|
||||
if (pred_tag.pred_inx) { // use predicate
|
||||
rw_info (0, 0, 0,
|
||||
"std::search_n (%s, %1$s, %s, const %s&, %s)",
|
||||
itname, szname, tname, predname);
|
||||
}
|
||||
else { // not use predicate
|
||||
rw_info (0, 0, 0,
|
||||
"std::search_n (%s, %1$s, %s, const %s&)",
|
||||
itname, szname, tname);
|
||||
}
|
||||
|
||||
#undef TEST
|
||||
#define TEST(seq, n, val, off) \
|
||||
test_search_n (__LINE__, seq, Size(n, 0), val, std::size_t (off), \
|
||||
it, (T*)0, pred_tag)
|
||||
|
||||
//
|
||||
// +----------------- sequence to search through
|
||||
// | +------------ number of occurrences
|
||||
// | | +-------- element value to match
|
||||
// | | | +--- match found at offset
|
||||
// v v v v
|
||||
TEST ("", 0, 'x', 0);
|
||||
TEST ("", 1, 'x', -1);
|
||||
TEST ("", 2, 'x', -1);
|
||||
TEST ("", -1, 'x', -1);
|
||||
|
||||
TEST ("A", 0, 'B', 0);
|
||||
TEST ("A", 0, 'A', 0);
|
||||
TEST ("A", 1, 'B', -1);
|
||||
TEST ("A", 1, 'A', 0);
|
||||
|
||||
TEST ("AB", 1, 'A', 0);
|
||||
TEST ("AB", 2, 'A', -1);
|
||||
TEST ("AB", 1, 'B', 1);
|
||||
TEST ("AB", 2, 'B', -1);
|
||||
|
||||
TEST ("ABC", 0, 'A', 0);
|
||||
TEST ("ABC", 0, 'B', 0);
|
||||
TEST ("ABC", 0, 'C', 0);
|
||||
TEST ("ABC", 0, 'D', 0);
|
||||
|
||||
TEST ("ABC", 1, 'A', 0);
|
||||
TEST ("ABC", 1, 'B', 1);
|
||||
TEST ("ABC", 1, 'C', 2);
|
||||
TEST ("ABC", 1, 'D', -1);
|
||||
|
||||
TEST ("ABC", 2, 'A', -1);
|
||||
TEST ("ABC", 2, 'B', -1);
|
||||
TEST ("ABC", 2, 'C', -1);
|
||||
TEST ("ABC", 2, 'D', -1);
|
||||
|
||||
TEST ("ABC", -1, 'A', -1);
|
||||
TEST ("ABC", -2, 'B', -1);
|
||||
TEST ("ABC", -3, 'C', -1);
|
||||
TEST ("ABC", -4, 'D', -1);
|
||||
|
||||
TEST ("ABAD", 1, 'A', 0);
|
||||
TEST ("ABCB", 1, 'B', 1);
|
||||
TEST ("ABCC", 1, 'C', 2);
|
||||
|
||||
TEST ("ABAACAAAD", 2, 'A', 2);
|
||||
TEST ("ABCBBDBBB", 2, 'B', 3);
|
||||
|
||||
TEST ("ABAACAADE", 3, 'A', -1);
|
||||
TEST ("ABCBBDBBE", 3, 'B', -1);
|
||||
TEST ("ABAACAAAD", 3, 'A', 5);
|
||||
TEST ("ABCBBDBBB", 3, 'B', 6);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_search; // --no-search
|
||||
/* extern */ int rw_opt_no_search_n; // --no-search_n
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
/* extern */ int rw_opt_no_predicate; // --no-Predicate
|
||||
|
||||
|
||||
template <class ForwardIterator, class T, class PredTag>
|
||||
void test_search (ForwardIterator it, const T*, PredTag pred_tag)
|
||||
{
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search (it, FwdIter<T>(), (T*)0, pred_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search (it, BidirIter<T>(), (T*)0, pred_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search (it, RandomAccessIter<T>(), (T*)0, pred_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class PredTag>
|
||||
void test_search (const T*, PredTag pred_tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %1$s%{?}, class %s%{;}> "
|
||||
"std::search (%1$s, %1$s, %1$s, %1$s%{?}, %3$s%{;})",
|
||||
"ForwardIterator", pred_tag.pred_inx, "BinaryPredicate",
|
||||
pred_tag.pred_inx);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search (FwdIter<T>(), (T*)0, pred_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search (BidirIter<T>(), (T*)0, pred_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search (RandomAccessIter<T>(), (T*)0, pred_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Size, class PredTag>
|
||||
void test_search_n(const T* , Size* , PredTag pred_tag)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s%{?}, class %s%{;}> "
|
||||
"std::search_n (%1$s, %1$s, %2$s, %s%{?}, %4$s%{;})",
|
||||
"ForwardIterator", "Size", "T",
|
||||
pred_tag.pred_inx, "BinaryPredicate", "const T&",
|
||||
pred_tag.pred_inx);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search_n (FwdIter<T>(), (T*)0, (Size*)0, pred_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search_n (BidirIter<T>(), (T*)0, (Size*)0, pred_tag);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_search_n (RandomAccessIter<T>(), (T*)0, (Size*)0, pred_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_search (const T*)
|
||||
{
|
||||
NonPredicateTag<T> non_predicate_tag = { false };
|
||||
PredicateTag<T> predicate_tag = { true };
|
||||
|
||||
test_search ((T*)0, non_predicate_tag);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::search predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_search ((T*)0, predicate_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_search_n (const T*)
|
||||
{
|
||||
NonPredicateTag<T> non_predicate_tag = { false };
|
||||
PredicateTag<T> predicate_tag = { true };
|
||||
|
||||
test_search_n ((T*)0, (Size<int>*)0, non_predicate_tag);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::search_n predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_search_n ((T*)0, (Size<int>*)0, predicate_tag);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_search) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::search test disabled");
|
||||
}
|
||||
else {
|
||||
test_search ((UserClass*)0);
|
||||
}
|
||||
|
||||
if (rw_opt_no_search_n) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::search_n test disabled");
|
||||
}
|
||||
else {
|
||||
test_search_n ((UserClass*)0);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.search",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-search# "
|
||||
"|-no-search_n# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator# "
|
||||
"|-no-Predicate",
|
||||
&rw_opt_no_search,
|
||||
&rw_opt_no_search_n,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
460
extern/stdcxx/4.2.1/tests/algorithms/25.set.difference.cpp
vendored
Normal file
460
extern/stdcxx/4.2.1/tests/algorithms/25.set.difference.cpp
vendored
Normal file
@@ -0,0 +1,460 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.set.difference.cpp - test exercising lib.set.difference
|
||||
*
|
||||
* $Id: 25.set.difference.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for set_difference
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_difference (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_difference (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &x,
|
||||
const UserClass &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t Less::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// ordinary (non-template) base to minimize code bloat
|
||||
struct SetDifferenceBase
|
||||
{
|
||||
virtual ~SetDifferenceBase() {}
|
||||
|
||||
const char* iter_names [3];
|
||||
|
||||
// pure virtual
|
||||
virtual UserClass*
|
||||
set_difference (const UserClass*, const UserClass*, const UserClass*,
|
||||
const UserClass*, UserClass*, UserClass*,
|
||||
const Less*) const = 0;
|
||||
};
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
struct SetDifference: SetDifferenceBase
|
||||
{
|
||||
SetDifference () {
|
||||
iter_names [0] = type_name (InputIterator1 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [1] = type_name (InputIterator2 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [2] = type_name (OutputIterator (0, 0, 0), (UserClass*)0);
|
||||
}
|
||||
|
||||
virtual UserClass*
|
||||
set_difference (const UserClass *xsrc1, const UserClass *xsrc1_end,
|
||||
const UserClass *xsrc2, const UserClass *xsrc2_end,
|
||||
UserClass *xdst, UserClass *xdst_end,
|
||||
const Less *ppred) const {
|
||||
|
||||
const InputIterator1 first1 (xsrc1, xsrc1, xsrc1_end);
|
||||
const InputIterator1 last1 (xsrc1_end, xsrc1, xsrc1_end);
|
||||
const InputIterator2 first2 (xsrc2, xsrc2, xsrc2_end);
|
||||
const InputIterator2 last2 (xsrc2_end, xsrc2, xsrc2_end);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst_end);
|
||||
|
||||
const OutputIterator ret = ppred ?
|
||||
std::set_difference (first1, last1, first2, last2, result, *ppred)
|
||||
: std::set_difference (first1, last1, first2, last2, result);
|
||||
|
||||
// silence EDG eccp 3.7 and prior remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (ret);
|
||||
|
||||
return ret.cur_;
|
||||
}
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises set_difference: 25.3.5.4
|
||||
void test_set_difference (int line,
|
||||
const char *src1,
|
||||
std::size_t nsrc1,
|
||||
const char *src2,
|
||||
std::size_t nsrc2,
|
||||
const char *res,
|
||||
std::size_t ndst,
|
||||
bool predicate,
|
||||
const SetDifferenceBase &alg)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const fname = "set_difference";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
UserClass* const xsrc1 = UserClass::from_char (src1, nsrc1,
|
||||
true /* must be sorted */);
|
||||
UserClass* const xsrc2 = UserClass::from_char (src2, nsrc2,
|
||||
true /* must be sorted */);
|
||||
|
||||
// assert that the sequences have been successfully created
|
||||
RW_ASSERT (0 == nsrc1 || xsrc1);
|
||||
RW_ASSERT (0 == nsrc2 || xsrc2);
|
||||
|
||||
UserClass* const xdst = new UserClass [ndst];
|
||||
|
||||
const int max1_id = nsrc1 > 0 ? xsrc1[nsrc1 - 1].id_ : -1;
|
||||
|
||||
UserClass* const xsrc1_end = xsrc1 + nsrc1;
|
||||
UserClass* const xsrc2_end = xsrc2 + nsrc2;
|
||||
UserClass* const xdst_end = xdst + ndst;
|
||||
|
||||
const std::size_t last_n_op_lt = UserClass::n_total_op_lt_;
|
||||
|
||||
const Less pred (0, 0);
|
||||
const Less* const ppred = predicate ? &pred : 0;
|
||||
|
||||
UserClass* xdst_res = alg.set_difference (xsrc1, xsrc1_end,
|
||||
xsrc2, xsrc2_end,
|
||||
xdst, xdst_end, ppred);
|
||||
|
||||
// check the returned value
|
||||
bool success = xdst_res == xdst_end;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"got res + %td, expected res + %zu",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, xdst_res - xdst, ndst);
|
||||
|
||||
// quit here to avoid the running out of the array boundaries
|
||||
if (!success) {
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
return;
|
||||
}
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Less::funcalls_ : UserClass::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// verify the algorithm correctness
|
||||
std::size_t i = 0;
|
||||
std::size_t n1 = 0;
|
||||
std::size_t n2 = 0;
|
||||
for ( ; i < ndst; ++i) {
|
||||
xdst[i].origin_ <= max1_id ? n1++ : n2++;
|
||||
success = xdst[i].data_.val_ == res[i];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\", expected \"%s\"",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, int (ndst), i, xdst, res);
|
||||
|
||||
// verfiy that only elements from first sequence sequence were taken
|
||||
success = n1 == ndst;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\" got %zu elements from first sequence and "
|
||||
"%zu from second, expected %zu from first and 0 from second",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate, funname,
|
||||
src1, src2, int (ndst), -1, xdst, n1, n2, ndst);
|
||||
|
||||
// verify that the operation is stable : two equal elements
|
||||
// should go in the same order
|
||||
for (i = 1; i < ndst; i++) {
|
||||
success = xdst[i - 1].origin_ < xdst[i].origin_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
if (ndst > 1) {
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...)"
|
||||
" ==> \"%{X=*.*}\" not stable : elements %#c==%#c have "
|
||||
"ids %d >= %d ",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, int (ndst), i, xdst,
|
||||
xdst[i - 1].data_.val_, xdst[i].data_.val_,
|
||||
xdst[i - 1].origin_, xdst[i].origin_);
|
||||
}
|
||||
|
||||
// verify the complexity
|
||||
const std::size_t n_exp_ops =
|
||||
nsrc1 + nsrc2 > 0 ? 2 * (nsrc1 + nsrc2) - 1 : 0;
|
||||
|
||||
rw_assert (n_ops_lt <= n_exp_ops, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"complexity: got %zu, expected no more than %zu",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate, funname,
|
||||
src1, src2, n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_set_difference (const SetDifferenceBase &alg,
|
||||
bool predicate)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const fname = "set_difference";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::%s(%s, %3$s, %s, %4$s, %1$s%{?}, %s%{;})",
|
||||
outname, fname, it1name, it2name, predicate, funname);
|
||||
|
||||
#define TEST(src1, src2, res) \
|
||||
test_set_difference (__LINE__, src1, sizeof src1 - 1, \
|
||||
src2, sizeof src2 - 1, res, sizeof res - 1, \
|
||||
predicate, alg)
|
||||
|
||||
// +-------------------- first set
|
||||
// | +----------- second set
|
||||
// | | +-- difference
|
||||
// | | |
|
||||
// V V V
|
||||
TEST ("a", "", "a");
|
||||
TEST ("abcde", "", "abcde");
|
||||
TEST ("", "a", "");
|
||||
TEST ("", "abcde", "");
|
||||
TEST ("a", "b", "a");
|
||||
TEST ("b", "a", "b");
|
||||
TEST ("aa", "aa", "");
|
||||
TEST ("ab", "ab", "");
|
||||
TEST ("aa", "ab", "a");
|
||||
TEST ("aa", "bb", "aa");
|
||||
TEST ("ab", "bb", "a");
|
||||
TEST ("ac", "bb", "ac");
|
||||
TEST ("ace", "bdf", "ace");
|
||||
TEST ("acf", "bdf", "ac");
|
||||
TEST ("ade", "bdf", "ae");
|
||||
TEST ("bce", "bdf", "ce");
|
||||
TEST ("aacee", "aacee", "");
|
||||
TEST ("aacee", "aaace", "e");
|
||||
TEST ("aacee", "aaaae", "ce");
|
||||
TEST ("aacee", "aaaaa", "cee");
|
||||
TEST ("aacee", "aaabd", "cee");
|
||||
TEST ("aacee", "aabee", "c");
|
||||
TEST ("aaaaa", "aaaaa", "");
|
||||
TEST ("aaaaa", "aaaa", "a");
|
||||
TEST ("aaaaa", "aaa", "aa");
|
||||
TEST ("aaaaa", "aa", "aaa");
|
||||
TEST ("aaaaa", "a", "aaaa");
|
||||
TEST ("acegi", "bdfhj", "acegi");
|
||||
TEST ("bdfhj", "acegi", "bdfhj");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
void gen_set_difference_test (const InputIterator1&,
|
||||
const InputIterator2&,
|
||||
const OutputIterator&,
|
||||
bool predicate)
|
||||
{
|
||||
const SetDifference<InputIterator1, InputIterator2, OutputIterator> alg;
|
||||
|
||||
test_set_difference (alg, predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2>
|
||||
void gen_set_difference_test (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_output_iter)
|
||||
gen_set_difference_test (
|
||||
it1, it2, OutputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_difference_test (
|
||||
it1, it2, FwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_difference_test (
|
||||
it1, it2, BidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_difference_test (
|
||||
it1, it2, RandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
template <class InputIterator1>
|
||||
void gen_set_difference_test (const InputIterator1 &it1,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_input_iter)
|
||||
gen_set_difference_test (
|
||||
it1, InputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_difference_test (
|
||||
it1, ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_difference_test (
|
||||
it1, ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_difference_test (
|
||||
it1, ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
// generates a specialization of the set_union test for each of the required
|
||||
// iterator categopries
|
||||
void gen_set_difference_test (bool predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s%{?}, class %s%{;}> %3$s "
|
||||
"set_difference (%1$s, %1$s, %2$s, %2$s, %3$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2", "OutputIterator",
|
||||
predicate, "Compare", predicate, "Compare");
|
||||
|
||||
if (rw_opt_no_output_iter)
|
||||
rw_note (0, 0, 0, "OutputIterator test disabled");
|
||||
|
||||
if (rw_opt_no_input_iter)
|
||||
rw_note (0, 0, 0, "InputIterator test disabled");
|
||||
else
|
||||
gen_set_difference_test (InputIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter)
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
else
|
||||
gen_set_difference_test (ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_bidir_iter)
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
else
|
||||
gen_set_difference_test (ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_rnd_iter)
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
else
|
||||
gen_set_difference_test (
|
||||
ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_predicate)
|
||||
rw_note (0, 0, 0, "predicate test disabled");
|
||||
|
||||
const int niters = rw_opt_no_predicate ? 1 : 2;
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
for (int i = 0; i != niters; ++i) {
|
||||
gen_set_difference_test (1 == i);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.set.difference",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
440
extern/stdcxx/4.2.1/tests/algorithms/25.set.intersection.cpp
vendored
Normal file
440
extern/stdcxx/4.2.1/tests/algorithms/25.set.intersection.cpp
vendored
Normal file
@@ -0,0 +1,440 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25. set.intersection.cpp - test exercising lib.set.intersection
|
||||
*
|
||||
* $Id: 25.set.intersection.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for set_intersection
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_intersection (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_intersection (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &x,
|
||||
const UserClass &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t Less::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct SetIntersectionBase
|
||||
{
|
||||
virtual ~SetIntersectionBase() {}
|
||||
|
||||
const char* iter_names [3];
|
||||
|
||||
// pure virtual
|
||||
virtual UserClass*
|
||||
set_intersection (const UserClass*, const UserClass*, const UserClass*,
|
||||
const UserClass*, UserClass*, UserClass*,
|
||||
const Less*) const = 0;
|
||||
};
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
struct SetIntersection: SetIntersectionBase
|
||||
{
|
||||
SetIntersection () {
|
||||
iter_names [0] = type_name (InputIterator1 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [1] = type_name (InputIterator2 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [2] = type_name (OutputIterator (0, 0, 0), (UserClass*)0);
|
||||
}
|
||||
|
||||
virtual UserClass*
|
||||
set_intersection (const UserClass *xsrc1, const UserClass *xsrc1_end,
|
||||
const UserClass *xsrc2, const UserClass *xsrc2_end,
|
||||
UserClass *xdst, UserClass *xdst_end,
|
||||
const Less *ppred) const {
|
||||
|
||||
const InputIterator1 first1 (xsrc1, xsrc1, xsrc1_end);
|
||||
const InputIterator1 last1 (xsrc1_end, xsrc1, xsrc1_end);
|
||||
const InputIterator2 first2 (xsrc2, xsrc2, xsrc2_end);
|
||||
const InputIterator2 last2 (xsrc2_end, xsrc2, xsrc2_end);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst_end);
|
||||
|
||||
const OutputIterator ret = ppred ?
|
||||
std::set_intersection (first1, last1, first2,
|
||||
last2, result, *ppred)
|
||||
: std::set_intersection (first1, last1, first2,
|
||||
last2, result);
|
||||
|
||||
// silence EDG eccp 3.7 and prior remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (ret);
|
||||
|
||||
return ret.cur_;
|
||||
}
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_set_intersection (int line,
|
||||
const char *src1,
|
||||
std::size_t nsrc1,
|
||||
const char *src2,
|
||||
std::size_t nsrc2,
|
||||
const char *res,
|
||||
std::size_t ndst,
|
||||
bool predicate,
|
||||
const SetIntersectionBase &alg)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const fname = "set_intersection";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
UserClass* const xsrc1 = UserClass::from_char (src1, nsrc1,
|
||||
true /* must be sorted */);
|
||||
UserClass* const xsrc2 = UserClass::from_char (src2, nsrc2,
|
||||
true /* must be sorted */);
|
||||
|
||||
// assert that the sequences have been successfully created
|
||||
RW_ASSERT (0 == nsrc1 || xsrc1);
|
||||
RW_ASSERT (0 == nsrc2 || xsrc2);
|
||||
|
||||
UserClass* const xdst = new UserClass [ndst];
|
||||
|
||||
const int max1_id = nsrc1 > 0 ? xsrc1[nsrc1 - 1].id_ : -1;
|
||||
|
||||
UserClass* const xsrc1_end = xsrc1 + nsrc1;
|
||||
UserClass* const xsrc2_end = xsrc2 + nsrc2;
|
||||
UserClass* const xdst_end = xdst + ndst;
|
||||
|
||||
const std::size_t last_n_op_lt = UserClass::n_total_op_lt_;
|
||||
|
||||
const Less pred (0, 0);
|
||||
const Less* const ppred = predicate ? &pred : 0;
|
||||
|
||||
const UserClass* const xdst_res =
|
||||
alg.set_intersection (xsrc1, xsrc1_end, xsrc2,
|
||||
xsrc2_end, xdst, xdst_end, ppred);
|
||||
|
||||
// check the returned value
|
||||
bool success = xdst_res == xdst_end;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"got res + %td, expected res + %zu",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, xdst_res - xdst, ndst);
|
||||
|
||||
// quit here to avoid the running out of the array boundaries
|
||||
if (!success) {
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
return;
|
||||
}
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Less::funcalls_ : UserClass::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// check the algorithm correctness
|
||||
std::size_t i = 0;
|
||||
std::size_t n1 = 0;
|
||||
std::size_t n2 = 0;
|
||||
for ( ; i < ndst; i++) {
|
||||
xdst[i].origin_ <= max1_id ? n1++ : n2++;
|
||||
success = xdst[i].data_.val_ == res[i];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\", expected \"%s\"",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, int (ndst), i, xdst, res);
|
||||
|
||||
// check that the operation is stable : for two equal elements
|
||||
// one from the first sequence should be taken
|
||||
success = n2 == 0;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\" got %zu elements from first sequence and "
|
||||
"%zu from second, expected %zu from first and 0 from second",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate, funname,
|
||||
src1, src2, int (ndst), -1, xdst, n1, n2, ndst);
|
||||
|
||||
// check the complexity
|
||||
const std::size_t n_exp_ops =
|
||||
nsrc1 + nsrc2 > 0 ? 2 * (nsrc1 + nsrc2) - 1 : 0;
|
||||
|
||||
rw_assert (n_ops_lt <= n_exp_ops, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"complexity: got %zu, expected no more than %zu",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate, funname,
|
||||
src1, src2, n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_set_intersection (const SetIntersectionBase &alg,
|
||||
bool predicate)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const fname = "set_intersection";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::%s(%s, %3$s, %s, %4$s, %1$s%{?}, %s%{;})",
|
||||
outname, fname, it1name, it2name, predicate, funname);
|
||||
|
||||
#define TEST(src1, src2, res) \
|
||||
test_set_intersection (__LINE__, src1, sizeof src1 - 1, \
|
||||
src2, sizeof src2 - 1, \
|
||||
res, sizeof res - 1, \
|
||||
predicate, alg)
|
||||
|
||||
TEST ("a", "", "");
|
||||
TEST ("abcde", "", "");
|
||||
|
||||
TEST ("", "a", "");
|
||||
TEST ("", "abcde", "");
|
||||
|
||||
TEST ("a", "b", "");
|
||||
TEST ("b", "a", "");
|
||||
|
||||
TEST ("aa", "aa", "aa");
|
||||
TEST ("ab", "ab", "ab");
|
||||
|
||||
TEST ("aa", "ab", "a");
|
||||
TEST ("ab", "bb", "b");
|
||||
TEST ("aa", "bb", "");
|
||||
TEST ("ac", "bb", "");
|
||||
|
||||
TEST ("ace", "bdf", "");
|
||||
TEST ("acf", "bdf", "f");
|
||||
TEST ("ade", "bdf", "d");
|
||||
TEST ("bce", "bdf", "b");
|
||||
|
||||
TEST ("aacee", "aacee", "aacee");
|
||||
TEST ("aacee", "aaace", "aace");
|
||||
TEST ("aacee", "aaaae", "aae");
|
||||
TEST ("aacee", "aaaaa", "aa");
|
||||
TEST ("aaaae", "aacee", "aae");
|
||||
TEST ("aaaaa", "aacee", "aa");
|
||||
TEST ("aacee", "aaabd", "aa");
|
||||
TEST ("aaabd", "aacee", "aa");
|
||||
TEST ("aacee", "aabee", "aaee");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
void gen_set_intersection_test (const InputIterator1&,
|
||||
const InputIterator2&,
|
||||
const OutputIterator&,
|
||||
bool predicate)
|
||||
{
|
||||
const SetIntersection<InputIterator1, InputIterator2, OutputIterator> alg;
|
||||
|
||||
test_set_intersection (alg, predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2>
|
||||
void gen_set_intersection_test (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_output_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, it2, OutputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, it2, FwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, it2, BidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, it2, RandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
template <class InputIterator1>
|
||||
void gen_set_intersection_test (const InputIterator1 &it1,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_input_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, InputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_intersection_test (
|
||||
it1, ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
// generates a specialization of the set_intersection test for each of
|
||||
// the required iterator categopries
|
||||
static void
|
||||
gen_set_intersection_test (bool predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s%{?}, class %s%{;}> %3$s "
|
||||
"set_intersection(%1$s, %1$s, %2$s, %2$s, %3$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2", "OutputIterator",
|
||||
predicate, "Compare", predicate, "Compare");
|
||||
|
||||
if (rw_opt_no_output_iter)
|
||||
rw_note (0, 0, 0, "OutputIterator test disabled");
|
||||
|
||||
if (rw_opt_no_input_iter)
|
||||
rw_note (0, 0, 0, "InputIterator test disabled");
|
||||
else
|
||||
gen_set_intersection_test (InputIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter)
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
else
|
||||
gen_set_intersection_test (ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_bidir_iter)
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
else
|
||||
gen_set_intersection_test (ConstBidirIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
|
||||
if (rw_opt_no_rnd_iter)
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
else
|
||||
gen_set_intersection_test (
|
||||
ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_predicate)
|
||||
rw_note (0, 0, 0, "predicate test disabled");
|
||||
|
||||
const int niters = rw_opt_no_predicate ? 1 : 2;
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
for (int i = 0; i != niters; ++i) {
|
||||
gen_set_intersection_test (1 == i);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.set.intersection",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
467
extern/stdcxx/4.2.1/tests/algorithms/25.set.sym.difference.cpp
vendored
Normal file
467
extern/stdcxx/4.2.1/tests/algorithms/25.set.sym.difference.cpp
vendored
Normal file
@@ -0,0 +1,467 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.set.symmetric.difference.cpp - test for lib.set.symmetric.difference
|
||||
*
|
||||
* $Id: 25.set.sym.difference.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for set_symmetric_difference
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_symmetric_difference (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_symmetric_difference (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &x,
|
||||
const UserClass &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t Less::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct SetSymDifferenceBase
|
||||
{
|
||||
virtual ~SetSymDifferenceBase() {}
|
||||
|
||||
const char* iter_names [3];
|
||||
|
||||
// ipure virtual
|
||||
virtual UserClass*
|
||||
set_sym_difference (const UserClass*, const UserClass*, const UserClass*,
|
||||
const UserClass*, UserClass*, UserClass*,
|
||||
const Less*) const = 0;
|
||||
};
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
struct SetSymDifference: SetSymDifferenceBase
|
||||
{
|
||||
SetSymDifference () {
|
||||
iter_names [0] = type_name (InputIterator1 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [1] = type_name (InputIterator2 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [2] = type_name (OutputIterator (0, 0, 0), (UserClass*)0);
|
||||
}
|
||||
|
||||
virtual ~SetSymDifference() {}
|
||||
|
||||
virtual UserClass*
|
||||
set_sym_difference (const UserClass *xsrc1, const UserClass *xsrc1_end,
|
||||
const UserClass *xsrc2, const UserClass *xsrc2_end,
|
||||
UserClass *xdst, UserClass *xdst_end,
|
||||
const Less *ppred) const {
|
||||
|
||||
const InputIterator1 first1 (xsrc1, xsrc1, xsrc1_end);
|
||||
const InputIterator1 last1 (xsrc1_end, xsrc1, xsrc1_end);
|
||||
const InputIterator2 first2 (xsrc2, xsrc2, xsrc2_end);
|
||||
const InputIterator2 last2 (xsrc2_end, xsrc2, xsrc2_end);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst_end);
|
||||
|
||||
const OutputIterator ret = ppred ?
|
||||
std::set_symmetric_difference (first1, last1, first2, last2,
|
||||
result, *ppred)
|
||||
: std::set_symmetric_difference (first1, last1, first2, last2,
|
||||
result);
|
||||
|
||||
// silence EDG eccp 3.7 and prior remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (ret);
|
||||
|
||||
return ret.cur_;
|
||||
}
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises set_difference: 25.3.5.5
|
||||
void test_set_sym_difference (int line,
|
||||
const char *src1,
|
||||
std::size_t nsrc1,
|
||||
const char *src2,
|
||||
std::size_t nsrc2,
|
||||
const char *res,
|
||||
std::size_t ndst,
|
||||
const std::size_t nf,
|
||||
bool predicate,
|
||||
const SetSymDifferenceBase &alg)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const algname = "set_symmetric_difference";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
UserClass* const xsrc1 = UserClass::from_char (src1, nsrc1,
|
||||
true /* must be sorted */);
|
||||
UserClass* const xsrc2 = UserClass::from_char (src2, nsrc2,
|
||||
true /* must be sorted */);
|
||||
UserClass* const xdst = new UserClass [ndst];
|
||||
|
||||
// source sequences must be sorted
|
||||
RW_ASSERT (0 == nsrc1 || 0 != xsrc1);
|
||||
RW_ASSERT (0 == nsrc2 || 0 != xsrc2);
|
||||
|
||||
const int max1_id = nsrc1 > 0 ? xsrc1 [nsrc1 - 1].id_ : -1;
|
||||
|
||||
UserClass* const xsrc1_end = xsrc1 + nsrc1;
|
||||
UserClass* const xsrc2_end = xsrc2 + nsrc2;
|
||||
UserClass* const xdst_end = xdst + ndst;
|
||||
|
||||
const std::size_t last_n_op_lt = UserClass::n_total_op_lt_;
|
||||
|
||||
const Less pred (0, 0);
|
||||
const Less* const ppred = predicate ? &pred : 0;
|
||||
|
||||
UserClass* xdst_res = alg.set_sym_difference (xsrc1, xsrc1_end,
|
||||
xsrc2, xsrc2_end,
|
||||
xdst, xdst_end, ppred);
|
||||
|
||||
// check the returned value
|
||||
bool success = xdst_res == xdst_end;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"got res + %td, expected res + %zu",
|
||||
__LINE__, algname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, xdst_res - xdst, ndst);
|
||||
|
||||
//quit here to avoid the running out of the array boundaries
|
||||
if (! success) {
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
return;
|
||||
}
|
||||
|
||||
std::size_t n_ops_lt = ppred ?
|
||||
Less::funcalls_ : UserClass::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// verify the algorithm correctness
|
||||
std::size_t i = 0;
|
||||
std::size_t n1 = 0;
|
||||
std::size_t n2 = 0;
|
||||
for ( ; i < ndst; i++) {
|
||||
xdst [i].origin_ <= max1_id ? n1++ : n2++;
|
||||
success = xdst [i].data_.val_ == res [i];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\", expected \"%s\"",
|
||||
__LINE__, algname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, int (ndst), i, xdst, res);
|
||||
|
||||
// verfiy that only elements from first sequence sequence were taken
|
||||
success = n1 == nf;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\" got %zu elements from first sequence and "
|
||||
"%zu from second, expected %zu from first and %zu from second",
|
||||
__LINE__, algname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2,
|
||||
int (ndst), -1, xdst, n1, n2, nf, ndst - nf);
|
||||
|
||||
// verify that the operation is stable: two equal elements
|
||||
// should go in the same order
|
||||
for (i = 1; i < ndst; i++) {
|
||||
if (xdst [i - 1].data_.val_ == xdst [i].data_.val_) {
|
||||
success = xdst [i - 1].origin_ < xdst [i].origin_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
if (ndst > 1) {
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...)"
|
||||
" ==> \"%{X=*.*}\" not stable : elements %#c==%#c have "
|
||||
"ids %d >= %d ",
|
||||
__LINE__, algname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, int (ndst), i, xdst,
|
||||
xdst[i - 1].data_.val_, xdst[i].data_.val_,
|
||||
xdst[i - 1].origin_, xdst[i].origin_);
|
||||
}
|
||||
|
||||
// verify the complexity
|
||||
std::size_t n_exp_ops = nsrc1 + nsrc2 > 0 ? 2 * (nsrc1 + nsrc2) - 1 : 0;
|
||||
rw_assert (n_ops_lt <= n_exp_ops, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"complexity: got %zu, expected no more than %zu",
|
||||
__LINE__, algname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_set_sym_difference (const SetSymDifferenceBase &alg,
|
||||
bool predicate)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const algname = "set_symmetric_difference";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::%s(%s, %3$s, %s, %4$s, %1$s%{?}, %s%{;})",
|
||||
outname, algname, it1name, it2name, predicate, funname);
|
||||
|
||||
#define TEST(src1, src2, res, nf) \
|
||||
test_set_sym_difference (__LINE__, src1, sizeof src1 -1, \
|
||||
src2, sizeof src2 - 1, \
|
||||
res, sizeof res - 1, \
|
||||
nf, predicate, alg)
|
||||
|
||||
// +------------------------------ first set
|
||||
// | +--------------------- second set
|
||||
// | | +------------ symmetric difference between them
|
||||
// | | | +-- number of elements from the first
|
||||
// | | | | sequence copied to the result
|
||||
// V V V V
|
||||
TEST ("a", "", "a", 1);
|
||||
TEST ("abcde", "", "abcde", 5);
|
||||
TEST ("", "a", "a", 0);
|
||||
TEST ("", "abcde", "abcde", 0);
|
||||
TEST ("a", "b", "ab", 1);
|
||||
TEST ("b", "a", "ab", 1);
|
||||
TEST ("aa", "aa", "", 0);
|
||||
TEST ("ab", "ab", "", 0);
|
||||
TEST ("aa", "ab", "ab", 1);
|
||||
TEST ("aa", "bb", "aabb", 2);
|
||||
TEST ("ab", "bb", "ab", 1);
|
||||
TEST ("ac", "bb", "abbc", 2);
|
||||
TEST ("ace", "bdf", "abcdef", 3);
|
||||
TEST ("acf", "bdf", "abcd", 2);
|
||||
TEST ("ade", "bdf", "abef", 2);
|
||||
TEST ("bce", "bdf", "cdef", 2);
|
||||
TEST ("aacee", "aacee", "", 0);
|
||||
TEST ("aacee", "aaace", "ae", 1);
|
||||
TEST ("aacee", "aaaae", "aace", 2);
|
||||
TEST ("aacee", "aaaaa", "aaacee", 3);
|
||||
TEST ("aacee", "aaabd", "abcdee", 3);
|
||||
TEST ("aacee", "aabee", "bc", 1);
|
||||
TEST ("aaaaa", "aaaaa", "", 0);
|
||||
TEST ("aaaaa", "aaaa", "a", 1);
|
||||
TEST ("aaaaa", "aaa", "aa", 2);
|
||||
TEST ("aaaaa", "aa", "aaa", 3);
|
||||
TEST ("aaaaa", "a", "aaaa", 4);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
void gen_set_sym_difference_test (const InputIterator1&,
|
||||
const InputIterator2&,
|
||||
const OutputIterator&,
|
||||
bool predicate)
|
||||
{
|
||||
const SetSymDifference<
|
||||
InputIterator1, InputIterator2, OutputIterator> alg;
|
||||
|
||||
test_set_sym_difference (alg, predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2>
|
||||
void gen_set_sym_difference_test (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_output_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, it2, OutputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, it2, FwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, it2, BidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, it2, RandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
template <class InputIterator1>
|
||||
void gen_set_sym_difference_test (const InputIterator1 &it1,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_input_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, InputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_sym_difference_test (
|
||||
it1, ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
// generates a specialization of the set_union test for each of the required
|
||||
// iterator categopries
|
||||
void gen_set_sym_difference_test (bool predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s%{?}, class %s%{;}> %3$s "
|
||||
"set_symmetric_difference (%1$s, %1$s, %2$s, %2$s, "
|
||||
"%3$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2", "OutputIterator",
|
||||
predicate, "Compare", predicate, "Compare");
|
||||
|
||||
if (rw_opt_no_output_iter)
|
||||
rw_note (0, 0, 0, "OutputIterator test disabled");
|
||||
|
||||
if (rw_opt_no_input_iter)
|
||||
rw_note (0, 0, 0, "InputIterator test disabled");
|
||||
else
|
||||
gen_set_sym_difference_test (InputIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter)
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
else
|
||||
gen_set_sym_difference_test (ConstFwdIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
|
||||
if (rw_opt_no_bidir_iter)
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
else
|
||||
gen_set_sym_difference_test (ConstBidirIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
|
||||
if (rw_opt_no_rnd_iter)
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
else
|
||||
gen_set_sym_difference_test (
|
||||
ConstRandomAccessIter<UserClass>(0, 0, 0), predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_predicate)
|
||||
rw_note (0, 0, 0, "predicate test disabled");
|
||||
|
||||
const int niters = rw_opt_no_predicate ? 1 : 2;
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
for (int i = 0; i != niters; ++i) {
|
||||
gen_set_sym_difference_test (1 == i);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.set.symmetric.difference",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
432
extern/stdcxx/4.2.1/tests/algorithms/25.set.union.cpp
vendored
Normal file
432
extern/stdcxx/4.2.1/tests/algorithms/25.set.union.cpp
vendored
Normal file
@@ -0,0 +1,432 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.set.union.cpp - test exercising 25.3.5.2 [lib.set.union]
|
||||
*
|
||||
* $Id: 25.set.union.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for set_union
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_union (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >
|
||||
set_union (InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &x,
|
||||
const UserClass &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t Less::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// ordinary (non-template) base to minimize code bloat
|
||||
struct SetUnionBase
|
||||
{
|
||||
virtual ~SetUnionBase() { /* no-op */ }
|
||||
|
||||
const char* iter_names [3];
|
||||
|
||||
// pure virtual, must be overridden
|
||||
virtual UserClass*
|
||||
set_union (const UserClass*, const UserClass*, const UserClass*,
|
||||
const UserClass*, UserClass*, UserClass*,
|
||||
const Less*) const = 0;
|
||||
};
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
struct SetUnion: SetUnionBase
|
||||
{
|
||||
SetUnion () {
|
||||
iter_names [0] = type_name (InputIterator1 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [1] = type_name (InputIterator2 (0, 0, 0), (UserClass*)0);
|
||||
iter_names [2] = type_name (OutputIterator (0, 0, 0), (UserClass*)0);
|
||||
}
|
||||
|
||||
virtual UserClass*
|
||||
set_union (const UserClass *xsrc1, const UserClass *xsrc1_end,
|
||||
const UserClass *xsrc2, const UserClass *xsrc2_end,
|
||||
UserClass *xdst, UserClass *xdst_end,
|
||||
const Less *ppred) const {
|
||||
|
||||
const InputIterator1 first1 (xsrc1, xsrc1, xsrc1_end);
|
||||
const InputIterator1 last1 (xsrc1_end, xsrc1, xsrc1_end);
|
||||
const InputIterator2 first2 (xsrc2, xsrc2, xsrc2_end);
|
||||
const InputIterator2 last2 (xsrc2_end, xsrc2, xsrc2_end);
|
||||
|
||||
const OutputIterator result (xdst, xdst, xdst_end);
|
||||
|
||||
const OutputIterator ret = ppred ?
|
||||
std::set_union (first1, last1, first2, last2, result, *ppred)
|
||||
: std::set_union (first1, last1, first2, last2, result);
|
||||
|
||||
// silence EDG eccp 3.7 and prior remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (ret);
|
||||
|
||||
return ret.cur_;
|
||||
}
|
||||
};
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_set_union (int line,
|
||||
const char *src1,
|
||||
std::size_t nsrc1,
|
||||
const char *src2,
|
||||
std::size_t nsrc2,
|
||||
const char *res,
|
||||
std::size_t ndst,
|
||||
bool predicate,
|
||||
const SetUnionBase &alg)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const fname = "set_union";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
UserClass* const xsrc1 = UserClass::from_char (src1, nsrc1,
|
||||
true /* must be sorted */);
|
||||
UserClass* const xsrc2 = UserClass::from_char (src2, nsrc2,
|
||||
true /* must be sorted */);
|
||||
// assert that the sequences have been successfully created
|
||||
RW_ASSERT (0 == nsrc1 || xsrc1);
|
||||
RW_ASSERT (0 == nsrc2 || xsrc2);
|
||||
|
||||
UserClass* const xdst = new UserClass [ndst];
|
||||
|
||||
const int max1_id = nsrc1 > 0 ? xsrc1 [nsrc1 - 1].id_ : -1;
|
||||
|
||||
UserClass* const xsrc1_end = xsrc1 + nsrc1;
|
||||
UserClass* const xsrc2_end = xsrc2 + nsrc2;
|
||||
UserClass* const xdst_end = xdst + ndst;
|
||||
|
||||
const std::size_t last_n_op_lt = UserClass::n_total_op_lt_;
|
||||
|
||||
const Less pred (0, 0);
|
||||
const Less* const ppred = predicate ? &pred : 0;
|
||||
|
||||
const UserClass* const xdst_res =
|
||||
alg.set_union (xsrc1, xsrc1_end, xsrc2, xsrc2_end,
|
||||
xdst, xdst_end, ppred);
|
||||
|
||||
// check the returned value
|
||||
bool success = xdst_res == xdst_end;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"got res + %td, expected res + %zu",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, xdst_res - xdst, ndst);
|
||||
|
||||
//quit here to avoid the running out of the array boundaries
|
||||
if (! success) {
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
return;
|
||||
}
|
||||
|
||||
const std::size_t n_ops_lt = ppred ?
|
||||
Less::funcalls_ : UserClass::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
// check the algorithm correctness
|
||||
std::size_t i = 0;
|
||||
std::size_t n1 = 0;
|
||||
std::size_t n2 = 0;
|
||||
for ( ; i < ndst; i++) {
|
||||
xdst[i].origin_ <= max1_id ? n1++ : n2++;
|
||||
success = xdst[i].data_.val_ == res[i];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
i = i < ndst ? i : ndst - 1;
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\", expected \"%s\"",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate,
|
||||
funname, src1, src2, int (ndst), i, xdst, res);
|
||||
|
||||
// check that the operation is stable : for two equal elements
|
||||
// one from the first sequence should be taken
|
||||
success = n1 == nsrc1;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
" ==> \"%{X=*.*}\" got %zu elements from first sequence and "
|
||||
"%zu from second, expected %zu from first and %zu from second",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate, funname,
|
||||
src1, src2, int (ndst), -1, xdst, n1, n2, nsrc1, ndst - nsrc1);
|
||||
|
||||
// check the complexity
|
||||
const std::size_t n_exp_ops =
|
||||
nsrc1 + nsrc2 > 0 ? 2 * (nsrc1 + nsrc2) - 1 : 0;
|
||||
|
||||
rw_assert (n_ops_lt <= n_exp_ops, 0, line,
|
||||
"line %d: %s<%s, %s, %s%{?}, %s%{;}> (\"%s\", \"%s\", ...) "
|
||||
"complexity: got %zu, expected no more than %zu",
|
||||
__LINE__, fname, it1name, it2name, outname, predicate, funname,
|
||||
src1, src2, n_ops_lt, n_exp_ops);
|
||||
|
||||
delete[] xsrc1;
|
||||
delete[] xsrc2;
|
||||
delete[] xdst;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
void test_set_union (const SetUnionBase &alg,
|
||||
bool predicate)
|
||||
{
|
||||
const char* const it1name = alg.iter_names [0];
|
||||
const char* const it2name = alg.iter_names [1];
|
||||
const char* const outname = alg.iter_names [2];
|
||||
const char* const fname = "set_union";
|
||||
const char* const funname = predicate ? "Less" : 0;
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"%s std::%s(%s, %3$s, %s, %4$s, %1$s%{?}, %s%{;})",
|
||||
outname, fname, it1name, it2name, predicate, funname);
|
||||
|
||||
#define TEST(src1, src2, res) \
|
||||
test_set_union (__LINE__, src1, sizeof src1 - 1, \
|
||||
src2, sizeof src2 - 1, \
|
||||
res, sizeof res - 1, \
|
||||
predicate, alg)
|
||||
|
||||
TEST ("a", "", "a");
|
||||
TEST ("abcde", "", "abcde");
|
||||
|
||||
TEST ("", "a", "a");
|
||||
TEST ("", "abcde", "abcde");
|
||||
|
||||
TEST ("a", "b", "ab");
|
||||
TEST ("b", "a", "ab");
|
||||
|
||||
TEST ("aa", "aa", "aa");
|
||||
TEST ("ab", "ab", "ab");
|
||||
|
||||
TEST ("aa", "ab", "aab");
|
||||
TEST ("aa", "bb", "aabb");
|
||||
TEST ("ab", "bb", "abb");
|
||||
TEST ("ac", "bb", "abbc");
|
||||
|
||||
TEST ("ace", "bdf", "abcdef");
|
||||
TEST ("acf", "bdf", "abcdf");
|
||||
TEST ("ade", "bdf", "abdef");
|
||||
TEST ("bce", "bdf", "bcdef");
|
||||
|
||||
TEST ("abcde", "fghij", "abcdefghij");
|
||||
TEST ("aacde", "ffhij", "aacdeffhij");
|
||||
TEST ("abbde", "fggij", "abbdefggij");
|
||||
TEST ("abcce", "fghhj", "abccefghhj");
|
||||
TEST ("abcdd", "fghii", "abcddfghii");
|
||||
|
||||
TEST ("aacee", "aacee", "aacee");
|
||||
TEST ("aacee", "aaace", "aaacee");
|
||||
TEST ("aacee", "aaaae", "aaaacee");
|
||||
TEST ("aacee", "aaaaa", "aaaaacee");
|
||||
TEST ("aacee", "aaaab", "aaaabcee");
|
||||
TEST ("aacee", "aaabd", "aaabcdee");
|
||||
TEST ("aacee", "aabee", "aabcee");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
void gen_set_union_test (const InputIterator1&,
|
||||
const InputIterator2&,
|
||||
const OutputIterator&,
|
||||
bool predicate)
|
||||
{
|
||||
const SetUnion<InputIterator1, InputIterator2, OutputIterator> alg;
|
||||
|
||||
test_set_union (alg, predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator1, class InputIterator2>
|
||||
void gen_set_union_test (const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_output_iter)
|
||||
gen_set_union_test (it1, it2, OutputIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_union_test (it1, it2, FwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_union_test (it1, it2, BidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_union_test (it1, it2, RandomAccessIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
}
|
||||
|
||||
template <class InputIterator1>
|
||||
void gen_set_union_test (const InputIterator1 &it1,
|
||||
bool predicate)
|
||||
{
|
||||
if (0 == rw_opt_no_input_iter)
|
||||
gen_set_union_test (it1, InputIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_fwd_iter)
|
||||
gen_set_union_test (it1, ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_bidir_iter)
|
||||
gen_set_union_test (it1, ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
if (0 == rw_opt_no_rnd_iter)
|
||||
gen_set_union_test (it1, ConstRandomAccessIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
}
|
||||
|
||||
// generates a specialization of the set_union test for each of the required
|
||||
// iterator categories
|
||||
void gen_set_union_test (bool predicate)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s, class %s%{?}, class %s%{;}> "
|
||||
"%3$s set_union(%1$s, %1$s, %2$s, %2$s, %3$s%{?}, %s%{;})",
|
||||
"InputIterator1", "InputIterator2", "OutputIterator",
|
||||
predicate, "Compare", predicate, "Compare");
|
||||
|
||||
if (rw_opt_no_output_iter)
|
||||
rw_note (0, 0, 0, "OutputIterator test disabled");
|
||||
|
||||
if (rw_opt_no_input_iter)
|
||||
rw_note (0, 0, 0, "InputIterator test disabled");
|
||||
else
|
||||
gen_set_union_test (InputIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter)
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
else
|
||||
gen_set_union_test (ConstFwdIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_bidir_iter)
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
else
|
||||
gen_set_union_test (ConstBidirIter<UserClass>(0, 0, 0), predicate);
|
||||
|
||||
if (rw_opt_no_rnd_iter)
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
else
|
||||
gen_set_union_test (ConstRandomAccessIter<UserClass>(0, 0, 0),
|
||||
predicate);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_predicate)
|
||||
rw_note (0, 0, 0, "predicate test disabled");
|
||||
|
||||
const int niters = rw_opt_no_predicate ? 1 : 2;
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
for (int i = 0; i != niters; ++i) {
|
||||
gen_set_union_test (1 == i);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.set.union",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-predicate#"
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
418
extern/stdcxx/4.2.1/tests/algorithms/25.sort.cpp
vendored
Normal file
418
extern/stdcxx/4.2.1/tests/algorithms/25.sort.cpp
vendored
Normal file
@@ -0,0 +1,418 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.sort.cpp - test exercising lib.sort and lib.stable.sort
|
||||
*
|
||||
* $Id: 25.sort.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for sort, stable_sort
|
||||
#include <cstring> // for strlen, size_t
|
||||
#include <cstddef> // for ptrdiff_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
sort (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
sort (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
stable_sort (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
void
|
||||
stable_sort (RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
RandomAccessIter<lt_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<lt_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct Less
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
// dummy arguments provided to prevent the class from being
|
||||
// default constructible and implicit conversion from int
|
||||
Less (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const T &x, const T &y) /* non-const */ {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (x.data_.val_ < y.data_.val_);
|
||||
}
|
||||
|
||||
static const char* name () { return "Less"; }
|
||||
|
||||
private:
|
||||
void operator= (Less&); // not assignable
|
||||
};
|
||||
|
||||
template<class T> std::size_t Less<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_sort (int line,
|
||||
const char *src,
|
||||
const std::size_t N,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool stable,
|
||||
bool alloc)
|
||||
{
|
||||
typedef RandomAccessIter<T> RandIter;
|
||||
const RandIter it(0, 0, 0);
|
||||
|
||||
const char* const itname = "RandomAccessIterator";
|
||||
const char* const fname = stable ? "stable_sort" : "sort";
|
||||
const char* const funname = ppred ? Predicate::name() : "operator<()";
|
||||
|
||||
// generate random values for each default constructed T
|
||||
T::gen_ = gen_rnd;
|
||||
|
||||
const std::size_t nsrc = src ? std::strlen (src) : N;
|
||||
|
||||
T* const xsrc = src ? T::from_char (src, nsrc) : new T[nsrc];
|
||||
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
|
||||
RandIter first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
RandIter last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
const Predicate pred(0, 0);
|
||||
|
||||
std::size_t last_n_op_lt = T::n_total_op_lt_;
|
||||
std::size_t last_n_op_cpy = T::n_total_op_assign_ + T::n_total_copy_ctor_;
|
||||
|
||||
_RWSTD_UNUSED (last_n_op_cpy);
|
||||
|
||||
if (stable) {
|
||||
std::pair<UserClass*, std::ptrdiff_t> dummy;
|
||||
if (alloc) {
|
||||
dummy = std::_GET_TEMP_BUFFER (T, nsrc + 1);
|
||||
rw_assert (0 != dummy.first, 0, 0,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (): "
|
||||
"memory allocation failed for %zu elements",
|
||||
__LINE__, fname, itname, ppred, funname, nsrc);
|
||||
}
|
||||
|
||||
if (ppred)
|
||||
std::stable_sort (first, last, pred);
|
||||
else
|
||||
std::stable_sort (first, last);
|
||||
|
||||
if (alloc && dummy.first)
|
||||
std::return_temporary_buffer (dummy.first);
|
||||
}
|
||||
else {
|
||||
if (ppred)
|
||||
std::sort (first, last, pred);
|
||||
else
|
||||
std::sort (first, last);
|
||||
}
|
||||
|
||||
// some tracing goes here
|
||||
/*
|
||||
if (! stable) {
|
||||
// number of comparison operations
|
||||
std::size_t ops = std::size_t (T::n_total_op_lt_ - last_n_op_lt);
|
||||
// number of copy ctor and assignmen operator calls
|
||||
std::size_t cpy =
|
||||
std::size_t (T::n_total_op_assign_ + T::n_total_copy_ctor_)
|
||||
- std::size_t (last_n_op_cpy);
|
||||
|
||||
// expected complexity (number opf comparisons)
|
||||
std::size_t cmplx = (nsrc + 1) * ilog2 (nsrc + 2);
|
||||
double x = double (ops) / cmplx;
|
||||
|
||||
// max and min T
|
||||
static double x_max = 0.0;
|
||||
static double x_min = 1.0;
|
||||
|
||||
if (x > x_max)
|
||||
x_max = x;
|
||||
|
||||
if (nsrc > 16 && x < x_min)
|
||||
x_min = x;
|
||||
|
||||
// complexity: UserClass * N * log (N),
|
||||
// ideally with UserClass approaching 1
|
||||
|
||||
if (!(nsrc % 20)) {
|
||||
rw_info (0, 0, 0,
|
||||
"\n+------+------+------+------+------+------+------+\n"
|
||||
"| N | COMP | COPY |N lg N| X | max X| min X|\n"
|
||||
"+======+======+======+======+======+======+======+\n");
|
||||
|
||||
// # | comp | assign | exp. complexity | X | max X | min X
|
||||
rw_info (0, 0, 0, "\n|%6d|%6d|%6d|%6d|%6.2f|%6.2f|%6.2f|\n",
|
||||
nsrc + 1, ops, cpy, cmplx, x, x_max, x_min);
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
// check that the array is sorted
|
||||
bool success = is_sorted_lt (xsrc, xsrc_end);
|
||||
if (src) {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\" not sorted",
|
||||
__LINE__, fname, itname, ppred, funname, src,
|
||||
int (nsrc), -1, xsrc);
|
||||
}
|
||||
else {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (%zu, ...): "
|
||||
"not sorted",
|
||||
__LINE__, fname, itname, ppred, funname, nsrc);
|
||||
}
|
||||
|
||||
// verify 25.3.1.1, p2 and 25.3.1.2, p3
|
||||
// the complexity of our implementation is no worse than
|
||||
// 3.33 * N * log (N) (hence the magic 7 and 2)
|
||||
const std::size_t n_ops =
|
||||
ppred ? Predicate::funcalls_ : T::n_total_op_lt_ - last_n_op_lt;
|
||||
|
||||
const std::size_t exp_ops = 7 * nsrc * ::ilog2 (nsrc);
|
||||
success = 2 * n_ops <= exp_ops;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (): complexity for "
|
||||
"length %zu is %zu, expected no more than %zu",
|
||||
__LINE__, fname, itname, ppred, funname, nsrc,
|
||||
n_ops, exp_ops / 2);
|
||||
|
||||
// verify 25.3.1.2 p2
|
||||
if (stable) {
|
||||
std::size_t j = 1;
|
||||
for ( ; j < N; j++) {
|
||||
if (xsrc[j - 1].data_.val_ == xsrc[j].data_.val_)
|
||||
success = xsrc[j - 1].origin_ < xsrc[j].origin_;
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
// to avoid errors in --trace mode
|
||||
j = j < nsrc ? j : nsrc - 1;
|
||||
|
||||
if (src) {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (\"%s\", ...) ==> "
|
||||
"\"%{X=*.*}\" relative order is broken at %zu: "
|
||||
"got ids %zu and %zu for values %#c and %#c",
|
||||
__LINE__, fname, itname, ppred, funname, src,
|
||||
int (nsrc), -1, xsrc, j, xsrc[j - 1].origin_,
|
||||
xsrc[j].origin_, xsrc[j - 1].data_.val_,
|
||||
xsrc[j].data_.val_);
|
||||
}
|
||||
else {
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: %s<%s%{?}, %s%{;}> (): relative order "
|
||||
"is broken for %zu at %zu: got ids %zu and %zu "
|
||||
"for values %d and %d",
|
||||
__LINE__, fname, itname, ppred, funname,
|
||||
nsrc, j, xsrc[j - 1].origin_, xsrc[j].origin_,
|
||||
xsrc[j - 1].data_.val_, xsrc[j].data_.val_);
|
||||
}
|
||||
}
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 256; // --nloops=#
|
||||
/* extern */ int rw_opt_no_sort; // --no-sort
|
||||
/* extern */ int rw_opt_no_stable_sort; // --no-stable_sort
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_complexity; // --no-complexity
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_sort (const std::size_t N,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool stable,
|
||||
bool alloc)
|
||||
{
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s%{?}, class %s%{;}> "
|
||||
"void std::%{?}stable_%{;}sort (%1$s, %1$s%{?}, %3$s%{;})"
|
||||
"%{?} with memory allocation%{;}",
|
||||
"RandomAccessIterator", ppred, "StrictWeakComp",
|
||||
stable, ppred, stable && alloc);
|
||||
|
||||
const char* const itname = "RandomAccessIterator";
|
||||
const char* const fname = stable ? "stable_sort" : "sort";
|
||||
const char* const funname = ppred ? Predicate::name() : "operator<()";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s%{?}, %s%{;})",
|
||||
fname, itname, ppred, funname);
|
||||
|
||||
#define TEST(src) \
|
||||
test_sort (__LINE__, src, 0, (T*)0, ppred, stable, alloc)
|
||||
|
||||
TEST ("a");
|
||||
|
||||
TEST ("ba");
|
||||
TEST ("cba");
|
||||
TEST ("dcba");
|
||||
TEST ("edcba");
|
||||
TEST ("fedcba");
|
||||
TEST ("gfedcba");
|
||||
TEST ("hgfedcba");
|
||||
TEST ("ihgfedcba");
|
||||
TEST ("jihgfedcba");
|
||||
|
||||
TEST ("ab");
|
||||
TEST ("abc");
|
||||
TEST ("abcd");
|
||||
TEST ("abcde");
|
||||
TEST ("abcdef");
|
||||
TEST ("abcdefg");
|
||||
TEST ("abcdefgh");
|
||||
TEST ("abcdefghi");
|
||||
TEST ("abcdefghij");
|
||||
|
||||
TEST ("aa");
|
||||
TEST ("aabb");
|
||||
TEST ("bbccaa");
|
||||
TEST ("ddbbccaa");
|
||||
TEST ("ddeebbccaa");
|
||||
|
||||
TEST ("aaaaaaaaaa");
|
||||
TEST ("ababababab");
|
||||
TEST ("bababababa");
|
||||
|
||||
#undef TEST
|
||||
|
||||
if (rw_opt_no_complexity) {
|
||||
rw_note (0, 0, 0,
|
||||
"std::%s (%s, %2$s%{?}, %s%{;}) complexity test disabled",
|
||||
fname, itname, ppred, funname);
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s%{?}, %s%{;}): complexity test",
|
||||
fname, itname, ppred, funname);
|
||||
|
||||
for (std::size_t i = 1; i < N; i++)
|
||||
test_sort (__LINE__, 0, i, (T*)0, ppred, stable, alloc);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_sort (const std::size_t N,
|
||||
const T*,
|
||||
bool stable,
|
||||
bool alloc)
|
||||
{
|
||||
test_sort (N, (T*)0, (Less<T>*)0, stable, alloc);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::%{?}stable_%{;}sort predicate test disabled",
|
||||
stable);
|
||||
}
|
||||
else {
|
||||
const Less<T> pred(0, 0);
|
||||
test_sort (N, (T*)0, &pred, stable, alloc);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
|
||||
static int run_test (int, char*[])
|
||||
{
|
||||
const std::size_t N = std::size_t (rw_opt_nloops);
|
||||
|
||||
if (rw_opt_no_sort) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::sort test disabled");
|
||||
}
|
||||
else {
|
||||
test_sort (N, (UserClass*)0, false, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_stable_sort) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::stable_sort test disabled");
|
||||
}
|
||||
else {
|
||||
test_sort (N, (UserClass*)0, true, false);
|
||||
// test with memory reallocation
|
||||
test_sort (N, (UserClass*)0, true, true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.sort",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-nloops#0 " // must be non-negative
|
||||
"|-no-sort# "
|
||||
"|-no-stable_sort# "
|
||||
"|-no-predicate",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_sort,
|
||||
&rw_opt_no_stable_sort,
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_complexity);
|
||||
}
|
||||
386
extern/stdcxx/4.2.1/tests/algorithms/25.swap.cpp
vendored
Normal file
386
extern/stdcxx/4.2.1/tests/algorithms/25.swap.cpp
vendored
Normal file
@@ -0,0 +1,386 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.swap.cpp - test exercising 25.2.2 [lib.alg.swap]
|
||||
*
|
||||
* $Id: 25.swap.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for swap, swap_ranges, iter_swap
|
||||
#include <cstring> // for size_t, strlen()
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
void
|
||||
swap (assign<base<cpy_ctor> >&, assign<base<cpy_ctor> >&);
|
||||
|
||||
template
|
||||
FwdIter<assign<base<cpy_ctor> > >
|
||||
swap_ranges (FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >);
|
||||
|
||||
template
|
||||
void
|
||||
iter_swap (FwdIter<assign<base<cpy_ctor> > >,
|
||||
FwdIter<assign<base<cpy_ctor> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator1, class ForwardIterator2>
|
||||
void test_iter_swap (int line,
|
||||
const char* seq,
|
||||
ForwardIterator1 /* dummy */,
|
||||
ForwardIterator2 /* dummy */,
|
||||
const T* /* dummy */,
|
||||
bool it_swap,
|
||||
const char* it1name,
|
||||
const char* it2name,
|
||||
const char* fname)
|
||||
{
|
||||
// generate sequential values for each default constructed T
|
||||
const std::size_t nseq = std::strlen (seq);
|
||||
|
||||
// construct a sequence of `nseq' elements to pass to swap
|
||||
T* const tseq = T::from_char (seq, nseq + 1);
|
||||
|
||||
int a_val, b_val;
|
||||
bool success = true;
|
||||
std::size_t i = 1;
|
||||
for ( ; i < nseq; ++i) {
|
||||
|
||||
const ForwardIterator1 it1 =
|
||||
make_iter (tseq, tseq, tseq + nseq, it1);
|
||||
|
||||
const ForwardIterator2 it2 =
|
||||
make_iter (tseq + i, tseq, tseq + nseq, it2);
|
||||
|
||||
a_val = (*it1).data_.val_;
|
||||
b_val = (*it2).data_.val_;
|
||||
|
||||
it_swap ? std::iter_swap (it1, it2) : std::swap(*it1, *it2);
|
||||
|
||||
// verify 25.2.2, p2, p7
|
||||
success = a_val == (*it2).data_.val_ && b_val == (*it1).data_.val_;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"%s<%s%{?}, %s%{;}>(%#c, %#c): got: { %#c, %#c } "
|
||||
"expected: { %5$#c, %4$#c } at step %zu",
|
||||
fname, it1name, it_swap, it2name, a_val, b_val,
|
||||
tseq->data_.val_, (tseq + i)->data_.val_, i);
|
||||
|
||||
delete[] tseq;
|
||||
}
|
||||
|
||||
template <class T, class ForwardIterator1, class ForwardIterator2>
|
||||
void test_iter_swap (ForwardIterator1 it1, ForwardIterator2 it2,
|
||||
const T*, bool it_swap)
|
||||
{
|
||||
const char* const it1name = it_swap ? type_name (it1, (T*)0) : "UserClass";
|
||||
const char* const it2name = it_swap ? type_name (it2, (T*)0) : "UserClass";
|
||||
const char* const fname = it_swap ? "iter_swap" : "swap";
|
||||
|
||||
rw_info (0, 0, 0, "std::%s (%s, %s)", fname, it1name, it2name);
|
||||
|
||||
#undef TEST
|
||||
#define TEST(seq) \
|
||||
test_iter_swap (__LINE__, seq, it1, it2, (T*)0, it_swap, \
|
||||
it1name, it2name, fname)
|
||||
|
||||
TEST("ab");
|
||||
TEST("abc");
|
||||
TEST("abcd");
|
||||
TEST("abcde");
|
||||
TEST("abcdef");
|
||||
TEST("abcdefg");
|
||||
TEST("abcdefgh");
|
||||
TEST("abcdefghi");
|
||||
TEST("abcdefghij");
|
||||
TEST("abcdefghijk");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator1, class ForwardIterator2>
|
||||
void test_swap_ranges (int line,
|
||||
const char* seq1,
|
||||
const char* seq2,
|
||||
ForwardIterator1 it1,
|
||||
ForwardIterator2 it2,
|
||||
const T* /* dummy */,
|
||||
const char* it1name,
|
||||
const char* it2name)
|
||||
{
|
||||
const std::size_t nseq = std::strlen (seq1);
|
||||
|
||||
// construct a sequence of `nseq' elements to pass to swap_ranges
|
||||
T* const tseq1 = T::from_char (seq1, nseq + 1);
|
||||
T* const tseq2 = T::from_char (seq2, nseq + 1);
|
||||
|
||||
const ForwardIterator1 first1 =
|
||||
make_iter (tseq1, tseq1, tseq1 + nseq, it1);
|
||||
const ForwardIterator1 last1 =
|
||||
make_iter (tseq1 + nseq, tseq1, tseq1 + nseq, it1);
|
||||
const ForwardIterator2 first2 =
|
||||
make_iter (tseq2, tseq2, tseq2 + nseq, it2);
|
||||
const ForwardIterator2 last2 =
|
||||
make_iter (tseq2 + nseq, tseq2, tseq2 + nseq, it2);
|
||||
|
||||
// silence bogus EDG eccp remark #550-D: variable was set
|
||||
// but never used
|
||||
_RWSTD_UNUSED (last2);
|
||||
|
||||
T a, b;
|
||||
|
||||
std::size_t last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
std::swap (a, b);
|
||||
|
||||
std::size_t assigns_per_swap = T::n_total_op_assign_ - last_n_op_assign;
|
||||
|
||||
last_n_op_assign = T::n_total_op_assign_;
|
||||
|
||||
// exercise 25.2.3 - std::swap_ranges()
|
||||
const ForwardIterator2 res = std::swap_ranges(first1, last1, first2);
|
||||
|
||||
// silence bogus EDG eccp remark #550-D: variable was set
|
||||
// but never used
|
||||
_RWSTD_UNUSED (res);
|
||||
|
||||
// check the returned value, 25.2.2 p5
|
||||
bool success = res.cur_ == last2.cur_;
|
||||
rw_assert (success, 0, line,
|
||||
"swap_ranges<%s, %s>(\"%s\", \"%s\") == first + %td, "
|
||||
"got first + %td",
|
||||
it1name, it2name, seq1, seq2, res.cur_ - tseq2,
|
||||
last2.cur_ - tseq2);
|
||||
|
||||
// check that the sequences were swapped, 25.2.2 p4
|
||||
std::size_t i = 0;
|
||||
for ( ; i < nseq; ++i) {
|
||||
success = (tseq1 + i)->data_.val_ == seq2[i]
|
||||
&& (tseq2 + i)->data_.val_ == seq1[i];
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, line,
|
||||
"swap_ranges<%s, %s>(\"%s\", \"%s\") mismatch at pos %zu "
|
||||
"got { %#c, %#c }, expected { %#c, %#c }",
|
||||
it1name, it2name, seq1, seq2, i, (tseq1 + i)->data_.val_,
|
||||
(tseq2 + i)->data_.val_, seq2[i], seq1[i]);
|
||||
|
||||
// check the complexity, 25.2.2 p6
|
||||
std::size_t swaps_per_swap_ranges =
|
||||
(T::n_total_op_assign_ - last_n_op_assign) / assigns_per_swap;
|
||||
rw_assert (swaps_per_swap_ranges == nseq, 0, line,
|
||||
"swap_ranges<%s, %s>(\"%s\", \"%s\") complexity: "
|
||||
"%zu, expected %zu swaps",
|
||||
it1name, it2name, seq1, seq2, swaps_per_swap_ranges, nseq);
|
||||
|
||||
delete[] tseq1;
|
||||
delete[] tseq2;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class ForwardIterator1, class ForwardIterator2>
|
||||
void test_swap_ranges (ForwardIterator1 it1,
|
||||
ForwardIterator2 it2,
|
||||
const T* /* dummy */)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, (T*)0);
|
||||
static const char* const it2name = type_name (it2, (T*)0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::swap_ranges (%s, %1$s, %s)", it1name, it2name);
|
||||
|
||||
#undef TEST
|
||||
#define TEST(seq1, seq2) \
|
||||
test_swap_ranges (__LINE__, seq1, seq2, it1, it2, (T*)0, \
|
||||
it1name, it2name)
|
||||
|
||||
TEST("", "");
|
||||
TEST("a", "z");
|
||||
TEST("ab", "zy");
|
||||
TEST("abc", "zyx");
|
||||
TEST("abcd", "zyxw");
|
||||
TEST("abcde", "zyxwv");
|
||||
TEST("abcdef", "zyxwvu");
|
||||
TEST("abcdefg", "zyxwvut");
|
||||
TEST("abcdefgh", "zyxwvuts");
|
||||
TEST("abcdefghi", "zyxwvutsr");
|
||||
TEST("abcdefghij", "zyxwvutsrq");
|
||||
TEST("abcdefghijk", "zyxwvutsrqp");
|
||||
TEST("abcdefghijkl", "zyxwvutsrqpo");
|
||||
TEST("abcdefghijklm", "zyxwvutsrqpon");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_swap; // --no-swap
|
||||
/* extern */ int rw_opt_no_swap_ranges; // --no-swap_ranges
|
||||
/* extern */ int rw_opt_no_iter_swap; // --no-iter_swap
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
template <class T, class ForwardIterator1>
|
||||
void test_swap (ForwardIterator1 it1, const T*, bool test_ranges)
|
||||
{
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (test_ranges)
|
||||
test_swap_ranges (it1, FwdIter<T>(), (T*)0);
|
||||
else
|
||||
test_iter_swap (it1, FwdIter<T>(), (T*)0, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (test_ranges)
|
||||
test_swap_ranges (it1, BidirIter<T>(), (T*)0);
|
||||
else
|
||||
test_iter_swap (it1, BidirIter<T>(), (T*)0, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (test_ranges)
|
||||
test_swap_ranges (it1, RandomAccessIter<T>(), (T*)0);
|
||||
else
|
||||
test_iter_swap (it1, RandomAccessIter<T>(), (T*)0, true);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
void test_swap (const T*, bool test_ranges)
|
||||
{
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_swap (FwdIter<T>(), (T*)0, test_ranges);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_swap (BidirIter<T>(), (T*)0, test_ranges);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_swap (RandomAccessIter<T>(), (T*)0, test_ranges);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
if (rw_opt_no_swap) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::swap test disabled");
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0, "template <class T> void swap (T&, T&)");
|
||||
|
||||
test_iter_swap (FwdIter<UserClass>(), FwdIter<UserClass>(),
|
||||
(UserClass*)0, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_swap_ranges) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::swap_ranges test disabled");
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> %2$s "
|
||||
"swap_ranges (%1$s, %1$s, %2$s)",
|
||||
"ForwardIterator1", "ForwardIterator2");
|
||||
|
||||
test_swap ((UserClass*)0, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_iter_swap) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::iter_swap test disabled");
|
||||
}
|
||||
else {
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s, class %s> void iter_swap (%1$s, %2$s)",
|
||||
"ForwardIterator1", "ForwardIterator2");
|
||||
|
||||
test_swap ((UserClass*)0, false);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.swap",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-swap# "
|
||||
"|-no-swap_ranges# "
|
||||
"|-no-iter_swap# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator",
|
||||
&rw_opt_no_swap,
|
||||
&rw_opt_no_swap_ranges,
|
||||
&rw_opt_no_iter_swap,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
504
extern/stdcxx/4.2.1/tests/algorithms/25.transform.cpp
vendored
Normal file
504
extern/stdcxx/4.2.1/tests/algorithms/25.transform.cpp
vendored
Normal file
@@ -0,0 +1,504 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.transform.cpp - test exercising 25.2.3 [lib.alg.transform]
|
||||
*
|
||||
* $Id: 25.transform.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for transform
|
||||
#include <cstddef> // for size_t
|
||||
|
||||
#include <alg_test.h>
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
// disable explicit instantiation for compilers (like MSVC)
|
||||
// that can't handle it
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
template
|
||||
OutputIter<assign<base<> > >
|
||||
transform (InputIter<assign<base<> > >,
|
||||
InputIter<assign<base<> > >,
|
||||
OutputIter<assign<base<> > >,
|
||||
func<assign<base<> > >);
|
||||
|
||||
template
|
||||
OutputIter<assign<base<> > >
|
||||
transform (InputIter<assign<base<> > >,
|
||||
InputIter<assign<base<> > >,
|
||||
InputIter<assign<base<> > >,
|
||||
OutputIter<assign<base<> > >,
|
||||
binary_func<assign<base<> > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T>
|
||||
struct incT
|
||||
{
|
||||
// not a binary function
|
||||
enum { binary = 0 };
|
||||
|
||||
// function name
|
||||
static const char* name () { return "unary_function"; }
|
||||
|
||||
// dummy arguments to prevent the class from being default
|
||||
// constructible or construtible by conversion from an int
|
||||
incT (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// non-const in order to detect unwarranted assumptions
|
||||
// in the algorithm(s)
|
||||
T operator() (const T &x) /* non-const */ {
|
||||
++funcalls_;
|
||||
T y (x);
|
||||
y.data_.val_ += 1;
|
||||
return y;
|
||||
}
|
||||
|
||||
static std::size_t funcalls_;
|
||||
};
|
||||
|
||||
|
||||
template <class T>
|
||||
struct plusT
|
||||
{
|
||||
// binary function
|
||||
enum { binary = 1 };
|
||||
|
||||
// function name
|
||||
static const char* name () { return "binary_function"; }
|
||||
|
||||
// dummy arguments to prevent the class from being default
|
||||
// constructible or construtible by conversion from an int
|
||||
plusT (int, int) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// non-const in order to detect unwarranted assumptions
|
||||
// in the algorithm(s)
|
||||
T operator() (const T &a, const T &b) /* non-const */ {
|
||||
++funcalls_;
|
||||
T x (a);
|
||||
x.data_.val_ = a.data_.val_ + b.data_.val_;
|
||||
return x;
|
||||
}
|
||||
|
||||
static std::size_t funcalls_;
|
||||
};
|
||||
|
||||
template <class T> std::size_t incT<T>::funcalls_;
|
||||
template <class T> std::size_t plusT<T>::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_nloops = 32; // --nloops=#
|
||||
/* extern */ int rw_opt_no_unary_function; // --no-unary_function
|
||||
/* extern */ int rw_opt_no_binary_function; // --no-binary_function
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class InputIterator, class Unused, class OutputIterator>
|
||||
OutputIterator
|
||||
invoke_transform (InputIterator first, InputIterator last,
|
||||
Unused /* for compatibility with the overload below */,
|
||||
OutputIterator dest, incT<UserClass> fun)
|
||||
{
|
||||
return std::transform (first, last, dest, fun);
|
||||
}
|
||||
|
||||
template <class InputIterator1, class InputIterator2, class OutputIterator>
|
||||
OutputIterator
|
||||
invoke_transform (InputIterator1 first1, InputIterator1 last1,
|
||||
InputIterator2 first2,
|
||||
OutputIterator dest, plusT<UserClass> fun)
|
||||
{
|
||||
return std::transform (first1, last1, first2, dest, fun);
|
||||
}
|
||||
|
||||
|
||||
template <class T, class InputIterator1, class InputIterator2,
|
||||
class OutputIterator, class Function>
|
||||
void test_transform (const T* ptr,
|
||||
const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
const OutputIterator &out,
|
||||
const Function*,
|
||||
int same_seq)
|
||||
{
|
||||
static const char* const it1name = type_name (it1, ptr);
|
||||
static const char* const it2name = type_name (it2, ptr);
|
||||
static const char* const outname = type_name (out, ptr);
|
||||
static const char* const algname = "transform";
|
||||
static const char* const funname = Function::name ();
|
||||
static const bool binary = Function::binary;
|
||||
|
||||
const std::size_t nloops = std::size_t (rw_opt_nloops);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s%{?}, %s%{;}, %s, %s)%{?}, %s%d == %s%{;}",
|
||||
algname, it1name, binary, it2name, outname, funname,
|
||||
same_seq, "first", same_seq, "dest");
|
||||
|
||||
// generate sequential values for each default constructed T
|
||||
T::gen_ = gen_seq;
|
||||
|
||||
// make sure buf{1,2}[0] is dereferenceable even when (nloops == 0)
|
||||
T* const buf1 = new T [nloops + 1];
|
||||
T* const buf2 = new T [nloops + 1];
|
||||
T* const buf3 = same_seq ? (same_seq == 1 ? buf1 : buf2) : new T [nloops];
|
||||
|
||||
const int start1_val =
|
||||
same_seq == 2 ? buf2 [0].data_.val_ : buf1 [0].data_.val_;
|
||||
const int start2_val =
|
||||
same_seq == 2 ? buf1 [0].data_.val_ : buf2 [0].data_.val_;
|
||||
|
||||
for (std::size_t i = 0; i < nloops; ++i) {
|
||||
|
||||
T* const buf1_end = buf1 + i;
|
||||
const T* const buf2_end = buf2 + i;
|
||||
const T* const buf3_end = buf3 + i;
|
||||
|
||||
const InputIterator1 first1 = make_iter (buf1, buf1, buf1_end, it1);
|
||||
const InputIterator1 last1 = make_iter (buf1_end, buf1, buf1_end, it1);
|
||||
const InputIterator2 first2 = make_iter (buf2, buf2, buf2_end, it2);
|
||||
const OutputIterator dest = make_iter (buf3, buf3, buf3_end, out);
|
||||
|
||||
const Function fun (0, 0); // dummy arguments
|
||||
|
||||
// invoke the overload of std::transform() appropriate
|
||||
// for this Function
|
||||
const OutputIterator result =
|
||||
invoke_transform (first1, last1, first2, dest, fun);
|
||||
|
||||
// check the returned iterator
|
||||
bool success = result.cur_ == buf3_end;
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. %s (%s, %2$s%{?}, %s%{;}, %s, %s)%{?}, "
|
||||
"%s%d == %s%{;} : return val: "
|
||||
"dest + %td, expected dest + %zu",
|
||||
i, algname, it1name, binary, it2name, outname, funname,
|
||||
same_seq, "first", same_seq, "dest",
|
||||
result.cur_ - buf3, i);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// check the transformation results
|
||||
int exp_val = 0;
|
||||
std::size_t j = 0;
|
||||
for ( ; j < i; j++) {
|
||||
if (0 == same_seq) {
|
||||
exp_val = binary ?
|
||||
start1_val + int (j) + start2_val + int (j)
|
||||
: start1_val + int (j) + 1;
|
||||
}
|
||||
else {
|
||||
exp_val = binary ?
|
||||
start1_val + int (j)
|
||||
+ (start2_val + int (j)) * int (i - j)
|
||||
: start1_val + int (i);
|
||||
}
|
||||
|
||||
success = buf3 [j].data_.val_ == exp_val;
|
||||
if (!success)
|
||||
break;
|
||||
}
|
||||
|
||||
rw_assert (success, 0, __LINE__,
|
||||
"%zu. %s (%s, %2$s%{?}, %s%{;}, %s, %s)%{?}, "
|
||||
"%s%d == %s%{;} : error: incorrect value %d, "
|
||||
"expected %d, position %zu",
|
||||
i, algname, it1name, binary, it2name, outname, funname,
|
||||
same_seq, "first", same_seq, "dest",
|
||||
buf3 [j].data_.val_, exp_val, j + 1);
|
||||
|
||||
if (!success)
|
||||
break;
|
||||
|
||||
// check compexity, 25.2.3 p4
|
||||
rw_assert (Function::funcalls_ == i, 0, __LINE__,
|
||||
"%zu. %s (%s, %2$s%{?}, %s%{;}, %s, %s)%{?}, "
|
||||
"%s%d == %s%{;} : complexity : %zu "
|
||||
"applications of %5$s, expected %zu",
|
||||
i, algname, it1name, binary, it2name, outname, funname,
|
||||
same_seq, "first", same_seq, "dest",
|
||||
Function::funcalls_, i);
|
||||
}
|
||||
|
||||
delete[] buf1;
|
||||
delete[] buf2;
|
||||
|
||||
if (0 == same_seq)
|
||||
delete[] buf3;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class InputIterator1, class InputIterator2,
|
||||
class OutputIterator, class Function>
|
||||
void gen_test (const T* ptr,
|
||||
const InputIterator1 &it1,
|
||||
const InputIterator2 &it2,
|
||||
const OutputIterator &out,
|
||||
const Function* pfun,
|
||||
int tag1,
|
||||
int tag2,
|
||||
int tag3,
|
||||
int same_seq)
|
||||
{
|
||||
const InputIter<UserClass> input_iter (0, 0, 0);
|
||||
const OutputIter<T> output_iter (0, 0, 0);
|
||||
const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
const RandomAccessIter<UserClass> rand_iter (0, 0, 0);
|
||||
|
||||
// tag1, tag2 and tag3 indicates that an iterator needs to be generated
|
||||
// at the corresponding position by a recursive call to gen_test
|
||||
// and other positions there the iterator will be used
|
||||
// for all tags:
|
||||
// 0 means that no iterator is needed here
|
||||
// (maybe it was already generated or just not needed)
|
||||
// 1 means that the iterator is needed at this position
|
||||
// (first for tag1, second for tag2, etc)
|
||||
// 2 means that the iterator is needed at this position and the
|
||||
// same type of iterator should be used at third position
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_input_iter) {
|
||||
if (1 == tag1 || 0 == tag1 && 1 == tag2)
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (1 == tag1) {
|
||||
gen_test (ptr, input_iter, it2, out,
|
||||
pfun, 0, tag2, tag3, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 1 == tag2) {
|
||||
gen_test (ptr, it1, input_iter, out,
|
||||
pfun, tag1, 0, tag3, same_seq);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
if (tag1 || !tag1 && tag2 || !tag1 && !tag2 && tag3)
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (1 == tag1) {
|
||||
gen_test (ptr, fwd_iter, it2, out,
|
||||
pfun, 0, tag2, tag3, same_seq);
|
||||
}
|
||||
else if (2 == tag1) {
|
||||
gen_test (ptr, fwd_iter, it2, fwd_iter,
|
||||
pfun, 0, tag2, 0, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 1 == tag2) {
|
||||
gen_test (ptr, it1, fwd_iter, out,
|
||||
pfun, tag1, 0, tag3, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 2 == tag2) {
|
||||
gen_test (ptr, it1, fwd_iter, fwd_iter,
|
||||
pfun, tag1, 0, 0, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 0 == tag2 && 1 == tag3) {
|
||||
gen_test (ptr, it1, it2, fwd_iter,
|
||||
pfun, tag1, tag2, 0, same_seq);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
if (tag1 || !tag1 && tag2 || !tag1 && !tag2 && tag3)
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (1 == tag1) {
|
||||
gen_test (ptr, bidir_iter, it2, out,
|
||||
pfun, 0, tag2, tag3, same_seq);
|
||||
}
|
||||
else if (2 == tag1) {
|
||||
gen_test (ptr, bidir_iter, it2, bidir_iter,
|
||||
pfun, 0, tag2, 0, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 1 == tag2) {
|
||||
gen_test (ptr, it1, bidir_iter, out,
|
||||
pfun, tag1, 0, tag3, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 2 == tag2) {
|
||||
gen_test (ptr, it1, bidir_iter, bidir_iter,
|
||||
pfun, tag1, 0, 0, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 0 == tag2 && 1 == tag3) {
|
||||
gen_test (ptr, it1, it2, bidir_iter,
|
||||
pfun, tag1, tag2, 0, same_seq);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
if (tag1 || !tag1 && tag2 || !tag1 && !tag2 && tag3)
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (1 == tag1) {
|
||||
gen_test (ptr, rand_iter, it2, out,
|
||||
pfun, 0, tag2, tag3, same_seq);
|
||||
}
|
||||
else if (2 == tag1) {
|
||||
gen_test (ptr, rand_iter, it2, rand_iter,
|
||||
pfun, 0, tag2, 0, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 1 == tag2) {
|
||||
gen_test (ptr, it1, rand_iter, out,
|
||||
pfun, tag1, 0, tag3, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 2 == tag2) {
|
||||
gen_test (ptr, it1, rand_iter, rand_iter,
|
||||
pfun, tag1, 0, 0, same_seq);
|
||||
}
|
||||
else if (0 == tag1 && 0 == tag2 && 1 == tag3) {
|
||||
gen_test (ptr, it1, it2, rand_iter,
|
||||
pfun, tag1, tag2, 0, same_seq);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////
|
||||
if (rw_opt_no_output_iter) {
|
||||
if (0 == tag1 && 0 == tag2 && 1 == tag3)
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (0 == tag1 && 0 == tag2 && 1 == tag3) {
|
||||
gen_test (ptr, it1, it2, output_iter,
|
||||
pfun, tag1, tag2, 0, same_seq);
|
||||
}
|
||||
}
|
||||
|
||||
if (0 == tag1 && 0 == tag2 && 0 == tag3) {
|
||||
test_transform (ptr, it1, it2, out, pfun, same_seq);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
const InputIter<UserClass> input_iter (0, 0, 0);
|
||||
const RandomAccessIter<UserClass> rand_iter;
|
||||
const UserClass* const ptr = 0;
|
||||
|
||||
// test transform with a unary function
|
||||
// according to 25.2.3 p5 'result may be equal to first'
|
||||
// so it is neccessary to test this case separately
|
||||
if (rw_opt_no_unary_function) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::transform unary function test disabled");
|
||||
}
|
||||
else {
|
||||
const incT<UserClass>* const pfun = 0;
|
||||
|
||||
gen_test (ptr, input_iter, rand_iter, rand_iter,
|
||||
pfun, 1, 0, 1, 0 /* result distinct from first */);
|
||||
|
||||
// test 25.2.3 p5 - result is equal to first
|
||||
// set tag1 = 2 and tag3 = 0 to test all iterators at the first
|
||||
// position and avoid generating iterators at the third pos
|
||||
gen_test (ptr, input_iter, rand_iter, rand_iter,
|
||||
pfun, 2, 0, 0, 1 /* result same as first */);
|
||||
}
|
||||
|
||||
// test transform with a binary function
|
||||
// according to 25.2.3 p5 'result may be equal to first1 or first2'
|
||||
// so it is neccessary to test these cases separately
|
||||
if (rw_opt_no_binary_function) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::transform binary function test disabled");
|
||||
}
|
||||
else {
|
||||
const plusT<UserClass>* const pfun = 0;
|
||||
|
||||
gen_test (ptr, input_iter, rand_iter, rand_iter,
|
||||
pfun, 1, 1, 1, 0 /* result distinct from first{1,2} */);
|
||||
|
||||
// test 25.2.3 p5 - result is equal to first2
|
||||
// set tag2 = 2 and tag3 = 0 to test all iterators at the second
|
||||
// position and avoid generating iterators at the third pos
|
||||
gen_test (ptr, input_iter, rand_iter, rand_iter,
|
||||
pfun, 1, 2, 0, 2 /* result same as first2 */);
|
||||
|
||||
// test 25.2.3 p5 - result is equal to first1
|
||||
// set tag1 = 2 and tag3 = 0 to test all iterators at the first
|
||||
// position and avoid generating iterators at the third pos
|
||||
// set same_seq to 1 to indicate that first1 and dest should be
|
||||
// the same iterators
|
||||
gen_test (ptr, input_iter, rand_iter, rand_iter,
|
||||
pfun, 2, 1, 0, 1 /* result same as first1 */);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.transform",
|
||||
0 /* no comment */, run_test,
|
||||
"|-nloops#0 " // must be non-negative
|
||||
"|-no-unary_function# "
|
||||
"|-no-binary_function# "
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator",
|
||||
&rw_opt_nloops,
|
||||
&rw_opt_no_unary_function,
|
||||
&rw_opt_no_binary_function,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
408
extern/stdcxx/4.2.1/tests/algorithms/25.unique.cpp
vendored
Normal file
408
extern/stdcxx/4.2.1/tests/algorithms/25.unique.cpp
vendored
Normal file
@@ -0,0 +1,408 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* unique.cpp - test exercising 25.2.8 [lib.alg.unique]
|
||||
*
|
||||
* $Id: 25.unique.cpp 510071 2007-02-21 15:58:53Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 2000-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <algorithm> // for unique, unique_copy
|
||||
#include <cstring> // for strlen
|
||||
|
||||
#include <alg_test.h> // for BinaryPredicate
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test()
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
_RWSTD_NAMESPACE (std) {
|
||||
|
||||
#ifndef _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
// also exercise LWG issue 241:
|
||||
// http://www.open-std.org/jtc1/sc22/wg21/docs/lwg-defects.html#241
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<assign<base<> > > >
|
||||
unique (FwdIter<eq_comp<assign<base<> > > >,
|
||||
FwdIter<eq_comp<assign<base<> > > >);
|
||||
|
||||
template
|
||||
FwdIter<eq_comp<assign<base<> > > >
|
||||
unique (FwdIter<eq_comp<assign<base<> > > >,
|
||||
FwdIter<eq_comp<assign<base<> > > >,
|
||||
binary_predicate<eq_comp<assign<base<> > > >);
|
||||
|
||||
template
|
||||
OutputIter<eq_comp<assign<base<cpy_ctor> > > >
|
||||
unique_copy (InputIter<eq_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<eq_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<eq_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
template
|
||||
OutputIter<eq_comp<assign<base<cpy_ctor> > > >
|
||||
unique_copy (InputIter<eq_comp<assign<base<cpy_ctor> > > >,
|
||||
InputIter<eq_comp<assign<base<cpy_ctor> > > >,
|
||||
OutputIter<eq_comp<assign<base<cpy_ctor> > > >,
|
||||
binary_predicate<eq_comp<assign<base<cpy_ctor> > > >);
|
||||
|
||||
#endif // _RWSTD_NO_EXPLICIT_INSTANTIATION
|
||||
|
||||
} // namespace std
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// exercises std::unique and std::unique_copy()
|
||||
template <class FwdIterator, class FwdCopyIterator,
|
||||
class OutIterator, class T, class Predicate>
|
||||
void test_unique (int line,
|
||||
const char *src,
|
||||
const char *dst,
|
||||
const FwdIterator &it,
|
||||
const FwdCopyIterator &itc,
|
||||
const OutIterator &out,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool use_copy)
|
||||
{
|
||||
const char* const outname = type_name (out, (T*)0);
|
||||
const char* const itname =
|
||||
use_copy ? type_name (itc, (T*)0) : type_name (it, (T*)0);
|
||||
const char* const fname =
|
||||
use_copy ? "unique_copy" : "unique";
|
||||
const char* const funname =
|
||||
ppred ? "BinaryPredicate" : "operator==()";
|
||||
|
||||
const std::size_t nsrc = std::strlen (src);
|
||||
const std::size_t ndst = std::strlen (dst);
|
||||
|
||||
T* const xsrc = T::from_char (src, nsrc);
|
||||
T* xdst = use_copy ? T::from_char (dst, ndst) : xsrc;
|
||||
|
||||
T* const xsrc_end = xsrc + nsrc;
|
||||
T* const xdst_end = xdst + ndst;
|
||||
|
||||
const FwdIterator first = make_iter (xsrc, xsrc, xsrc_end, it);
|
||||
const FwdIterator last = make_iter (xsrc_end, xsrc, xsrc_end, it);
|
||||
|
||||
const FwdCopyIterator first_c = make_iter (xsrc, xsrc, xsrc_end, itc);
|
||||
const FwdCopyIterator last_c = make_iter (xsrc_end, xsrc, xsrc_end, itc);
|
||||
|
||||
const OutIterator result = make_iter (xdst, xdst, xdst_end, out);
|
||||
|
||||
// compute the actual number of invocations of operator==() or predicate
|
||||
std::size_t n_total_ops =
|
||||
ppred ? Predicate::n_total_op_fcall_ : T::n_total_op_eq_;
|
||||
|
||||
OutIterator res_c (0, 0, 0);
|
||||
FwdIterator res (0, 0, 0);
|
||||
|
||||
if (use_copy)
|
||||
res_c = ppred ?
|
||||
std::unique_copy (first_c, last_c, result, *ppred)
|
||||
: std::unique_copy (first_c, last_c, result);
|
||||
else
|
||||
res = ppred ?
|
||||
std::unique (first, last, *ppred)
|
||||
: std::unique (first, last);
|
||||
|
||||
const T* const f_cur = use_copy ? result.cur_ : first.cur_;
|
||||
const T* const r_cur = use_copy ? res_c.cur_ : res.cur_;
|
||||
|
||||
bool success = r_cur == f_cur + ndst;
|
||||
rw_assert (success, 0, line,
|
||||
"line %d: std::%s <%s%{?}, %s%{;}%{?}, %s%{;}>(\"%s\", ...) "
|
||||
"== (res + %zu), got (res + %td)",
|
||||
__LINE__, fname, itname, use_copy, outname, 0 != ppred,
|
||||
funname, src, ndst, r_cur - f_cur);
|
||||
|
||||
// verify that the copied sequence matches the expected range
|
||||
const T* const mismatch = T::mismatch (xdst, dst, ndst);
|
||||
|
||||
rw_assert (0 == mismatch, 0, line,
|
||||
"line %d: std::%s <%s%{?}, %s%{;}%{?}, %s%{;}>(\"%s\", ...) "
|
||||
"==> \"%s\", got \"%{X=*.@}\"",
|
||||
__LINE__, fname, itname, use_copy, outname, 0 != ppred,
|
||||
funname, src, dst, int (ndst), mismatch, xdst);
|
||||
|
||||
if (ppred)
|
||||
n_total_ops = ppred->n_total_op_fcall_ - n_total_ops;
|
||||
else
|
||||
n_total_ops = T::n_total_op_eq_ - n_total_ops;
|
||||
|
||||
// compute the expected number of invocations of operator==() or predicate
|
||||
const std::size_t n_expect_ops = nsrc ? nsrc - 1 : 0;
|
||||
|
||||
// verify the number of applications of operator==() or predicate
|
||||
rw_assert (n_total_ops <= n_expect_ops, 0, line,
|
||||
"line %d: std::%s <%s%{?}, %s%{;}%{?}, %s%{;}>(\"%s\", ...) "
|
||||
"%s called %zu times, %zu expected",
|
||||
__LINE__, fname, itname, use_copy, outname, 0 != ppred,
|
||||
funname, src, funname, n_total_ops, n_expect_ops);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class FwdIterator, class FwdCopyIterator,
|
||||
class OutIterator, class T, class Predicate>
|
||||
void test_unique (const FwdIterator &it,
|
||||
const FwdCopyIterator &itc,
|
||||
const OutIterator &out,
|
||||
const T*,
|
||||
const Predicate *ppred,
|
||||
bool use_copy)
|
||||
{
|
||||
const char* const outname = type_name (out, (T*)0);
|
||||
const char* const itname = use_copy ?
|
||||
type_name (itc, (T*)0) : type_name (it, (T*)0);
|
||||
const char* const fname = use_copy ? "unique_copy" : "unique";
|
||||
const char* const funname = ppred ? "BinaryPredicate" : "operator==()";
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::%s (%s, %2$s%{?}, %s%{;}%{?}, %s%{;})",
|
||||
fname, itname, use_copy, outname, ppred, funname);
|
||||
|
||||
#define TEST(src, dst) \
|
||||
test_unique (__LINE__, src, dst, it, itc, out, (T*)0, \
|
||||
ppred, use_copy)
|
||||
|
||||
// +---------------- source sequence
|
||||
// | +- destination sequence
|
||||
// | |
|
||||
// v v
|
||||
TEST ("", "");
|
||||
TEST ("a", "a");
|
||||
TEST ("ab", "ab");
|
||||
TEST ("abc", "abc");
|
||||
TEST ("abcd", "abcd");
|
||||
TEST ("abcde", "abcde");
|
||||
TEST ("abcdef", "abcdef");
|
||||
TEST ("abcdefg", "abcdefg");
|
||||
TEST ("abcdefgh", "abcdefgh");
|
||||
TEST ("abcdefghi", "abcdefghi");
|
||||
TEST ("abcdefghij", "abcdefghij");
|
||||
TEST ("abcdefghijk", "abcdefghijk");
|
||||
|
||||
TEST ("abcabc", "abcabc");
|
||||
TEST ("abcabcabc", "abcabcabc");
|
||||
TEST ("abcdabcd", "abcdabcd");
|
||||
TEST ("abcdabcdabcd","abcdabcdabcd");
|
||||
|
||||
TEST ("aa", "a");
|
||||
TEST ("aaa", "a");
|
||||
TEST ("aab", "ab");
|
||||
TEST ("aaa", "a");
|
||||
TEST ("aaaa", "a");
|
||||
TEST ("aaabb", "ab");
|
||||
TEST ("aaabbb", "ab");
|
||||
TEST ("abba", "aba");
|
||||
TEST ("abbba", "aba");
|
||||
TEST ("aaabbba", "aba");
|
||||
TEST ("aaabbbaa", "aba");
|
||||
TEST ("aaabbbaaa", "aba");
|
||||
TEST ("aaabbbaaab", "abab");
|
||||
TEST ("aaabbbaaabb", "abab");
|
||||
TEST ("abbbbbaaabb", "abab");
|
||||
TEST ("abaaaaaaabb", "abab");
|
||||
TEST ("ababbbbbbbb", "abab");
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
/* extern */ int rw_opt_no_unique; // --no-unique
|
||||
/* extern */ int rw_opt_no_unique_copy; // --no-unique_copy
|
||||
/* extern */ int rw_opt_no_predicate; // --no-predicate
|
||||
/* extern */ int rw_opt_no_input_iter; // --no-InputIterator
|
||||
/* extern */ int rw_opt_no_output_iter; // --no-OutputIterator
|
||||
/* extern */ int rw_opt_no_fwd_iter; // --no-ForwardIterator
|
||||
/* extern */ int rw_opt_no_bidir_iter; // --no-BidirectionalIterator
|
||||
/* extern */ int rw_opt_no_rnd_iter; // --no-RandomAccessIterator
|
||||
|
||||
|
||||
template <class T, class Predicate, class FwdIterator>
|
||||
void test_unique (const FwdIterator &it,
|
||||
const T*,
|
||||
const Predicate *ppred)
|
||||
{
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const OutputIter<T> output_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique (fwd_iter, it, fwd_iter, (T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique (bidir_iter, it, bidir_iter, (T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique (rand_iter, it, rand_iter, (T*)0, ppred, true);
|
||||
}
|
||||
|
||||
if (rw_opt_no_output_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "OutputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique (fwd_iter, it, output_iter, (T*)0, ppred, true);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class T, class Predicate>
|
||||
void test_unique (const T*,
|
||||
const Predicate *ppred,
|
||||
bool use_copy)
|
||||
{
|
||||
static const InputIter<T> input_iter (0, 0, 0);
|
||||
static const FwdIter<T> fwd_iter (0, 0, 0);
|
||||
static const BidirIter<T> bidir_iter (0, 0, 0);
|
||||
static const RandomAccessIter<T> rand_iter (0, 0, 0);
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"template <class %s%{?}, class %s%{;}%{?}, class %s%{;}> "
|
||||
"%s std::%s (%1$s, %1$s%{?}, %3$s%{;}%{?}, %5$s%{;})",
|
||||
use_copy ? "InputIterator" : "ForwardIterator",
|
||||
use_copy, "OutputIterator", 0 != ppred, "Predicate",
|
||||
use_copy ? "OutputIterator" : "ForwardIterator",
|
||||
use_copy ? "unique_copy" : "unique", use_copy, 0 != ppred);
|
||||
|
||||
if (use_copy)
|
||||
{
|
||||
if (rw_opt_no_input_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "InputIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique (input_iter, (T*)0, ppred);
|
||||
}
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (use_copy)
|
||||
test_unique (fwd_iter, (T*)0, ppred);
|
||||
else
|
||||
test_unique (fwd_iter, fwd_iter, fwd_iter, (T*)0, ppred, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (use_copy)
|
||||
test_unique (bidir_iter, (T*)0, ppred);
|
||||
else
|
||||
test_unique (bidir_iter, bidir_iter, bidir_iter,
|
||||
(T*)0, ppred, false);
|
||||
}
|
||||
|
||||
if (rw_opt_no_rnd_iter) {
|
||||
rw_note (0, __FILE__, __LINE__, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
if (use_copy)
|
||||
test_unique (rand_iter, (T*)0, ppred);
|
||||
else
|
||||
test_unique (rand_iter, rand_iter, rand_iter,
|
||||
(T*)0, ppred, false);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
const BinaryPredicate pred (BinaryPredicate::op_equals);
|
||||
|
||||
if (rw_opt_no_unique) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::unique test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique ((UserClass*)0, (BinaryPredicate*)0, false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::unique predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique ((UserClass*)0, &pred, false);
|
||||
}
|
||||
}
|
||||
|
||||
if (rw_opt_no_unique_copy) {
|
||||
rw_note (0, __FILE__, __LINE__, "std::unique_copy test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique ((UserClass*) 0, (BinaryPredicate*)0, true);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"std::unique_copy predicate test disabled");
|
||||
}
|
||||
else {
|
||||
test_unique ((UserClass*)0, &pred, true);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.alg.unique",
|
||||
0 /* no comment */, run_test,
|
||||
"|-no-unique# "
|
||||
"|-no-unique_copy# "
|
||||
"|-no-InputIterator# "
|
||||
"|-no-OutputIterator# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator# "
|
||||
"|-no-predicate",
|
||||
&rw_opt_no_unique,
|
||||
&rw_opt_no_unique_copy,
|
||||
&rw_opt_no_input_iter,
|
||||
&rw_opt_no_output_iter,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter,
|
||||
&rw_opt_no_predicate);
|
||||
}
|
||||
297
extern/stdcxx/4.2.1/tests/algorithms/25.upper.bound.cpp
vendored
Normal file
297
extern/stdcxx/4.2.1/tests/algorithms/25.upper.bound.cpp
vendored
Normal file
@@ -0,0 +1,297 @@
|
||||
/***************************************************************************
|
||||
*
|
||||
* 25.upper.bound.cpp - test exercising 25.3.3.2 [lib.upper.bound]
|
||||
*
|
||||
* $Id: 25.upper.bound.cpp 510970 2007-02-23 14:57:45Z faridz $
|
||||
*
|
||||
***************************************************************************
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed
|
||||
* with this work for additional information regarding copyright
|
||||
* ownership. The ASF licenses this file to you under the Apache
|
||||
* License, Version 2.0 (the "License"); you may not use this file
|
||||
* except in compliance with the License. You may obtain a copy of
|
||||
* the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
* implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*
|
||||
* Copyright 1994-2006 Rogue Wave Software.
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
#include <rw/_config.h>
|
||||
|
||||
#if defined (__IBMCPP__) && !defined (_RWSTD_NO_IMPLICIT_INCLUSION)
|
||||
// disable implicit inclusion to work around a limitation
|
||||
// of IBM VisualAge 5.0 (see PR #26959)
|
||||
# define _RWSTD_NO_IMPLICIT_INCLUSION
|
||||
#endif
|
||||
|
||||
#include <algorithm> // for upper_bound()
|
||||
#include <cstring> // for strlen()
|
||||
|
||||
#include <alg_test.h> // for iterators
|
||||
#include <rw_value.h> // for UserClass
|
||||
#include <driver.h> // for rw_test(), ...
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
// distinct and not Less-Than-Comparable with class UserClass (except as
|
||||
// defined below) to detect unwarranted assumptions made by the
|
||||
// implementation of the algorithms
|
||||
struct Y
|
||||
{
|
||||
UserClass xval_;
|
||||
|
||||
// not Default-Constructible
|
||||
Y (int /* dummy */, int /*dummy */): xval_ () { }
|
||||
|
||||
// CopyConstructible
|
||||
Y (const Y &rhs): xval_ (rhs.xval_) { }
|
||||
|
||||
private:
|
||||
|
||||
void operator=(Y&); // not Assignable
|
||||
};
|
||||
|
||||
|
||||
inline conv_to_bool
|
||||
operator< (const UserClass &lhs, const Y &rhs)
|
||||
{
|
||||
return conv_to_bool::make (lhs < rhs.xval_);
|
||||
}
|
||||
|
||||
inline conv_to_bool
|
||||
operator< (const Y &lhs, const UserClass &rhs)
|
||||
{
|
||||
return conv_to_bool::make (lhs.xval_ < rhs);
|
||||
}
|
||||
|
||||
// predicate used as the Compare argument to upper_bound()
|
||||
struct LessThan
|
||||
{
|
||||
static std::size_t funcalls_;
|
||||
|
||||
LessThan (int /* dummy */, int /* dummy */) {
|
||||
funcalls_ = 0;
|
||||
}
|
||||
|
||||
// return a type other than bool but one that is implicitly
|
||||
// convertible to bool to detect incorrect assumptions
|
||||
conv_to_bool operator() (const UserClass &lhs, const Y &rhs) {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (lhs < rhs.xval_);
|
||||
}
|
||||
|
||||
conv_to_bool operator() (const Y &lhs, const UserClass &rhs) {
|
||||
++funcalls_;
|
||||
return conv_to_bool::make (lhs.xval_ < rhs);
|
||||
}
|
||||
|
||||
private:
|
||||
void operator= (LessThan&); // not assignable
|
||||
};
|
||||
|
||||
std::size_t LessThan::funcalls_;
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator>
|
||||
void test_upper_bound (int line,
|
||||
const char *src_str,
|
||||
char val_char,
|
||||
std::size_t result_off,
|
||||
std::size_t ncomp,
|
||||
const ForwardIterator*,
|
||||
const char *itname,
|
||||
bool predicate)
|
||||
{
|
||||
RW_ASSERT (0 != src_str);
|
||||
|
||||
const std::size_t nsrc = std::strlen (src_str);
|
||||
UserClass* const xsrc = UserClass::from_char (src_str, nsrc);
|
||||
|
||||
if (nsrc < result_off)
|
||||
result_off = nsrc;
|
||||
|
||||
// construct the source range to pass to the algorithm
|
||||
const ForwardIterator first (xsrc, xsrc, xsrc + nsrc);
|
||||
const ForwardIterator last (xsrc + nsrc, xsrc + nsrc, xsrc + nsrc);
|
||||
|
||||
// construct the object to pass to the algorithm
|
||||
// the type of the object is distinct from the iterator's value_type
|
||||
// to detect unwarranted assumptions made by the implementation
|
||||
Y value (0, 0 /* dummy arguments */);
|
||||
value.xval_.data_.val_ = val_char;
|
||||
|
||||
// construct the Compare function object to pass to the algorithm
|
||||
// when `predicate' is true
|
||||
const LessThan comp (0, 0 /* dummy arguments */);
|
||||
|
||||
// reset the counter of invocations of UserClass::operator<()
|
||||
UserClass::n_total_op_lt_ = 0;
|
||||
|
||||
// invoke the appropriate form of the algorithm, storing
|
||||
// the resturned value
|
||||
const ForwardIterator result = predicate
|
||||
? std::upper_bound (first, last, value, comp)
|
||||
: std::upper_bound (first, last, value);
|
||||
|
||||
// silence bogus EDG eccp 3.6 remark #550-D:
|
||||
// variable was set but never used
|
||||
_RWSTD_UNUSED (result);
|
||||
|
||||
// verify correctness
|
||||
const std::size_t off = std::size_t (result.cur_ - xsrc);
|
||||
|
||||
rw_assert (off == result_off, 0, line,
|
||||
"upper_bound(%s = \"%s\", ...%{?}%#c%{;}) ==> "
|
||||
"first + %zu, got %zu",
|
||||
itname, src_str, !predicate, val_char,
|
||||
off, result_off);
|
||||
|
||||
// verify complexity
|
||||
const std::size_t funcalls = predicate
|
||||
? LessThan::funcalls_ : UserClass::n_total_op_lt_;
|
||||
|
||||
rw_assert (funcalls <= ncomp, 0, line,
|
||||
"upper_bound(%s = \"%s\", ...%{?}%#c%{;}) complexity: "
|
||||
"invoked predicate at most %zu times, got %zu",
|
||||
itname, src_str, !predicate, val_char,
|
||||
ncomp, funcalls);
|
||||
|
||||
delete[] xsrc;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
template <class ForwardIterator>
|
||||
void test_upper_bound (const ForwardIterator*,
|
||||
const char *itname,
|
||||
bool predicate)
|
||||
{
|
||||
#define TEST(str, val, off, comp) \
|
||||
test_upper_bound (__LINE__, str, val, std::size_t (off), \
|
||||
std::size_t (comp), (ForwardIterator*)0, \
|
||||
itname, predicate)
|
||||
|
||||
rw_info (0, 0, 0,
|
||||
"std::upper_bound (%s, %1$s, const UserClass&%{?}, %s%{;})",
|
||||
itname, predicate, "LessThan");
|
||||
|
||||
// +--------------- source sequence
|
||||
// | +--------- value argument
|
||||
// | | +----- offset of the resturned iterator, -1 for end
|
||||
// | | | +-- complexity: at most (log(last - first) + 1)
|
||||
// | | | | comparisons (or applications of the predicate)
|
||||
// | | | |
|
||||
// V V V V
|
||||
TEST ("", 'a', 0, 0);
|
||||
TEST ("a", 'a', 1, 1);
|
||||
TEST ("a", 'b', 1, 1);
|
||||
TEST ("b", 'a', 0, 1);
|
||||
|
||||
TEST ("aa", 'a', 2, 2);
|
||||
TEST ("ab", 'a', 1, 2);
|
||||
TEST ("ab", 'b', 2, 2);
|
||||
TEST ("bb", 'a', 0, 2);
|
||||
|
||||
TEST ("ace", 'a', 1, 3);
|
||||
TEST ("ace", 'b', 1, 3);
|
||||
TEST ("ace", 'c', 2, 3);
|
||||
TEST ("ace", 'd', 2, 3);
|
||||
TEST ("ace", 'e', 3, 3);
|
||||
TEST ("ace", 'f', 3, 3);
|
||||
|
||||
TEST ("aceg", 'a', 1, 3);
|
||||
TEST ("aceg", 'b', 1, 3);
|
||||
TEST ("aceg", 'c', 2, 3);
|
||||
TEST ("aceg", 'd', 2, 3);
|
||||
TEST ("aceg", 'e', 3, 3);
|
||||
TEST ("aceg", 'f', 3, 3);
|
||||
TEST ("aceg", 'g', 4, 3);
|
||||
TEST ("aceg", 'h', 4, 3);
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int rw_opt_no_fwd_iter;
|
||||
static int rw_opt_no_bidir_iter;
|
||||
static int rw_opt_no_rnd_iter;
|
||||
static int rw_opt_no_predicate;
|
||||
|
||||
|
||||
static void
|
||||
test_upper_bound (bool predicate)
|
||||
{
|
||||
rw_info (0, 0, 0, "template <class %s, class %s%{?}, class %s%{;}> "
|
||||
"std::upper_bound (%1$s, %1$s, const UserClass&%{?}, %4$s%{;})",
|
||||
"ForwardIterator", "UserClass", predicate, "Compare", predicate);
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "ForwardIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_upper_bound ((FwdIter<UserClass>*)0, "ForwardIterator", predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_bidir_iter) {
|
||||
rw_note (0, 0, 0, "BidirectionalIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_upper_bound ((BidirIter<UserClass>*)0, "BidirectionalIterator",
|
||||
predicate);
|
||||
}
|
||||
|
||||
if (rw_opt_no_fwd_iter) {
|
||||
rw_note (0, 0, 0, "RandomAccessIterator test disabled");
|
||||
}
|
||||
else {
|
||||
test_upper_bound ((RandomAccessIter<UserClass>*)0,
|
||||
"RandomAccessIterator",
|
||||
predicate);
|
||||
}
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
static int
|
||||
run_test (int, char*[])
|
||||
{
|
||||
test_upper_bound (false);
|
||||
|
||||
if (rw_opt_no_predicate) {
|
||||
rw_note (0, __FILE__, __LINE__,
|
||||
"test of the Predicate form of std::upper_bound disabled");
|
||||
}
|
||||
else {
|
||||
test_upper_bound (true);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**************************************************************************/
|
||||
|
||||
int main (int argc, char *argv[])
|
||||
{
|
||||
return rw_test (argc, argv, __FILE__,
|
||||
"lib.upper.bound",
|
||||
0 /* no comment */,
|
||||
run_test,
|
||||
"|-no-Predicate# "
|
||||
"|-no-ForwardIterator# "
|
||||
"|-no-BidirectionalIterator# "
|
||||
"|-no-RandomAccessIterator#",
|
||||
&rw_opt_no_predicate,
|
||||
&rw_opt_no_fwd_iter,
|
||||
&rw_opt_no_bidir_iter,
|
||||
&rw_opt_no_rnd_iter);
|
||||
}
|
||||
Reference in New Issue
Block a user