Создание нулевых указателей из пакета параметров шаблона c 11

#c #templates #metaprogramming #c 11

#c #шаблоны #метапрограммирование #c 11

Вопрос:

Я выполняю некоторое метапрограммирование, и прямо сейчас мне нужно проверить, может ли функция-член данного типа вызываться с заданным набором аргументов, поэтому я делаю что-то вроде следующего (что сильно упрощается путем удаления всего, что не важно для этой конкретной проблемы, конечно):

 template<typename T, typename... Args>
struct argument_tester {
    struct base: public T { 
        using T::my_member; 
        no my_member(...){}
    };
    typedef decltype(static_cast<base*>(0)->my_member(*static_cast<Args*...>(0))) type;
    //verify return type
};
 

Конечно, это не работает *static_cast<Args*...>(0) , поэтому мой вопрос заключается в том, есть ли какой-либо способ распаковать пакет параметров как разыменованные нулевые указатели или это тот случай, когда я должен специализироваться на каждом количестве аргументов. И, конечно, если есть способ, как я это сделаю? Я использую gcc 4.6 в случае, если это имеет значение для того, что возможно, а что нет.

Комментарии:

1. Знаете ли вы о std::declval ?

2. @R. Мартиньо Фернандес: я этого не делал, но какая разница в этой ситуации

3. Я думаю, что в этом коде есть ошибка, base которая не используется, и я думаю, что она должна была использоваться вместо T in static_cast<T*>(0) .

4. @Grizzly: немного, но вам не нужно будет использовать статические приведения и разыменовывать нулевые указатели. Просто информирование людей о новых инструментах 🙂

5. Использование std::declval делает код существенно более чистым (например) и позволяет указывать Tamp; в качестве аргумента. На данный момент, если один из параметрических аргументов it Tamp; , то Tamp;* произойдет сбой…

Ответ №1:

« ... Оператор» распаковки» может быть размещен вне выражения, и в этом случае выражение расширяется.

Таким образом, я думаю, решение было (*static_cast<Args*>(0))... бы следующим.

РЕДАКТИРОВАТЬ: следуя подсказке Р. Мартиньо Фернандеса

 typedef decltype(std::declval<base>().my_member(std::declval<Args>()...)) type;