Last time, we reviewed very briefly about what *is* STL. In this Chapter of the series, we will be talking about the algorithms it provides, and their value in CP (speaking of "value", some functions may be almost absolutely useless in CP due to another feature or some reason). We are not going to talk about using ranges for now, they are bound for another article. In Section 1 of Chapter 1, we will be talking about Non-modifying sequence operations. (I suggest that you read this article side by side with Cppreference, I get a lot of ideas and knowledge there, and the Sections are divided for convenience in reading side by side.)

`all_of`

, `none_of`

, `any_of`

These three functions are quite straightforward, and have $$$O(n)$$$ time complexity (if the passed function has $$$O(1)$$$ time complexity). They may be useful in many situations, but I have not found a real usage example yet.

`for_each`

, `for_each_n`

(C++17)

These two functions apply a certain (unary) function to each element of a container. Their time complexity is, quite clearly, $$$O(n)$$$, considering the case when the function applied takes $$$O(1)$$$ time. However, the former has been useless in my case, as range-based for statements were sufficient for me. **The latter, though, may be very useful, and is not replaced by the range-based for statement.**

`count`

, `count_if`

These two functions count the number of elements in the container that, for the former, matches a value, and for the latter, meets a condition. Their time complexity is $$$O(n)$$$, assuming the function takes $$$O(1)$$$ time. Both are useful in my opinion, **but the latter is much more important in CP.** This is because CP asks for the amount of values meeting a certain condition, more frequently than asking for a certain value.

`mismatch`

This function iterates through two ranges of iterators and then returns the first position where the values differ or the function passed returns a falsy value (which is 0). The time complexity is $$$O(n)$$$ assuming the function passed (`==`

by default) takes $$$O(1)$$$ time. **Now this function is very important**, in the sense that we can compare two ranges and check if all elements in range A meets a condition relative to range B. **We can even check if a range is a palindrome with this function**, by passing the iterators and reverse iterators to this function, and checking if the function finished at each ends. Do note that this function returns a pair of iterators, and this in turn could give an advantage over using the `equal`

function (which only returns a boolean value).

`find`

, `find_if`

, `find_if_not`

I am not going to talk too much about these functions in this article, their uses/time complexity/etc are too trivial and well-known. However, do note that, for the same reason stated about `count_if`

, **the latter two have relative importance over the former one.**

`find_end`

, `search`

In my opinion, I thought `find_end`

would have been better named as `search_end`

, as `search`

does the same thing, except `find_end`

searches for the last occurrence while `search`

searches for the first. These functions by default searches naively, so it has an $$$O(nm)$$$ time complexity. **Do use KMP when needed**; naive (and Boyer-Moore in its worst case) searching methods are too slow for CP.

`find_first_of`

This function finds the first occurrence of any value existing in a certain set (represented with a range) in a range. For example, you can find the first occurrence of any value in {2, 4, 6, 8} in a vector. This function has an $$$O(Sn)$$$ time complexity, and therefore **when looking for exact matches it can be replaced with the tree-based/hash-based containers** for $$$O(log(S)n)$$$, $$$O(n)$$$ time complexity correspondingly. However these container-based methods might not do very well **when in need of applying a function to compare the elements** (trust me, traversing these containers are $$$O(n)$$$ but it is a pain due to cache issues), so **in this case this function may be helpful.**

`adjacent_find`

This function compares adjacent values, and returns the first position where the values are identical, or meet a condition when passed a function. This function has $$$O(n)$$$ time complexity, assuming the comparison function has $$$O(1)$$$ time complexity. I have found usage of this function in 1713B - Optimal Reduction, consider the following explanation as a solution for the problem.

**Explanation for 1713B**

As shown in the explanation above, `adjacent_find`

**has great strength in comparing adjacent elements inplace, without making a difference array**. For this reason, I consider this function very important in CP.

`search_n`

This function finds the first point where $$$n$$$ consecutive elements in a row exist, which are same with the given argument (or meets a condition compared to it). This may be useful in problems such as when you need to find $$$k$$$ consecutive positive numbers. **Do remember though, that the given function takes the elements on the left argument and the argument in the right argument**.

In this article, we reviewed the Non-modifying sequence operation functions in the Algorithm category of STL. In the next section, we will be reviewing the Modifying sequence operation functions.

Auto comment: topic has been updated by chromate00 (previous revision, new revision, compare).Auto comment: topic has been updated by chromate00 (previous revision, new revision, compare).