stl 拷贝容器元素到另一容器中

1、std::copy、std::copy_if

描述:
       拷贝容器指定范围的元素到另一容器中。
       复制 [first, last) 所定义的范围中的元素到始于 d_first 的另一范围。
       复制范围 [first, last) 中的所有元素,从首元素开始逐次到末元素。
       仅复制谓词 pred 对其返回 true 的元素。

函数定义:

template< class InputIt, class OutputIt >
OutputIt copy( InputIt first, InputIt last, OutputIt d_first );

template< class InputIt, class OutputIt >
constexpr OutputIt copy( InputIt first, InputIt last, OutputIt d_first );

template< class InputIt, class OutputIt, class UnaryPredicate >
OutputIt copy_if( InputIt first, InputIt last,
                  OutputIt d_first,
                  UnaryPredicate pred );

template< class InputIt, class OutputIt, class UnaryPredicate >
constexpr OutputIt copy_if( InputIt first, InputIt last,
                            OutputIt d_first,
                            UnaryPredicate pred );

参数:
       first, last - 要复制的元素范围
       d_first - 目标范围的起始。
       pred - 对所要求的元素则返回 ​true 的一元谓词。

返回值:
       目标范围中最后复制元素的下个元素的输出迭代器。

可能的实现:

template<class InputIt, class OutputIt>
OutputIt copy(InputIt first, InputIt last, 
              OutputIt d_first)
{
     
    while (first != last) {
     
        *d_first++ = *first++;
    }
    return d_first;
}
template<class InputIt, class OutputIt, class UnaryPredicate>
OutputIt copy_if(InputIt first, InputIt last, 
                 OutputIt d_first, UnaryPredicate pred)
{
     
    while (first != last) {
     
        if (pred(*first))
            *d_first++ = *first;
        ++first;
    }
    return d_first;
}

示例:

int main()
{
     
	std::string s1 = "Hello world!";
	std::string s2, s3;

	std::copy(s1.begin(), s1.end(),std::back_inserter(s2));
	std::cout << s2 << std::endl;//Hello world!

	std::copy_if(s1.begin(), s1.end(), std::back_inserter(s3),
		[](char c) {
      return c == 'l' || c == 'o'; });//只拷贝l和o元素
	std::cout << s3 << std::endl;//llool
}

2、std::remove_copy,std::remove_copy_if

描述:
       拷贝容器元素,忽略满足判别条件的元素。
       复制来自范围 [first, last) 的元素到始于 d_first 的另一范围,省略满足特定判别标准的元素。源与目标范围不能重叠。
       忽略所有等于 value 的元素。
       忽略所有谓词 p 对其返回 true 的元素。

函数定义:

template< class InputIt, class OutputIt, class T >
OutputIt remove_copy( InputIt first, InputIt last, OutputIt d_first,
                      const T& value );
                      
template< class InputIt, class OutputIt, class T >
constexpr OutputIt remove_copy( InputIt first, InputIt last, OutputIt d_first,
                                const T& value );

template< class InputIt, class OutputIt, class UnaryPredicate >
OutputIt remove_copy_if( InputIt first, InputIt last, OutputIt d_first,
                         UnaryPredicate p );

template< class InputIt, class OutputIt, class UnaryPredicate >
constexpr OutputIt remove_copy_if( InputIt first, InputIt last, OutputIt d_first,
                                   UnaryPredicate p );

参数:
       first, last - 要复制的元素范围
       d_first - 目标范围的起始。
       value - 不复制的元素的值

返回值:
       返回最后被复制元素的迭代器。

可能的实现:

template<class InputIt, class OutputIt, class T>
OutputIt remove_copy(InputIt first, InputIt last,
                     OutputIt d_first, const T& value)
{
     
    for (; first != last; ++first) {
     
        if (!(*first == value)) {
     
            *d_first++ = *first;
        }
    }
    return d_first;
}
template<class InputIt, class OutputIt, class UnaryPredicate>
OutputIt remove_copy_if(InputIt first, InputIt last,
                        OutputIt d_first, UnaryPredicate p)
{
     
    for (; first != last; ++first) {
     
        if (!p(*first)) {
     
            *d_first++ = *first;
        }
    }
    return d_first;
}

示例:

int main()
{
     
	std::string s1 = "Hello world!";
	std::string s2, s3;

	std::remove_copy(s1.begin(), s1.end(),std::back_inserter(s2),' ');//忽略空格元素
	std::cout << s2 << std::endl;//Helloworld!

	std::remove_copy_if(s1.begin(), s1.end(), std::back_inserter(s3),
		[](char c) {
      return c == 'l' || c == 'o'; });//忽略l和o元素
	std::cout << s3 << std::endl;//He wrd!
}

3、std::copy_n

