STL sort Introduction and Vector for_each () lamdba output

Source: Internet
Author: User
Tags bool relative advantage
For_each (Vec.begin (), Vec.end (), [] (const t& t) {cout <<  t <<endl;}

There is a proverb in the West: Don't invent the wheel again.

STL almost encapsulates all the algorithms in the data structure, from the list to the queue, from vectors to stacks, to hash to two forks, from search to sort, from add to delete ... It can be said that if you understand the STL, you will find that you do not have to adhere to the algorithm itself, so standing on the shoulders of giants to consider more advanced applications.

Sorting is one of the most widely used algorithms, this paper introduces in detail the usage and difference of different sorting algorithms in STL. 1 The sort algorithm provided by the STL

C + + is so many people like it, because it has the concept of object-oriented, but also maintain the high efficiency of C language features. The STL sorting algorithm also needs to remain efficient. Therefore, for different requirements, STL provides different functions, different functions, the implementation of the algorithm is different. 1.1 Introduction to all sort algorithms

All parameters of the sort algorithm need to be entered in a range, [begin, end]. The iterator used here (iterator) needs to be a random iterator (radomaccessiterator), that is, an iterator that can be randomly accessed, such as: It+n or something. (except partition and stable_partition)
If you need to define a comparison function yourself, you can pass in your defined copy function (functor) as a parameter. Each of these algorithms supports incoming comparison functions. The following is a list of the names of all STL sort algorithm functions:

Functions Description of Function name

Sort    Sorts all elements of a given interval
stable_sort a stable ordering of all elements in a given interval
partial_sort    The ordering of all elements in a given interval
partial_sort_copy   copy and sort a given interval
nth_element find the element corresponding to a position in a given interval
is_sorted   Determine if an interval has been sequenced
partition   Causes elements that meet a certain condition to be placed in front
stable_partition    relatively stable so that elements that meet a certain condition are placed in front

Where Nth_element is the most difficult to understand, in fact, this function is used to find out the first few. For example: To find the value of the middle number in an array of 7 elements, at which point I may not care about the front or the back, I only care what the value of the element in the fourth bit is. The comparison function in 1.2 sort

When you need to sort in a particular way, you need to specify a comparison function for sort, or the program will automatically provide you with a comparison function.

Vector < int > vect;
//...
Sort (Vect.begin (), Vect.end ());
This is equivalent to calling
sort (vect.begin (), Vect.end (), less<int> ());

In the example above, the system itself provides less functor for sort. Other functor functions are provided in the STL, and the following is a list of the functor functions:
Name Function description

equal_to    equal
not_equal_to    not    less than
greater greater than
less_equal  less than equals
Greater_equal   greater than or equal to

The

need to be aware that these functions are not all suitable for your sort algorithm, how to choose, and decide on your application. In addition, you cannot write the name of the functor directly, but instead write its overloaded () function:
Less ()
greater ()
when elements in your container are standard types (int float char) or string, you can use these function templates directly. But if you define your own type or you need to sort by other means, there are two ways you can achieve this: one is to write your own comparison function. The other is an overloaded type of ' < ' operation assignment.

#include <iostream> #include <algorithm> #include <functional> #include <vector> using

namespace Std;
        class MyClass {public:myclass (int a, int b): First (a), second (b) {} int first;
        int second;
        BOOL Operator < (const MyClass &m) Const {return first < M.first;

}
};

BOOL Less_second (const MyClass & M1, const MyClass & m2) {return m1.second < M2.second;}
        int main () {vector< MyClass > Vect;
                for (int i = 0; i < ten; I + +) {MyClass my (10-i, i*3);
        Vect.push_back (my); } for (int i = 0; i < vect.size (); i + +) cout<< "(" <<vect[i].first<< "," <<vect[i
        ].second<< ") \ n";
        Sort (Vect.begin (), Vect.end ());
        cout<< "After sorted by first:" <<endl; for (int i = 0; i < vect.size (); i + +) cout<< "(" <<vect[i].first<< ", "<<vect[i].second<<") \ n ";
        cout<< "After sorted by second:" <<endl;
        Sort (Vect.begin (), Vect.end (), Less_second); for (int i = 0; i < vect.size (); i + +) cout<< "(" <<vect[i].first<< "," &LT;&LT;VECT[I].SECOND&L

        t;< ") \ n";
return 0; }

Know what the output is:

(10,0)
(9,3)
(8,6)
(7,9)
(6,12)
(5,15)
(4,18)
(3,21)
(2,24)
(1,27)
After sorted by first:
(1,27)
(2,24) (
3,21) (
4,18
) (5,15) (6,12) (7,9) ( 8,6) (
9,3)
(10,0) after
sorted by second:
(10,0)
(
9,3) (8,6) (7,9) (6,12)
(5,15)
(4,18)
(3,21)
(2,24)
(1,27)
stability of the 1.3 sort

You find it strange to have sort and stable_sort, and partition and Stable_partition. The difference is that a function with stable guarantees that the original relative order of the equal elements will remain unchanged after sorting. Perhaps you will ask, since equal, you also control his relative position, also can not know who is who. Here's a question to figure out, the equivalence here is that the function you provide means that two elements are equal and not necessarily a touch of the same element.
For example, if you write a comparison function:

BOOL Less_len (const string &STR1, const string &str2)
{
        return str1.length () < Str2.length ();
}

At this point, "Apple" and "winter" are equal, if "apple" appears in front of "winter", with stable functions sorted, their order must be the same, if you use a function without "stable" sort, then after sorting, " Winter "may be in front of" Apple ". 1.4 Full Order

A full order arranges all elements of a given range in the order of their size relationships. Functions that are used for full ordering are

Template <class randomaccessiterator>
void sort (randomaccessiterator first, Randomaccessiterator last);

Template <class Randomaccessiterator, class strictweakordering>
void Sort (randomaccessiterator first, Randomaccessiterator last,
strictweakordering comp);

Template <class randomaccessiterator>
void Stable_sort (randomaccessiterator first, Randomaccessiterator last);

Template <class Randomaccessiterator, class strictweakordering>
void Stable_sort (randomaccessiterator First, Randomaccessiterator last, 
strictweakordering comp);

In the 1th, 3 forms, sort and stable_sort do not specify a comparison function, and the system uses operator< to sort all elements in the interval [first,last] By default, so if you are using a type that the rebel has overloaded operator < function, then you can worry about it. 2nd, 4 forms, you can arbitrarily specify the comparison function, the application is more flexible. Take a look at the actual application:
There are 10 students in the class, I want to know their grades.

#include <iostream> #include <algorithm> #include <functional> #include <vector> #include <

String> using namespace std;
        Class student{Public:student (const string &a, int b): Name (a), score (b) {} string name;
        int score;
        BOOL Operator < (const student &m) Const {return score< M.score;

}
};
        int main () {vector< student> vect;
        Student St1 ("Tom", 74);
        Vect.push_back (ST1);
        St1.name= "Jimy";
        st1.score=56;
        Vect.push_back (ST1);
        St1.name= "Mary";
        st1.score=92;
        Vect.push_back (ST1);
        St1.name= "Jessy";
        st1.score=85;
        Vect.push_back (ST1);
        St1.name= "Jone";
        st1.score=56;
        Vect.push_back (ST1);
        St1.name= "Bush";
        st1.score=52;
        Vect.push_back (ST1);
        St1.name= "Winter";
        st1.score=77;
        Vect.push_back (ST1);
    St1.name= "Andyer";    st1.score=63;
        Vect.push_back (ST1);
        St1.name= "Lily";
        st1.score=76;
        Vect.push_back (ST1);
        St1.name= "Maryia";
        st1.score=89;
        Vect.push_back (ST1);
        cout<< "------before sort ..." <<endl;
        for (int i = 0; i < vect.size (); i + +) cout<<vect[i].name<< ": \ T" <<vect[i].score<<endl;
        Stable_sort (Vect.begin (), Vect.end (),less<student> ());
        cout << "-----after sort ..." <<endl;
        for (int i = 0; i < vect.size (); i + +) cout<<vect[i].name<< ": \ T" <<vect[i].score<<endl;
return 0; }

Its output is:

------before sort ...
Tom:    The
jimy: The Jessy: $
jone:
winter:77
andyer:63
Lily:
maryia:89
-----After sort ....
Bush:
jimy:
jone: andyer:63,
Tom: All
Lily:
winter:77
Jessy:
maryia:89
Mary:   92

Sort uses a sophisticated "fast-sorting algorithm" (most of the STL versions are now not simple, fast-sorting, but with interpolated sorting algorithms). Note 1, can guarantee a good average performance, the complexity of N*log (n), because the simple fast ordering in theory has the worst case, the performance is very low, its algorithm complexity is n*n, but most of the STL version has been optimized in this area, so you can rest assured that use. Stable_sort uses a "merge sort", allocating enough memory to be N*log (n), otherwise its complexity is N*log (n) *log (n), which has the advantage of keeping the relative positions between equal elements consistent before and after sorting. 1.5 Local sorting

A local sort is actually a sort of order that is provided to reduce unnecessary operations. Its function prototypes are:

template <class randomaccessiterator> void Partial_sort (RandomAccessIterator first,

Randomaccessiterator Middle, randomaccessiterator last);
Template <class Randomaccessiterator, class strictweakordering> void Partial_sort (Randomaccessiterator first,

Randomaccessiterator Middle, Randomaccessiterator last, strictweakordering comp); Template <class Inputiterator, class randomaccessiterator> Randomaccessiterator partial_sort_copy (

Inputiterator First, Inputiterator last, Randomaccessiterator Result_first, Randomaccessiterator result_last); Template <class Inputiterator, class Randomaccessiterator, class strictweakordering> Randomaccessiterator Partial_sort_copy (inputiterator First, Inputiterator last, Randomaccessiterator Result_first, RandomAccessIterator Result_last, Compare comp); 

After understanding the sort and stable_sort, it's easier to understand Partial_sort. Let's look at its purpose: There are 10 students in the class, and I want to know who is the 5 who have the lowest score. If you don't have a partial_sort, you need to sort all the people in order and then take the top 5. Now you just need to sort the score by a minimum of 5, and make the following changes to the above program:

Stable_sort (Vect.begin (), Vect.end (),less<student> ());

To be replaced by:

Partial_sort (Vect.begin (), Vect.begin () +5, Vect.end (),less<student> ());

The output is:

------before sort ...
Tom:    The
jimy: The Jessy: $
jone:
winter:77
andyer:63
Lily:
maryia:89
-----After sort ....
Bush:
jimy:
jone: $
andyer:63 Tom: The "
Mary"
Jessy:
winter:77
Lily:
maryia:89

That's a good thing to know. When the amount of data is small may not see the advantage, if it is 1 million students, I want to find the lowest score of 5 people ...
The heap ordering (heapsort) used by Partial_sort is N*log (n) in any case. If you want to use Partial_sort to achieve full ordering, you just have to let middle=last.

Partial_sort_copy is actually a combination of copy and Partial_sort. The number of sorted (copied) is [first, last] and [Result_first, result_last) the smaller interval. If the [Result_first, Result_last] interval is greater than the [first, last] interval, then the partial_sort is equivalent to the combination of copy and sort. 1.6 nth_element specifying element ordering

Nth_element a sort that is easy to read but explains rather troublesome. It is more convenient to use examples:
There are 10 students in the class, and I want to know the students who are ranked in the bottom 4th place.
If you want to meet the above requirements, you can use sort order, and then take the 4th bit (because it is from the small to the big row), the more intelligent friends will use Partial_sort, only the top 4, and then get 4th place. In fact this is you or waste, because the first two bits you do not need to sort at all, at this time, you need nth_element:

Template <class randomaccessiterator>
void Nth_element (randomaccessiterator first, Randomaccessiterator Nth,
randomaccessiterator last);

Template <class Randomaccessiterator, class strictweakordering>
void Nth_element (randomaccessiterator First, Randomaccessiterator nth,
randomaccessiterator last, strictweakordering comp);

For the above instance requirements, you only need to modify the program in 1.4 as follows:

Stable_sort (Vect.begin (), Vect.end (),less<student> ());

To be replaced by:

Nth_element (Vect.begin (), Vect.begin () +3, Vect.end (),less<student> ());

The result of the operation is:

------before sort ...
Tom:    The
jimy: The Jessy: $
jone:
winter:77
andyer:63
Lily:
maryia:89
-----After sort ....
Jone:
jimy: $
andyer:63 Jessy:   92
winter:77
Tom:    all
Lily:
maryia:89

Who's the fourth one? Andyer, this unlucky fellow. Why is begin () +3 instead of +4? I did not care when I began to write this article, and later, in ILOVEVC's reminder, I found this problem. Begin () is the first, begin () +1 is the second, ... begin () +3 of course it's the fourth one. 1.7 partition and Stable_partition

As if these two functions are not used for sorting, the ' classification ' algorithm will be more appropriate. Partition is to divide the elements of an interval into two categories according to a certain condition. Its function prototypes are:

Template <class ForwardIterator, class predicate>
ForwardIterator partition (forwarditerator first,
ForwardIterator last, predicate pred)
template <class ForwardIterator, class predicate>
ForwardIterator Stable_partition (ForwardIterator First, ForwardIterator last, 
predicate pred);

Take a look at the app: 10 students in the class, counting all the students who didn't pass (less than 60 points). You only need to replace the program in 1.4 with the following format:

Stable_sort (Vect.begin (), Vect.end (),less<student> ());

To be replaced by:

Student Exam ("pass");
Stable_partition (Vect.begin (), Vect.end (), bind2nd (less<student> (), exam));

The output is:

------before sort ...
Tom:    The
jimy: The Jessy: $
jone:
winter:77
andyer:63
Lily:
maryia:89
-----After sort ....
Jimy: Jone:--------
Tom: The
Jessy:  85
winter:77
andyer:63
Lily:
maryia:89

See, Jimy,jone, Bush (no wonder the American president is more stupid smile) failed. and using stable_partition, the relative order between the elements is unchanged. 2 Sort and Container

The standard container in STL is the main vector, list, deque, String, set, Multiset, map, Multimay, where set, Multiset, map, and Multimap all store their elements in a tree-structured manner. See: Learn the STL map, STL set data Structure Foundation. So in these containers, the elements are always orderly.
The iterator type of these containers is not a random iterator, so those sorting functions above are not available for these containers. The above sort functions are available for the following containers:

Vector
string
deque

If you define a container that also supports random iterators, there is no problem with sorting algorithms.
For the list container, the list comes with a sort member function List::sort (). It is similar to the sort in the algorithm function, but List::sort is a pointer-based sort, which means that all data movement and comparisons are implemented by pointers, so that the ordered iterator remains valid (the sort iterator in the vector is invalidated). 3 Selecting the appropriate sorting function

Why choose the right sort function. Maybe you don't care about efficiency (the efficiency here is the program run time), or you have a small amount of data, so you think it doesn't matter which function to use.
In fact, even if you do not care about efficiency, if you choose the appropriate sorting function, you will make your code easier to understand, you will make your code more extensibility, gradually develop a good habit, it is important smile.
If you've ever used qsort in C and want to know how qsort compares to them, I'll tell you that qsort and sort are the same, because they're all quick to sort. In terms of efficiency, the following sort algorithms are sorted, with efficiency from high to low (time consuming from small to large):

Partion
stable_partition
nth_element
partial_sort
sort
stable_sort

Remember, the previous translation of the effective STL article, which summarizes how to select the sorting function is very good:
To sort vectors, strings, deque, or array containers, you can choose sort or stable_sort;
If you only need to get top n elements in the vector, string, deque, or array container, the partial sort partial_sort is preferred.
For a vector, string, deque, or array container, you need to find the nth position element or you need to get top N and do not relate to the internal order of top N, Nth_element is ideal;
If you need to separate an element that satisfies a condition or does not satisfy a condition from a standard sequence container or array, you might want to use partition or stable_partition;
If you use the list container, you can use the partition and Stable_partition algorithms directly, and you can use List::sort instead of sort and stable_sort sorting. If you need to get a partial_sort or nth_element sort effect, you have to use it indirectly. As described above, there are several ways to choose.
In short, remember a word: If you want to save time, do not detours, also do not go the way unnecessary! 4 Summary

The

Discussion technology is like a bottomless pit, and it's often easy to extend another myriad of technical points. Therefore, you need to look at the problem from a global perspective, just like observing the sort algorithm in STL. In fact, there are make_heap, sort_heap and other sorting algorithms in STL. This article does not mention. In this paper, we explain the characteristics of the sorting algorithm in STL, and summarize how to choose the appropriate algorithm in the actual situation

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.