C++ Template Library Module35 Tenouk
C++ Template Library Module35 Tenouk
--THE STL--
ALGORITHM PART III
Note: Compiled using Microsoft Visual C++ .Net, win32 empty console mode application. g++ compilation
example is given at the end of this Module.
Abilities
inplace_merge()
- Combines the elements from two consecutive sorted ranges into a single sorted range, where the
ordering criterion may be specified by a binary predicate.
template<class BidirectionalIterator>
void inplace_merge(
BidirectionalIterator _First,
BidirectionalIterator _Middle,
BidirectionalIterator _Last
);
template<class BidirectionalIterator, class Pr>
void inplace_merge(
BidirectionalIterator _First,
BidirectionalIterator _Middle,
BidirectionalIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A bidirectional iterator addressing the position of the first element in the first of
_First
two consecutive sorted ranges to be combined and sorted into a single range.
A bidirectional iterator addressing the position of the first element in the second
_Middle
of two consecutive sorted ranges to be combined and sorted into a single range.
A bidirectional iterator addressing the position one past the last element in the
_Last second of two consecutive sorted ranges to be combined and sorted into a single
range.
User-defined predicate function object that defines the sense in which one
element is greater than another. The binary predicate takes two arguments and
_Comp
should return true when the first element is less than the second element and false
otherwise.
Table 35.1
- The sorted consecutive ranges referenced must be valid; all pointers must be de-referenceable and,
within each sequence, the last position must be reachable from the first by incrementation.
- The sorted consecutive ranges must each be arranged as a precondition to the application of the
inplace_merge() algorithm in accordance with the same ordering as is to be used by the algorithm
to sort the combined ranges.
- The operation is stable as the relative order of elements within each range is preserved. When there are
equivalent elements in both source ranges, the element is the first range precedes the element from the
second in the combined range.
- The complexity depends on the available memory as the algorithm allocates memory to a temporary
buffer. If sufficient memory is available, the best case is linear with (_Last – _First)–1
comparisons; if no auxiliary memory is available, the worst case is N log(N), where N =
(_Last–_First).
www.tenouk.com Page 1 of 40
//algorithm, inplace_merge()
#include <vector>
#include <algorithm>
//For greater<int>()
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1;
vector <int>::iterator Iter1, Iter2, Iter3;
int j;
for(j =-5; j <= 0; j++)
vec1.push_back(j);
www.tenouk.com Page 2 of 40
cout<<*Iter2<<" ";
cout<<endl;
Output:
iter_swap()
Parameters
Parameter Description
_Left One of the forward iterators whose value is to be exchanged.
_Right The second of the forward iterators whose value is to be exchanged.
Table 35.2
- swap() should be used in preference to iter_swap(), which was included in the C++ Standard for
backward compatibility. If Fit1 and Fit2 are forward iterators, then iter_swap(Fit1, Fit2),
is equivalent to swap(*Fit1, *Fit2).
- The value types of the input forward iterators must have the same value.
//algorithm, iter_swap()
#include <vector>
#include <deque>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
www.tenouk.com Page 3 of 40
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{ m_nVal = rhs.m_nVal; return *this;}
bool operator<(const CInt& rhs) const
{ return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
CInt c1 = 9, c2 = 12, c3 = 17;
deque<CInt> deq;
deque<CInt>::iterator deqIter;
deq.push_back(c1);
deq.push_back(c2);
deq.push_back(c3);
cout<<"\nThe deque of CInts data with first and last\nelements re swapped is: ";
for(deqIter = deq.begin(); deqIter != --deq.end(); deqIter++)
cout<<" "<<*deqIter<<",";
deqIter = --deq.end();
cout<<" "<<*deqIter<<endl;
int i;
for(i = 10; i <= 14; i++)
vec.push_back(i);
int j;
for(j = 16; j <= 20; j++)
deq1.push_back(j);
www.tenouk.com Page 4 of 40
for(deq1Iter = deq1.begin(); deq1Iter != deq1.end(); deq1Iter++)
cout<<*deq1Iter<<" ";
cout<<endl;
iter_swap(vec.begin(), deq1.begin());
cout<<"\nAfter exchanging first elements,\nvector vec data is: ";
for(Iter1 = vec.begin(); Iter1 != vec.end(); Iter1++)
cout<<*Iter1<<" ";
cout<<endl<<"and deque deq1 data is: ";
for(deq1Iter = deq1.begin(); deq1Iter != deq1.end(); deq1Iter++)
cout<<*deq1Iter<<" ";
cout<<endl;
return 0;
}
Output:
lexicographical_compare()
- Compares element by element between two sequences to determine which is lesser of the two.
Parameters
Parameter Description
An input iterator addressing the position of the first element in the first range to be
_First1
compared.
An input iterator addressing the position one past the final element in the first range to
_Last1
be compared.
An input iterator addressing the position of the first element in the second range to be
_First2
compared.
An input iterator addressing the position one past the final element in the second range
_Last2
to be compared.
User-defined predicate function object that defines sense in which one element is less
_Comp than another. A binary predicate takes two arguments and returns true when satisfied
and false when not satisfied.
www.tenouk.com Page 5 of 40
Table 35.3
- The return value is true if the first range is lexicographically less than the second range; otherwise
false.
- A lexicographical comparison between sequences compares them element by element until:
▪ It finds two corresponding elements unequal, and the result of their comparison is taken as the
result of the comparison between sequences.
▪ No inequalities are found, but one sequence has more elements than the other, and the shorter
sequence is considered less than the longer sequence.
▪ No inequalities are found and the sequences have the same number of elements, and so the
sequences are equal and the result of the comparison is false.
//algorithm, lexicographical_compare()
#include <vector>
#include <list>
#include <algorithm>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1, vec2;
list <int> lst;
vector <int>::iterator Iter1, Iter2;
list <int>::iterator lst_Iter, lst_inIter;
int i;
for(i = 0; i <= 5; i++)
vec1.push_back(5*i);
int j;
for(j = 0; j <= 6; j++)
lst.push_back(5*j);
int k;
for(k = 0; k <= 5; k++)
vec2.push_back(10*k);
www.tenouk.com Page 6 of 40
cout<<"Vector vec1 is lexicographically_less than lst."<<endl;
else
cout<<"Vector vec1 is lexicographically_less than lst."<<endl;
cout<<"\nOperation: lexicographical_compare(vec1.begin(),\nvec1.end(),
vec2.begin(), vec2.end(), twice).\n";
bool result3;
result3 = lexicographical_compare(vec1.begin(), vec1.end(), vec2.begin(),
vec2.end(), twice);
if(result3)
cout<<"Vector vec1 is lexicographically_less than\nvec2 based on twice."<<endl;
else
cout<<"Vector vec1 is not lexicographically_less than\nvec2 based on
twice."<<endl;
return 0;
}
Output:
lower_bound()
- Finds the position where the first element in an ordered range is or would be if it had a value that is less
than or equivalent to a specified value, where the sense of equivalence may be specified by a binary
predicate.
Parameters
Parameter Description
A forward iterator addressing the position of the first element in the range to be
_First
searched.
A forward iterator addressing the position one past the final element in the range to
_Last
be searched.
The value whose first position or possible first position is being searched for in the
_Val
ordered range.
User-defined predicate function object that defines sense in which one element is
_Comp less than another. A binary predicate takes two arguments and returns true when
satisfied and false when not satisfied.
www.tenouk.com Page 7 of 40
Table 35.4
- The return value is a forward iterator addressing the position where the first element in an ordered
range is or would be if it had a value that is less than or equivalent to a specified value, where the sense
of equivalence may be specified by a binary predicate.
- The sorted source range referenced must be valid; all pointers must be de-referenceable and within the
sequence the last position must be reachable from the first by incrementation.
- The sorted range must each be arranged as a precondition to the application of the lower_bound()
algorithm in accordance with the same ordering as is to be used by the algorithm to sort the combined
ranges.
- The range is not modified by the algorithm merge().
- The value types of the forward iterators need be less-than comparable to be ordered, so that, given two
elements, it may be determined either that they are equivalent (in the sense that neither is less than the
other) or that one is less than the other. This results in an ordering between the nonequivalent elements
- The complexity of the algorithm is logarithmic for random-access iterators and linear otherwise, with
the number of steps proportional to (_Last1 – _First1).
//algorithm, lower_bound()
#include <vector>
#include <algorithm>
//For greater<int>()
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1;
vector <int>::iterator Iter1, Result1;
//Constructing vectors vec1a & vec1b with default less than ordering
int i;
for(i = -3; i <= 6; i++)
vec1.push_back(i);
int j;
for(j =-5; j <= 2; j++)
vec1.push_back(j);
www.tenouk.com Page 8 of 40
<<"binary predicate\nmod_lesser is: ";
for(Iter3 = vec3.begin(); Iter3 != vec3.end(); Iter3++)
cout<<*Iter3<<" ";
cout<<endl;
Output
make_heap()
- Converts elements from a specified range into a heap in which the first element is the largest and for
which a sorting criterion may be specified with a binary predicate.
template<class RandomAccessIterator>
void make_heap(
RandomAccessIterator _First,
RandomAccessIterator _Last
);
template<class RandomAccessIterator, class BinaryPredicate>
void make_heap(
RandomAccessIterator _First,
RandomAccessIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A random-access iterator addressing the position of the first element in the range to be
_First
converted into a heap.
www.tenouk.com Page 9 of 40
A random-access iterator addressing the position one past the final element in the range to
_Last
be converted into a heap.
User-defined predicate function object that defines sense in which one element is less than
_Comp another. A binary predicate takes two arguments and returns true when satisfied and false
when not satisfied.
Table 35.5
- Heaps are an ideal way to implement priority queues and they are used in the implementation of the
Standard Template Library container adaptor priority_queue Class.
- The complexity is linear, requiring 3*(_Last – _First) comparisons.
//algorithm, make_heap()
#include <vector>
#include <algorithm>
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1, vec2;
vector <int>::iterator Iter1, Iter2;
int i;
for(i = 0; i <= 10; i++)
vec1.push_back(i);
Output
www.tenouk.com Page 10 of 40
max()
- Compares two objects and returns the larger of the two, where the ordering criterion may be specified
by a binary predicate.
template<class Type>
const Type& max(
const Type& _Left,
const Type& _Right
);
template<class Type, class Pr>
const Type& max(
const Type& _Left,
const Type& _Right,
BinaryPredicate _Comp
);
Parameters
Parameter Description
_Left The first of the two objects being compared.
_Right The second of the two objects being compared.
_Comp A binary predicate used to compare the two objects.
Table 35.6
- The return value is the greater of the two objects unless neither is greater, in which case it returns the
first of the two objects.
- The max() algorithm is unusual in having objects passed as parameters. Most STL algorithms operate
on a range of elements whose position is specified by iterator passes as parameters.
//algorithm, max()
#include <vector>
#include <set>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{m_nVal = rhs.m_nVal; return *this;}
bool operator<( const CInt& rhs ) const
{return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
www.tenouk.com Page 11 of 40
//Comparing integers directly using the max algorithm
int a = 11, b = -12, c = 20;
const int& result1 = max(a, b, mod_greater);
const int& result2 = max(b, c);
st1.insert(c1);
st1.insert(c2);
st2.insert(c2);
st2.insert(c3);
int i;
for(i = 0; i <= 3; i++)
vec1.push_back(i);
int j;
for(j = 0; j <= 4; j++)
vec2.push_back(j);
int k;
for(k = 0; k <= 2; k++)
vec3.push_back(2*k);
www.tenouk.com Page 12 of 40
cout<<*Iter5<<" ";
cout<<endl;
return 0;
}
Output
max_element()
- Finds the first occurrence of largest element in a specified range where the ordering criterion may be
specified by a binary predicate.
template<class ForwardIterator>
ForwardIterator max_element(
ForwardIterator _First,
ForwardIterator _Last
);
template<class ForwardIterator, class BinaryPredicate>
ForwardIterator max_element(
ForwardIterator _First,
ForwardIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A forward iterator addressing the position of the first element in the range to be
_First
searched for the largest element.
A forward iterator addressing the position one past the final element in the range to
_Last
be searched for the largest element.
User-defined predicate function object that defines the sense in which one element is
_Comp greater than another. The binary predicate takes two arguments and should return true
when the first element is less than the second element and false otherwise.
Table 35.7
- The return value is a forward iterator addressing the position of the first occurrence of the largest
element in the range searched.
- The range referenced must be valid; all pointers must be dereferenceable and within each sequence the
last position is reachable from the first by incrementation.
- The complexity is linear: (_Last – _First)–1 comparison is required for a nonempty range.
//algorithm, max_element()
#include <vector>
#include <set>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
www.tenouk.com Page 13 of 40
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{m_nVal = rhs.m_nVal; return *this;}
bool operator<(const CInt& rhs) const
{return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
//Searching a set container with elements of type CInt
//for the maximum element
CInt c1 = 1, c2 = 2, c3 = -3;
set<CInt> st1;
set<CInt>::iterator st1_Iter, st2_Iter, st3_Iter;
st1.insert(c1);
st1.insert(c2);
st1.insert(c3);
int i;
for(i = 0; i <= 3; i++)
vec.push_back(i);
int j;
for(j = 1; j <= 4; j++)
vec.push_back(-j);
www.tenouk.com Page 14 of 40
Output
merge()
- Combines all of the elements from two sorted source ranges into a single, sorted destination range,
where the ordering criterion may be specified by a binary predicate.
Parameters
Parameter Description
An input iterator addressing the position of the first element in the first of two sorted
_First1
source ranges to be combined and sorted into a single range.
An input iterator addressing the position one past the last element in the first of two sorted
_Last1
source ranges to be combined and sorted into a single range.
An input iterator addressing the position of the first element in second of two consecutive
_First2
sorted source ranges to be combined and sorted into a single range.
An input iterator addressing the position one past the last element in second of two
_Last2
consecutive sorted source ranges to be combined and sorted into a single range.
An output iterator addressing the position of the first element in the destination range
_Result
where the two source ranges are to be combined into a single sorted range.
User-defined predicate function object that defines the sense in which one element is
_Comp greater than another. The binary predicate takes two arguments and should return true
when the first element is less than the second element and false otherwise.
Table 35.8
- The return value is an output iterator addressing the position one past the last element in the sorted
destination range.
- The sorted source ranges referenced must be valid; all pointers must be de-referenceable and within
each sequence the last position must be reachable from the first by incrementation.
- The destination range should not overlap either of the source ranges and should be large enough to
contain the destination range.
- The sorted source ranges must each be arranged as a precondition to the application of the merge()
algorithm in accordance with the same ordering as is to be used by the algorithm to sort the combined
ranges.
- The operation is stable as the relative order of elements within each range is preserved in the
destination range. The source ranges are not modified by the algorithm merge().
www.tenouk.com Page 15 of 40
- The value types of the input iterators need be less than comparable to be ordered, so that, given two
elements, it may be determined either that they are equivalent, in the sense that neither is less than the
other or that one is less than the other. This results in an ordering between the nonequivalent elements.
- When there are equivalent elements in both source ranges, the elements in the first range precede the
elements from the second source range in the destination range.
- The complexity of the algorithm is linear with at most (_Last1 – _First1)–(_Last2 –
_First2)–1 comparisons.
- The list class provides a member function merge() to merge the elements of two lists.
//algorithm, merge()
#include <vector>
#include <algorithm>
//For greater<int>()
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1a, vec1b, vec1(12);
vector <int>::iterator Iter1a, Iter1b, Iter1;
//Constructing vector vec1a and vec1b with default less than ordering
int i;
for(i = 0; i <= 5; i++)
vec1a.push_back(i);
int j;
for(j =-5; j <= 0; j++)
vec1b.push_back(j);
www.tenouk.com Page 16 of 40
<<"binary predicate mod_lesser is: ";
for(Iter3a = vec3a.begin(); Iter3a != vec3a.end(); Iter3a++)
cout<<*Iter3a<<" ";
cout<<endl;
Output
www.tenouk.com Page 17 of 40
min()
- Compares two objects and returns the lesser of the two, where the ordering criterion may be specified
by a binary predicate.
template<class Type>
const Type& min(
const Type& _Left,
const Type& _Right
);
template<class Type, class Pr>
const Type& min(
const Type& _Left,
const Type& _Right,
BinaryPredicate _Comp
);
Parameters
Parameter Description
_Left The first of the two objects being compared.
_Right The second of the two objects being compared.
_Comp A binary predicate used to compare the two objects.
Table 35.9
- The return value is the lesser of the two objects unless neither is lesser, in which case it returns the first
of the two objects.
- The min() algorithm is unusual in having objects passed as parameters. Most STL algorithms operate
on a range of elements whose position is specified by iterators passed as parameters.
//algorithm, min()
#include <vector>
#include <set>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{
m_nVal = rhs.m_nVal;
return *this;
}
bool operator<(const CInt& rhs) const
{return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
www.tenouk.com Page 18 of 40
};
int main()
{
//Comparing integers directly using the min algorithm with
//binary predicate mod_lesser & with default less than
int a = 9, b = -12, c = 12;
const int& result1 = min(a, b, mod_lesser);
const int& result2 = min(b, c);
st1.insert(ci1);
st1.insert(ci2);
st2.insert(ci2);
st2.insert(ci3);
int i;
for(i = 1; i <= 4; i++)
vec1.push_back(i);
int j;
for(j = 1; j <= 3; j++)
vec2.push_back(j);
int k;
for(k = 1; k <= 3; k++)
vec3.push_back(2*k);
www.tenouk.com Page 19 of 40
cout<<endl;
Output:
min_element()
- Finds the first occurrence of smallest element in a specified range where the ordering criterion may be
specified by a binary predicate.
template<class ForwardIterator>
ForwardIterator min_element(
ForwardIterator _First,
ForwardIterator _Last
);
template<class ForwardIterator, class BinaryPredicate>
ForwardIterator min_element(
ForwardIterator _First,
ForwardIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A forward iterator addressing the position of the first element in the range to
_First
be searched for the largest element.
A forward iterator addressing the position one past the final element in the
_Last
range to be searched for the largest element.
User-defined predicate function object that defines the sense in which one
element is greater than another. The binary predicate takes two arguments and
_Comp
should return true when the first element is less than the second element and
false otherwise.
Table 35.10
- The return value is a forward iterator addressing the position of the first occurrence of the smallest
element in the range searched.
- The range referenced must be valid; all pointers must be de-referenceable and within each sequence the
last position is reachable from the first by incrementation.
- The complexity is linear: (_Last – _First)–1 comparison is required for a non-empty range.
www.tenouk.com Page 20 of 40
//algorithm, min_element()
#include <vector>
#include <set>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal( rhs.m_nVal ){}
CInt& operator=(const CInt& rhs)
{
m_nVal = rhs.m_nVal;
return *this;
}
bool operator<(const CInt& rhs) const
{return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
//Searching a set container with elements of type CInt
//for the minimum element
CInt ci1 = 4, ci2 = 12, ci3 = -4;
set<CInt> st1;
set<CInt>::iterator st1Iter, st2Iter, st3Iter;
st1.insert(ci1);
st1.insert(ci2);
st1.insert(ci3);
int i;
for(i = 1; i <= 4; i++)
vec1.push_back(i);
int j;
for(j = 1; j <= 5; j++)
vec1.push_back(-2*j);
www.tenouk.com Page 21 of 40
for(vec1Iter = vec1.begin(); vec1Iter != vec1.end(); vec1Iter++)
cout<<*vec1Iter<<" ";
cout<<endl;
Output:
mismatch()
- Compares two ranges element by element either for equality or equivalent in a sense specified by a
binary predicate and locates the first position where a difference occurs.
Parameters
Parameter Description
An input iterator addressing the position of the first element in the first range to be
_First1
tested.
An input iterator addressing the position one past the final element in the first
_Last1
range to be tested.
An input iterator addressing the position of the first element in the second range to
_First2
be tested.
User-defined predicate function object that defines the condition to be satisfied if
_Comp two elements are to be taken as equivalent. A binary predicate takes two arguments
and returns true when satisfied and false when not satisfied.
Table 35.11
www.tenouk.com Page 22 of 40
- The return value is a pair of iterators addressing the positions of the mismatch in the two ranges, the
first component iterator to the position in the first range and the second component iterator to the
position in the second range.
- If there is no difference between the elements in the ranges compared or if the binary predicate in the
second version is satisfied by all element pairs from the two ranges, then the first component iterator
points to the position one past the final element in the first range and the second component iterator to
position one past the final element tested in the second range.
- The range to be searched must be valid; all pointers must be de-referenceable and the last position is
reachable from the first by incrementation.
- The time complexity of the algorithm is linear in the number of elements contained in the range.
- The operator== used to determine the equality between elements must impose an equivalence
relation between its operands.
//algorithm, mismatch()
#include <vector>
#include <list>
#include <algorithm>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1, vec2;
list <int> lst;
vector <int>::iterator Iter1, Iter2;
list <int>::iterator lst_Iter, lst_inIter;
int i;
for(i = 0; i <= 5; i++)
vec1.push_back(5*i);
int j;
for(j = 0; j <= 7; j++)
lst.push_back(5*j);
int k;
for(k = 0; k <= 5; k++)
vec2.push_back(10*k);
www.tenouk.com Page 23 of 40
for(lst_Iter = lst.begin(); lst_Iter!= lst.end(); lst_Iter++)
cout<<*lst_Iter<<" ";
cout<<endl;
//Test vec1 and vec2 for mismatch under the binary predicate twice
pair<vector <int>::iterator, vector <int>::iterator> result2;
cout<<"\nOperation: mismatch(vec1.begin(), vec1.end(), vec2.begin(), twice).\n";
result2 = mismatch(vec1.begin(), vec1.end(), vec2.begin(), twice);
if(result2.first == vec1.end())
cout<<"The two ranges do not differ based on the\nbinary predicate twice."<<endl;
else
cout<<"The first mismatch is between "<<*result2.first<<" and
"<<*result2.second<<endl;
return 0;
}
Output
next_permutation()
- Reorders the elements in a range so that the original ordering is replaced by the lexicographically next
greater permutation if it exists, where the sense of next may be specified with a binary predicate.
template<class BidirectionalIterator>
bool next_permutation(
BidirectionalIterator _First,
BidirectionalIterator _Last
);
template<class BidirectionalIterator, class BinaryPredicate>
bool next_permutation(
BidirectionalIterator _First,
BidirectionalIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A bidirectional iterator pointing to the position of the first element in the range to be
_First
permuted.
A bidirectional iterator pointing to the position one past the final element in the range to
_Last
be permuted.
User-defined predicate function object that defines the comparison criterion to be
_Comp
satisfied by successive elements in the ordering. A binary predicate takes two
www.tenouk.com Page 24 of 40
arguments and returns true when satisfied and false when not satisfied.
Table 35.12
- The return value is true if the lexicographically next permutation exists and has replaced the original
ordering of the range; otherwise false, in which case the ordering is transformed into the
lexicographically smallest permutation.
- The range referenced must be valid; all pointers must be dereferenceable and within the sequence the
last position is reachable from the first by incrementation.
- The default binary predicate is less than and the elements in the range must be less than comparable to
insure that the next permutation is well defined.
- The complexity is linear with at most (_Last–_First)/2 swaps.
//algorithm, next_permutation()
#include <vector>
#include <deque>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{m_nVal = rhs.m_nVal; return *this;}
bool operator<(const CInt& rhs) const
{return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
//Reordering the elements of type CInt in a deque
//using the prev_permutation algorithm
CInt ci1 = 7, ci2 = 5, ci3 = 17;
bool deq1Result;
deque<CInt> deq1, deq2, deq3;
deque<CInt>::iterator deq1Iter;
deq1.push_back(ci1);
deq1.push_back(ci2);
deq1.push_back(ci3);
www.tenouk.com Page 25 of 40
cout<<"The lexicographically next permutation "
<<"exists and has\nreplaced the original "
<<"ordering of the sequence in deq1."<<endl;
else
cout<<"The lexicographically next permutation doesn't "
<<"exist\n and the lexicographically "
<<"smallest permutation\n has replaced the "
<<"ordering of the sequence in deq1."<<endl;
int i;
for(i = -3; i <= 4; i++)
vec1.push_back(i);
int k = 1;
while (k <= 5)
{
next_permutation(vec1.begin(), vec1.end(), mod_lesser);
cout<<"After another next_permutation() of vector vec1,\nvec1 data: ";
for(Iter1 = vec1.begin(); Iter1 != vec1.end(); Iter1 ++)
cout<<*Iter1<<" ";
cout<<endl;
k++;
}
return 0;
}
Output:
nth_element()
www.tenouk.com Page 26 of 40
- Partitions a range of elements, correctly locating the nth element of the sequence in the range so that all
the elements in front of it are less than or equal to it and all the elements that follow it in the sequence
are greater than or equal to it.
template<class RandomAccessIterator>
void nth_element(
RandomAccessIterator _First,
RandomAccessIterator _Nth,
RandomAccessIterator _Last
);
template<class RandomAccessIterator, class BinaryPredicate>
void nth_element(
RandomAccessIterator _First,
RandomAccessIterator _Nth,
RandomAccessIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A random-access iterator addressing the position of the first element in the range to be
_First
partitioned.
A random-access iterator addressing the position of element to be correctly ordered on
_Nth
the boundary of the partition.
A random-access iterator addressing the position one past the final element in the range
_Last
to be partitioned.
User-defined predicate function object that defines the comparison criterion to be
_Comp satisfied by successive elements in the ordering. A binary predicate takes two
arguments and returns true when satisfied and false when not satisfied.
Table 35.13
- The range referenced must be valid; all pointers must be de-referenceable and within the sequence the
last position is reachable from the first by incrementation.
- The nth_element() algorithm does not guarantee that elements in the sub-ranges either side of the
nth element are sorted. It thus makes fewer guarantees than partial_sort(), which orders the
elements in the range below some chosen element, and may be used as a faster alternative to
partial_sort() when the ordering of the lower range is not required.
- Elements are equivalent, but not necessarily equal, if neither is less than the other.
- The average of a sort complexity is linear with respect to _Last – _First.
//algorithm, nth_element()
#include <vector>
#include <algorithm>
//For greater<int>()
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec;
vector <int>::iterator Iter1;
int i;
for(i = 0; i <= 5; i++)
vec.push_back(i);
int j;
for(j = 10; j <= 15; j++)
vec.push_back(j);
int k;
for(k = 20; k <= 25; k++)
www.tenouk.com Page 27 of 40
vec.push_back(k);
Output:
partial_sort()
- Arranges a specified number of the smaller elements in a range into a non-descending order or
according to an ordering criterion specified by a binary predicate.
template<class RandomAccessIterator>
void partial_sort(
RandomAccessIterator _First,
www.tenouk.com Page 28 of 40
RandomAccessIterator _SortEnd,
RandomAccessIterator _Last
);
template<class RandomAccessIterator, class BinaryPredicate>
void partial_sort(
RandomAccessIterator _First,
RandomAccessIterator _SortEnd,
RandomAccessIterator _Last
BinaryPredicate _Comp
);
Parameters
Parameter Description
A random-access iterator addressing the position of the first element in the range
_First
to be sorted.
A random-access iterator addressing the position one past the final element in the
_SortEnd
sub-range to be sorted.
A random-access iterator addressing the position one past the final element in the
_Last
range to be partially sorted.
User-defined predicate function object that defines the comparison criterion to be
_Comp satisfied by successive elements in the ordering. A binary predicate takes two
arguments and returns true when satisfied and false when not satisfied.
Table 35.14
- The range referenced must be valid; all pointers must be de-referenceable and within the sequence the
last position is reachable from the first by incrementation.
- Elements are equivalent, but not necessarily equal, if neither is less than the other. The sort()
algorithm is not stable and does not guarantee that the relative ordering of equivalent elements will be
preserved. The algorithm stable_sort() does preserve this original ordering.
- The average of a sort complexity is O(N log N), where N = _Last – _First.
//algorithm, partial_sort()
#include <vector>
#include <algorithm>
//For greater<int>()
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1;
vector <int>::iterator Iter1;
int j;
for(j = 0; j <= 5; j++)
vec1.push_back(j);
www.tenouk.com Page 29 of 40
cout<<"\nOperation: partial_sort(vec1.begin(),\nvec1.begin()+4, vec1.end(),
greater<int>()).\n";
partial_sort(vec1.begin(), vec1.begin()+4, vec1.end(), greater<int>());
cout<<"Partially resorted (greater) vector vec1 data:\n";
for(Iter1 = vec1.begin(); Iter1 != vec1.end(); Iter1++)
cout<<*Iter1<<" ";
cout<<endl;
Output:
partial_sort_copy()
- Copies elements from a source range into a destination range where the source elements are ordered by
either less than or another specified binary predicate.
Parameters
Parameter Description
_First1 An input iterator addressing the position of the first element in the source range.
An input iterator addressing the position one past the final element in the source
_Last1
range.
A random-access iterator addressing the position of the first element in the sorted
_First2
destination range.
A random-access iterator addressing the position one past the final element in the
_Last2
sorted destination range.
www.tenouk.com Page 30 of 40
User-defined predicate function object that defines the condition to be satisfied if
_Comp two elements are to be taken as equivalent. A binary predicate takes two arguments
and returns true when satisfied and false when not satisfied.
Table 35.15
- The return value is a random-access iterator addressing the element in the destination range one
position beyond the last element inserted from the source range.
- The source and destination ranges must not overlap and must be valid; all pointers must be
dereferenceable and within each sequence the last position must be reachable from the first by
incrementation.
- The binary predicate must provide a strict weak ordering so that elements that are not equivalent are
ordered, but elements that are equivalent are not. Two elements are equivalent under less than, but not
necessarily equal, if neither is less than the other.
//algorithm, partial_sort_copy()
#include <vector>
#include <list>
#include <algorithm>
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec1, vec2;
list <int> lst;
vector <int>::iterator Iter1, Iter2;
list <int>::iterator lst_Iter, lst_inIter;
int i;
for(i = 0; i <= 7; i++)
vec1.push_back(i);
random_shuffle(vec1.begin(), vec1.end());
lst.push_back(6);
lst.push_back(5);
lst.push_back(2);
lst.push_back(3);
lst.push_back(4);
lst.push_back(1);
www.tenouk.com Page 31 of 40
result2 = partial_sort_copy(lst.begin(), lst.end(), vec2.begin(), vec2.begin()+6,
greater<int>());
cout<<"List lst into vector vec2 data: ";
for(Iter2 = vec2.begin(); Iter2 != vec2.end(); Iter2++)
cout<<*Iter2<<" ";
cout<<endl;
cout<<"The first vec2 element one position beyond"
<<"\nthe last lst element inserted was "<<*result2<<endl;
return 0;
}
Output:
partition()
- Classifies elements in a range into two disjoint sets, with those elements satisfying a unary predicate
preceding those that fail to satisfy it.
Parameters
Parameter Description
A bidirectional iterator addressing the position of the first element in the range to
_First
be partitioned.
A bidirectional iterator addressing the position one past the final element in the
_Last
range to be partitioned.
User-defined predicate function object that defines the condition to be satisfied if
_Comp an element is to be classified. A predicate takes a single argument and returns true
or false.
Table 35.16
- The return value is a bidirectional iterator addressing the position of the first element in the range to not
satisfy the predicate condition.
- The range referenced must be valid; all pointers must be dereferenceable and within the sequence the
last position is reachable from the first by incrementation.
- Elements a and b are equivalent, but not necessarily equal, if both Pr (a, b) is false and Pr (b, a) if
false, where Pr is the parameter-specified predicate. The partition() algorithm is not stable and
does not guarantee that the relative ordering of equivalent elements will be preserved. The algorithm
stable_ partition() does preserve this original ordering.
- The complexity is linear: there are (_Last – _First) applications of _Comp and at most
(_Last – _First)/2 swaps.
www.tenouk.com Page 32 of 40
//algorithm, partition()
#include <vector>
#include <algorithm>
#include <iostream>
using namespace std;
//user defined...
bool great(int value)
{return value >3;}
int main()
{
vector <int> vec1, vec2;
vector <int>::iterator Iter1, Iter2;
int i;
for(i = 0; i <= 10; i++)
vec1.push_back(i);
Output:
pop_heap()
- Removes the largest element from the front of a heap to the next-to-last position in the range and then
forms a new heap from the remaining elements.
template<class RandomAccessIterator>
void pop_heap(
RandomAccessIterator _First,
RandomAccessIterator _Last
);
template<class RandomAccessIterator, class BinaryPredicate>
void pop_heap(
RandomAccessIterator _First,
RandomAccessIterator _Last,
BinaryPredicate _Comp
);
Parameters
www.tenouk.com Page 33 of 40
Parameter Description
A random-access iterator addressing the position of the first element in the
_First
heap.
A random-access iterator addressing the position one past the final element in
_Last
the heap.
User-defined predicate function object that defines sense in which one element
_Comp is less than another. A binary predicate takes two arguments and returns true
when satisfied and false when not satisfied.
Table 35.17
- The pop_heap() algorithm is the inverse of the operation performed by the push_heap()
algorithm, in which an element at the next-to-last position of a range is added to a heap consisting of
the prior elements in the range, in the case when the element being added to the heap is larger than any
of the elements already in the heap.
- As mentioned before, heaps have two properties:
- Heaps are an ideal way to implement priority queues and they are used in the implementation of the
Standard Template Library container adaptor priority_queue Class.
- The range referenced must be valid; all pointers must be de-referenceable and within the sequence the
last position is reachable from the first by incrementation.
- The range excluding the newly added element at the end must be a heap.
- The complexity is logarithmic, requiring at most log (_Last – _First) comparisons.
//algorithm, pop_heap()
#include <vector>
#include <algorithm>
#include <functional>
#include <iostream>
using namespace std;
int main()
{
vector <int> vec;
vector <int>::iterator Iter1, Iter2;
int i;
for(i = 1; i <= 9; i++)
vec.push_back(i);
www.tenouk.com Page 34 of 40
push_heap(vec.begin(), vec.end(), greater<int>());
cout<<"The greater than reheaped vec data puts the\nsmallest element first:";
for(Iter1 = vec.begin(); Iter1 != vec.end(); Iter1++)
cout<<*Iter1<<" ";
cout<<endl;
Output
prev_permutation()
- Reorders the elements in a range so that the original ordering is replaced by the lexicographically next
greater permutation if it exists, where the sense of next may be specified with a binary predicate.
template<class BidirectionalIterator>
bool prev_permutation(
BidirectionalIterator _First,
BidirectionalIterator _Last
);
template<class BidirectionalIterator, class BinaryPredicate>
bool prev_permutation(
BidirectionalIterator _First,
BidirectionalIterator _Last,
BinaryPredicate _Comp
);
Parameters
Parameter Description
A bidirectional iterator pointing to the position of the first element in the range to
_First
be permuted.
A bidirectional iterator pointing to the position one past the final element in the
_Last
range to be permuted.
User-defined predicate function object that defines the comparison criterion to be
_Comp satisfied by successive elements in the ordering. A binary predicate takes two
arguments and returns true when satisfied and false when not satisfied.
Table 35.18
www.tenouk.com Page 35 of 40
- The return value is true if the lexicographically previous permutation exists and has replaced the
original ordering of the range; otherwise false, in which case the ordering is transformed into the
lexicographically largest permutation.
- The range referenced must be valid; all pointers must be dereferenceable and within the sequence the
last position is reachable from the first by incrementation.
- The default binary predicate is less than and the elements in the range must be less-than comparable to
ensure that the next permutation is well defined.
- The complexity is linear, with at most (_Last – _First)/2 swap.
//algorithm, prev_permutation()
#include <vector>
#include <deque>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{m_nVal = rhs.m_nVal; return *this;}
bool operator<(const CInt& rhs) const
{return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
//Reordering the elements of type CInt in a deque
//using the prev_permutation algorithm
CInt ci1 = 10, ci2 = 15, ci3 = 20;
bool deq1Result;
deque<CInt> deq1, deq2, deq3;
deque<CInt>::iterator d1_Iter;
deq1.push_back(ci1);
deq1.push_back(ci2);
deq1.push_back(ci3);
www.tenouk.com Page 36 of 40
<<"exist\nand the lexicographically "
<<"smallest permutation\nhas replaced the "
<<"original ordering of the sequence in deq1."<<endl;
int i;
for(i = -4; i <= 4; i++)
vec.push_back(i);
int j = 1;
while (j <= 5)
{
prev_permutation(vec.begin(), vec.end(), mod_lesser);
cout<<"After another prev_permutation() of vector vec,\nvec data: ";
for(Iter1 = vec.begin(); Iter1 != vec.end(); Iter1 ++)
cout<<*Iter1<<" ";
cout<<endl;
j++;
}
return 0;
}
Output:
www.tenouk.com Page 37 of 40
//*******algoiterswap.cpp*******
//algorithm, iter_swap()
#include <vector>
#include <deque>
#include <algorithm>
#include <iostream>
using namespace std;
class CInt;
ostream& operator<<(ostream& osIn, const CInt& rhs);
class CInt
{
public:
CInt(int n = 0) : m_nVal(n){}
CInt(const CInt& rhs) : m_nVal(rhs.m_nVal){}
CInt& operator=(const CInt& rhs)
{ m_nVal = rhs.m_nVal; return *this;}
bool operator<(const CInt& rhs) const
{ return (m_nVal < rhs.m_nVal);}
friend ostream& operator<<(ostream& osIn, const CInt& rhs);
private:
int m_nVal;
};
int main()
{
CInt c1 = 9, c2 = 12, c3 = 17;
deque<CInt> deq;
deque<CInt>::iterator deqIter;
deq.push_back(c1);
deq.push_back(c2);
deq.push_back(c3);
cout<<"\nThe deque of CInts data with first and last\nelements re swapped is: ";
for(deqIter = deq.begin(); deqIter != --deq.end(); deqIter++)
cout<<" "<<*deqIter<<",";
deqIter = --deq.end();
cout<<" "<<*deqIter<<endl;
www.tenouk.com Page 38 of 40
int i;
for(i = 10; i <= 14; i++)
vec.push_back(i);
int j;
for(j = 16; j <= 20; j++)
deq1.push_back(j);
iter_swap(vec.begin(), deq1.begin());
cout<<"\nAfter exchanging first elements,\nvector vec data is: ";
for(Iter1 = vec.begin(); Iter1 != vec.end(); Iter1++)
cout<<*Iter1<<" ";
cout<<endl<<"and deque deq1 data is: ";
for(deq1Iter = deq1.begin(); deq1Iter != deq1.end(); deq1Iter++)
cout<<*deq1Iter<<" ";
cout<<endl;
return 0;
}
//******algopartition.cpp*******
//algorithm, partition()
#include <vector>
#include <algorithm>
#include <iostream>
using namespace std;
//user defined...
bool great(int value)
{return value >3;}
int main()
{
vector <int> vec1, vec2;
vector <int>::iterator Iter1, Iter2;
int i;
for(i = 0; i <= 10; i++)
vec1.push_back(i);
www.tenouk.com Page 39 of 40
cout<<*Iter1<<" ";
cout<<endl;
www.tenouk.com Page 40 of 40