Модифицирующие алгоритмы. Преобразование и объединение элементов

   
На этом шаге мы рассмотрим использование первой формы алгоритма transform().

   
Алгоритм transform() существует в двух вариантах:

  • первая форма вызывается с четырьмя аргументами и преобразует элементы при копировании из источника в
    приемник (то есть модификация осуществляется одновременно с копированием);
  • вторая форма вызывается с пятью аргументами, она объединяет элементы из двух источников и записывает
    результат в приемник.

Преобразование элементов

   
Общий вид первой формы алгоритма transform() следующий:

  OutputIterator
  transform (InputIterator sourceBeg, InputIterator sourceEnd,
             Outputlterator destBeg,
             UnaryFunc op)

   
Данный алгоритм вызывает предикат op(elem) для каждого элемента в исходном интервале [sourceBeg,sourceEnd)
и записывает каждый результат ор в приемный интервал, начиная с destBeg:


Рис.1. Схема выполнения алгоритма

   
Возвращает позицию за последним преобразованным элементом в приемном интервале (то есть позицию первого
элемента, не перезаписанного в результате операции).

   
Перед вызовом необходимо убедиться в том, что приемный интервал имеет достаточный размер, или использовать
итераторы вставки.

   
Позиции sourceBeg и destBeg могут быть идентичными. Это означает, что алгоритм transform(),
как и for_each(), может использоваться для модификации элементов внутри интервала. Пример для алгоритма
for_each() приведен на 257 шаге.

   
Чтобы заменить заданной величиной элементы, удовлетворяющие критерию, используйте алгоритм replace().

   
Сложность линейная (numberOfElements присваиваний).

   
Следующая программа демонстрирует использование данной формы алгоритма transform():

//---------------------------------------------------------------------------

#include <vcl.h>
#include <iterator>
#include "algostuff.hpp"

#include <conio.h> //необходимо для getch()

#pragma hdrstop

//---------------------------------------------------------------------------

#pragma argsused
using namespace std;

std::string ToRus(const std::string &in)
{
  char *buff = new char [in.length()+1];
  CharToOem(in.c_str(),buff);
  std::string out(buff);
  delete [] buff;
  return out;
}


int main()
{
  vector<int> coll1;
  list<int> coll2;

  INSERT_ELEMENTS(coll1,1,9);
  PRINT_ELEMENTS(coll1,"1-я коллекция:\n");

  // Изменение знака всех элементов coll1
  transform (coll1.begin(), coll1.end(),      // Источник
             coll1.begin(),                   // Приемник
             negate<int>());                  // Операция
  PRINT_ELEMENTS(coll1,"Поменяли знак:\n");

  // Копирование элементов coll1, умноженных на 10, в coll2
  transform (coll1.begin(), coll1.end(),      // Источник
             back_inserter(coll2),            // Приемник
             bind2nd(multiplies<int>(),10));  // Операция
  PRINT_ELEMENTS(coll2,"2-я коллекция (умножили на 10):\n");

  // Вывод элементов coll2 с изменением знака и в обратном порядке
  cout << ToRus("2-я коллекция (изменили знак и вывели в обратном порядке):\n");
  transform (coll2.rbegin(), coll2.rend(),    // Источник
             ostream_iterator<int>(cout," "), // Приемник
             negate<int>());                  // Операция
  cout << endl;


  getch();
  return 0;
}

//---------------------------------------------------------------------------

Текст этого примера можно взять здесь.

   
Программа выводит следующий результат:


Рис.2. Результат работы приложения

   
На следующем шаге мы рассмотрим вторую форму алгоритма transform().



Вы можете оставить комментарий, или Трекбэк с вашего сайта.

Оставить комментарий