Может ли лямбда-выражение быть понижено до C++ 98

Недавно у меня возникла проблема с необходимостью интеграции кода C++ 11, написанного с лямбда-выражением, в старую базу кода, которая поддерживает только компилятор C++ 98. Я выяснил пару возможных эквивалентов лямбды, таких как макрос, функтор или указатель на функцию. Но, похоже, все они ограничены при переводе лямбды с захватом. Например, простая универсальная функция с обратным вызовом:

template <class Fn>  
void ForEachObject(Fn fn)  
{  
    for (uint i = 0; i < objectCount; i++)  
    {  
        fn(i, address + i * objectSize);  
    }  
}

и типичный абонент будет делать что-то вроде:

uint attributes = 0x0030;
....
ForEachObject([=](uint index, void * objectAddress)
{
    if ((ObjectInfo(index) & attributes) != 0)
    {
        fn(index, objectAddress);
    }
});

Примечание атрибуты здесь выходят за рамки лямбды. Есть ли еще способ повторного использования для каждой логики без лямбды? Или я должен переписать логику на каждом таком звонящем?

2 ответа

Решение

С функтором:

struct Functor
{
    explicit Functor(uint attributes) : attributes(attributes) {}
    void operator () (uint index, void * objectAddress) const
    {
        if ((ObjectInfo(index) & attributes) != 0)
        {
            fn(index, objectAddress);
        }
    }
    uint attributes;
};

А потом позвони

uint attributes = 0x0030;
// ....
ForEachObject(Functor(attributes));

Для каждой другой лямбды вы должны написать функтор. Вам не нужно изменять ForEachObject

Может ли выражение Lamda быть понижено до C++ 98

Нет, они не могут. Предыдущие стандарты C++11 не имеют понятия о лямбда-синтаксисе.

Хотя есть суррогаты, доступные как boost::lambda

Вы можете предоставить классы стиля функтора, переопределяя оператор вызова (<return_type> operator()(<args>);), чтобы обеспечить такой же эффект, как указано в другом ответе.

Другие вопросы по тегам