描述:
       根据元素个数拷贝容器到另一容器中。
       若 count>0 ,则准确复制来自始于 first 的范围的 count 个值到始于 result 的范围。

函数定义:

template< class InputIt, class Size, class OutputIt >
OutputIt copy_n( InputIt first, Size count, OutputIt result );

template< class InputIt, class Size, class OutputIt >
constexpr OutputIt copy_n( InputIt first, Size count, OutputIt result );

参数:
       first - 复制来源的元素范围起始
       count - 要复制的元素数
       result - 目标范围起始

返回值:
       若 count>0 则返回目标范围中最后被复制元素后一元素的迭代器,否则为 result 。

可能的实现:

template< class InputIt, class Size, class OutputIt>
OutputIt copy_n(InputIt first, Size count, OutputIt result)
{
     
    if (count > 0) {
     
        *result++ = *first;
        for (Size i = 1; i < count; ++i) {
     
            *result++ = *++first;
        }
    }
    return result;
}

示例:

int main()
{
     
	std::string s1 = "Hello world!";
	std::string s2;

	std::copy_n(s1.begin(), 4,std::back_inserter(s2));
	std::cout << s2 << std::endl;//Hell
}

4、std::set_difference

描述:
       计算两个集合的差集。
       复制来自已排序范围 [first1, last1) 并且不在已排序范围 [first2, last2) 中找到的元素到始于 d_first 的范围。结果范围亦已排序。
       用 operator< 比较元素,而范围必须对于相同者排序。
       用给定的二元比较函数 comp 比较元素,而范围必须对于相同者排序。

函数定义:

template< class InputIt1, class InputIt2, class OutputIt >
OutputIt set_difference( InputIt1 first1, InputIt1 last1,
                         InputIt2 first2, InputIt2 last2,
                         OutputIt d_first );
                         
template< class InputIt1, class InputIt2, class OutputIt >
constexpr OutputIt set_difference( InputIt1 first1, InputIt1 last1,
                                   InputIt2 first2, InputIt2 last2,
                                   OutputIt d_first );

template< class InputIt1, class InputIt2,
          class OutputIt, class Compare >
OutputIt set_difference( InputIt1 first1, InputIt1 last1,
                         InputIt2 first2, InputIt2 last2,
                         OutputIt d_first, Compare comp );

template< class InputIt1, class InputIt2,
          class OutputIt, class Compare >
constexpr OutputIt set_difference( InputIt1 first1, InputIt1 last1,
                                   InputIt2 first2, InputIt2 last2,
                                   OutputIt d_first, Compare comp );

参数:
       first1, last1 - 要检验的元素范围
       first2, last2 - 要搜索的元素范围
       d_first - 目标范围的起始
       comp - 比较函数对象(即满足比较 (Compare) 概念的对象),若第一参数小于(即先序于)第二参数则返回 ​true。

返回值:
       返回构造的范围的尾后迭代器。

可能的实现:

template<class InputIt1, class InputIt2, class OutputIt>
OutputIt set_difference(InputIt1 first1, InputIt1 last1,
                        InputIt2 first2, InputIt2 last2,
                        OutputIt d_first)
{
     
    while (first1 != last1) {
     
        if (first2 == last2) return std::copy(first1, last1, d_first);
 
        if (*first1 < *first2) {
     
            *d_first++ = *first1++;
        } else {
     
            if (! (*first2 < *first1)) {
     
                ++first1;
            }
            ++first2;
        }
    }
    return d_first;
}
template<class InputIt1, class InputIt2,
         class OutputIt, class Compare>
OutputIt set_difference( InputIt1 first1, InputIt1 last1,
                         InputIt2 first2, InputIt2 last2,
                         OutputIt d_first, Compare comp)
{
     
    while (first1 != last1) {
     
        if (first2 == last2) return std::copy(first1, last1, d_first);
 
        if (comp(*first1, *first2)) {
     
            *d_first++ = *first1++;
        } else {
     
            if (!comp(*first2, *first1)) {
     
                ++first1;
            }
            ++first2;
        }
    }
    return d_first;
}

示例:

#include 
#include 
#include 
#include 
 
int main() {
     
    std::vector<int> v1 {
     1, 2, 5, 5, 5, 9};
    std::vector<int> v2 {
     2, 5, 7};
    std::vector<int> diff;
 
    std::set_difference(v1.begin(), v1.end(), v2.begin(), v2.end(), 
                        std::inserter(diff, diff.begin()));
 
    for (auto i : v1) std::cout << i << ' ';
    std::cout << "minus ";
    for (auto i : v2) std::cout << i << ' ';
    std::cout << "is: ";
 
    for (auto i : diff) std::cout << i << ' ';
    std::cout << '\n';
}
/*
输出:
1 2 5 5 5 9 minus 2 5 7 is: 1 5 5 9
*/

