Мне нравится больше разбираться в шаблонах. Я попытался написать свою функцию, которая показывает каждый элемент контейнера.

void show_element(int i){
std::cout << i << endl;
}

int main(){

int dataarr[5]={1,4,66,88,9};
vector<int> data(&daten[0],&daten[0]+5);

std::for_each(data.begin(),data.end(),show_element) 

...

Моя функция show_element еще не является универсальной. Как мне его написать, чтобы я мог использовать его для разных типов контейнеров?

template <typename T>
using type = typename T::value_type;
void show_element(type i){ //type i must be sthg like *data.begin()
std::cout << i << endl;
}

Большое спасибо

1
Suslik 30 Окт 2015 в 12:07

3 ответа

Лучший ответ

Вместо функции более гибко использовать класс. В этом случае вы можете передать функциональному объекту дополнительные аргументы.

Например, вы можете указать поток, в котором вы собираетесь выводить элементы, или разделитель, который будет разделять элементы в потоке.

Класс может выглядеть следующим образом

#include <iostream>
#include <string>
#include <vector>
#include <algorithm>

template <typename T>
class show_elements
{
public:
    show_elements( const std::string &separator = " ", std::ostream &os = std::cout ) 
        : separator( separator ), os( os ) {}
    std::ostream & operator ()( const T &value ) const
    {
        return os << value << separator;
    }
protected:
    std::string separator;
    std::ostream &os;
};    

int main()
{
    int arr[] = { 1, 4, 66, 88, 9 };    
    std::vector<int> v( arr, arr + sizeof( arr ) / sizeof( *arr ) );

    std::for_each( v.begin(), v.end(), show_elements<int>() );
    std::cout << std::endl;
}

Вывод программы

1 4 66 88 9
1
Vlad from Moscow 30 Окт 2015 в 09:43

Другой простой способ - использовать цикл for на основе диапазона.

for(auto& element : container) {
    cout<<element<<endl;
}
0
William Chan 30 Окт 2015 в 10:58

Изменить на:

template <typename T>
void show_element(T const &i) { std::cout << i << std::endl; }

for_each применяет данную функцию (например, show_element) к результату разыменования каждого итератора в диапазоне [first, last) по порядку. Таким образом, вам не нужно брать value_type контейнера.

Также в С ++ 14 и выше вы можете определить общую лямбду:

auto show_element = [](auto const &i) { std::cout << i << std::endl; };

И используйте его как:

int arr[] = {1, 4, 66, 88, 9};
std::vector<int> data(arr, arr + sizeof(arr) / sizeof(int));
std::for_each(arr, arr + sizeof(arr) / sizeof(int), show_element);

LIVE DEMO

3
101010 30 Окт 2015 в 09:20