Как использовать for_each для вывода на cout? - PullRequest
17 голосов
/ 11 ноября 2010

Есть ли более простой способ сделать это?

for_each(v_Numbers.begin(), v_Numbers.end(), bind1st(operator<<, cout));

Без явного цикла for, если это возможно.

РЕДАКТИРОВАТЬ:

Как это сделать для std::cin с std::vector, если это возможно?(Как читать только n элементов)?

Ответы [ 5 ]

30 голосов
/ 11 ноября 2010

Вы можете достичь этого, используя std::copy в std::ostream_iterator:

std::vector<int> v_Numbers; // suppose this is the type
// put numbers in
std::copy(v_Numbers.begin(), v_Numbers.end(),
          std::ostream_iterator<int>(cout));

Было бы еще лучше, если бы вы добавили суффикс:

std::copy(v_Numbers.begin(), v_Numbers.end(),
          std::ostream_iterator<int>(cout, "\n"));

Это предполагает, что ваш контейнер - vector<int>, поэтому вам придется заменить эту часть на соответствующий тип.

Редактировать относительно чтения ввода:

И наоборот, вы можете копировать из диапазона std::istream_iterator в vector, используя std::back_inserter:

std::vector<int> v_Numbers;
std::copy(std::istream_iterator<int>(cin), std::istream_iterator<int>(),
          std::back_inserter(v_Numbers));

Если вы хотите прочитать только n элементов, посмотрите на этот вопрос .

9 голосов
/ 11 ноября 2010

Другой вариант - Boost.Lambda .

for_each(v.begin(), v.end(), cout << boost::lambda::_1);
7 голосов
/ 11 ноября 2010

Да, но вы должны использовать алгоритм std :: copy:

#include <iostream>
#include <iterator>
#include <vector>

int main()
{
    std::vector<int> a;
    // fill a...
    std::copy(a.begin(), a.end(), std::ostream_iterator<int>(std::cout));
}
4 голосов
/ 02 мая 2017

Да, используя лямбда-выражение (C ++ 11), мы можем встроить печать каждого элемента контейнера STL в cout.

#include <iostream>   // cout
#include <vector>     // vector
#include <algorithm>  // for_each
#include <iterator>   // istream_iterator
using namespace std;

int main()
{
   std::vector<int> v(10,2);
   std::for_each(v.begin(), v.end(), [](int i)->void {std::cout << i <<endl;});
   return 0;
}

Для чтения значений "n" из cin в вектор,

 int main()
 {
   std::vector<int> v;

   int elementsToRead;
   cin>>elementsToRead;  // Number of elements to copy

   // Reading from istream
   std::istream_iterator<int> ii2(std::cin);
   std::copy_n(ii2, elementsToRead, std::back_inserter(v));

   // printing updated vector
   std::for_each(v.begin(), v.end(), [](int i)->void {cout << i <<endl;});

   return 0;
}

(или) с помощью лямбда-выражения

std::for_each(std::istream_iterator<int>(cin),std::istream_iterator<int>(),[&v](int i)->void { v.push_back(i);});

Чтобы узнать больше о лямбда-выражении @ Что такое лямбда-выражение в C ++ 11?

0 голосов
/ 11 ноября 2010

Не всегда уместно в корпоративном коде, но для перечисления опций - если вы действительно находите другие решения for_each / std :: copy и т. Д. Слишком многословными, вы можете написать:

std::ostream& operator(std::ostream& os, const std::vector<My_Type>& v)
{
     // pick one of the other implementations for here...
    std::copy(std::istream_iterator<My_Type>(os), std::istream_iterator<My_Type>(),   
          std::back_inserter(v_Numbers));   
}

Гораздо приятнее, если вы достаточно хорошо воспитаны (;-p), чтобы перегружать только ваше конкретное создание экземпляра вектора (что требует, чтобы My_Type был больше, чем typedef, чтобы сказать int, хотя создать шаблонный класс не сложно. создавать новые типы, обертывающие произвольный тип). В противном случае, если кто-то сделает то же самое в другом месте в вашем модуле перевода, потоковая передача может стать неоднозначной.

...