5、std::unique_copy

描述:
       拷贝无连续相同的元素到另一容器中。
       从范围 [first, last) 复制元素到始于 d_first 的另一范围,使得无连续的相等元素。只复制每组等价元素的首元素。
       用 operator== 比较元素。
       用给定的二元谓词 p 比较元素。

函数定义:

template< class InputIt, class OutputIt >
OutputIt unique_copy( InputIt first, InputIt last,
                      OutputIt d_first );

template< class InputIt, class OutputIt >
constexpr OutputIt unique_copy( InputIt first, InputIt last,
                                OutputIt d_first );

template< class InputIt, class OutputIt, class BinaryPredicate >
OutputIt unique_copy( InputIt first, InputIt last,
                      OutputIt d_first, BinaryPredicate p );

template< class InputIt, class OutputIt, class BinaryPredicate >
constexpr OutputIt unique_copy( InputIt first, InputIt last,
                                OutputIt d_first, BinaryPredicate p );

参数:
       first, last - 要处理的元素范围
       d_first - 目标范围的起始
       policy - 所用的执行策略。细节见执行策略。
       p - 若元素应被当做相等则返回 ​true 的二元谓词。

返回值:
       返回最后被写入元素后一元素的输出迭代器。

示例:

int main()
{
     
	std::string s1 = "The      string    with mmany       sspaces!";

	std::string s2, s3;
	std::unique_copy(s1.begin(), s1.end(), std::back_inserter(s2));
	std::cout << s2 << std::endl;//The string with many spaces!

	std::unique_copy(s1.begin(), s1.end(), std::back_inserter(s3),
		[](char c1, char c2) {
      return c1 == ' ' && c2 == ' '; });
	std::cout << s3 << std::endl;//The string with mmany sspaces!
}

6、std::reverse_copy

描述:
       创建一个范围的逆向副本。
       复制来自范围 [first, last) 的元素到始于 d_first 的新范围,使得新范围中元素以逆序排列。

函数定义:

template< class BidirIt, class OutputIt >
OutputIt reverse_copy( BidirIt first, BidirIt last, OutputIt d_first );

template< class BidirIt, class OutputIt >
constexpr OutputIt reverse_copy( BidirIt first, BidirIt last, OutputIt d_first );

参数:
       first, last - 要复制的元素范围
       d_first - 新范围的起始

返回值:
       返回最后被复制元素后一元素的迭代器。

可能的实现:

template<class BidirIt, class OutputIt>
OutputIt reverse_copy(BidirIt first, BidirIt last, OutputIt d_first)
{
     
    while (first != last) {
     
        *(d_first++) = *(--last);
    }
    return d_first;
}

示例:

int main()
{
     
	std::string s1 = "Hello world!";

	std::string s2;
	s2.resize(12);
	std::reverse_copy(s1.begin(),s1.end(),s2.begin());
	std::cout << s2 << std::endl;//!dlrow olleH

	//std::string s3;
	//std::reverse_copy(s1.begin(), s1.end(), s3.begin());//错误
	//std::reverse_copy(s1.begin(), s1.end(), std::back_inserter(s3));//正确
	//std::reverse_copy(s1.begin(), s1.end(), std::inserter(s3,s3.begin()));//正确
	//std::cout << s3 << std::endl;//!dlrow olleH
}

7、std::copy_backward

描述:
       按从后往前的顺序复制一个范围内的元素到另一容器中。
       复制来自 [first, last) 所定义范围的元素,到终于 d_last 的范围。以逆序复制元素(首先复制末元素),但保持其相对顺序。

函数定义:

template< class BidirIt1, class BidirIt2 >
BidirIt2 copy_backward( BidirIt1 first, BidirIt1 last, BidirIt2 d_last );

template< class BidirIt1, class BidirIt2 >
constexpr BidirIt2 copy_backward( BidirIt1 first, BidirIt1 last, BidirIt2 d_last );

参数:
       first, last - 要复制的元素范围
       d_last - 目标范围的结尾。

返回值:
       返回最后复制元素的迭代器。

可能的实现:

template< class BidirIt1, class BidirIt2 >
BidirIt2 copy_backward(BidirIt1 first, BidirIt1 last, BidirIt2 d_last)
{
     
    while (first != last) {
     
        *(--d_last) = *(--last);
    }
    return d_last;
}

示例:

int main()
{
     
	std::string s1 = "Hello world!";

	std::string s2 = "Hello ";
	s2.resize(18);
	std::copy_backward(s1.begin(),s1.end(),s2.end());
	std::cout << s2 << std::endl;//Hello Hello world!
}

你可能感兴趣的:(stl)