Рекурсивный шаблон с переменным числом параметров

Тема в разделе "LANGS.C", создана пользователем Rel, 18 авг 2011.

  1. Rel

    Rel Well-Known Member

    Публикаций:
    2
    Регистрация:
    11 дек 2008
    Сообщения:
    5.323
    размышляю над такой задачкой... есть вот такой код (C++0x):
    Код (Text):
    1. #include <stdio.h>
    2.  
    3. template <uint32_t ... Ints> struct   Integers { static uint32_t Value[sizeof...(Ints)]; enum { Length = sizeof...(Ints) }; };
    4. template <uint32_t ... Ints> uint32_t Integers<Ints ...>::Value[sizeof...(Ints)] = { Ints * 10 ... };
    5.  
    6. int main()
    7. {
    8.     typedef Integers<10, 20, 30> Type;
    9.     for(uint32_t t = 0; t < Type::Length; t++)
    10.     { printf("%d\n", Type::Value[t]); }
    11.  
    12.     return 0;
    13. }
    то есть в зависимости от параметров шаблона числа (параметры шаблона) заталкиваются в массив умноженными на десять (на выходе: 100, 200, 300)... никак не могу понять, как сделать шаблон так, чтобы каждое число, помещаемое в массив зависело от значения предыдущего... например текущее число суммировалось бы с предыдущим, то есть для параметров шаблона <10, 20, 30> на выходе было бы 10, 30, 60... надо видимо как-то описать шаблон template <uint32_t Head, uint32_t ... Tail> uint32_t Integers<Head, Tail ...>::Value[sizeof...(Ints) + 1] = { ... }, но не приходит в голову, что поставить в фигурные скобки, чтобы это было понятно компилятору... есть какие-нить идеи? и еще можно ли как-нибудь внести зависимость от позиции элемента, например Ints * Idx * 10, где Idx - номер параметра?
     
  2. 100gold

    100gold New Member

    Публикаций:
    0
    Регистрация:
    26 фев 2010
    Сообщения:
    165
    Можно попробовать внутри класса объявить consexpr функцию, в которой объявить статический массив чисел, пока что без изменений. Функиця по переданному индексу будет вычислять реально требуемое значение массива. Теперь, чтобы сформировать итоговый массив надо вызвать имеющуюся функцию для каждого индекса массива.

    К сожалению код попробовать привести не могу -студия ещё неосилила constexpr и variadic templates
     
  3. srm

    srm New Member

    Публикаций:
    0
    Регистрация:
    14 июн 2011
    Сообщения:
    189
    Rel, чем компилите такой код?
     
  4. Rel

    Rel Well-Known Member

    Публикаций:
    2
    Регистрация:
    11 дек 2008
    Сообщения:
    5.323
    gcc 4.6.1 под линуксами и соответственно мингв с той же версией гцц под виндой...

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

    нашел решение подобной задачи в интернете... тут реализовано "шифрование строк" на этапе компиляции и каждый символ зависит от предыдущего: http://www.raptorfactor.com/improved-compile-time-string-encryption/, но чет я не могу код понять)))
     
  5. 100gold

    100gold New Member

    Публикаций:
    0
    Регистрация:
    26 фев 2010
    Сообщения:
    165
    Вот кажется там и описан способ сделать список. Кажется это должно быть как-то так
    Код (Text):
    1. template<uint32_t last>
    2. struct EndList
    3. {
    4.    struct EndMarker {};
    5.    enum
    6.    {
    7.       first = last;
    8.    }
    9.    typedef EndMarker Tail;
    10. };
    11. tempplate<uint32_t first, uint32_t ..Ints>
    12. struct MakeList
    13. {
    14.    enum
    15.    {
    16.       head = first;
    17.    }
    18.    typedef _IF<sizeof...(Ints)>1, MakeList<Ints...>, EndList<Ints...> > Tail;
    19. };
    Проверить не могу, поэтому извиняюсь за возможный бред )
     
  6. srm

    srm New Member

    Публикаций:
    0
    Регистрация:
    14 июн 2011
    Сообщения:
    189
    Вместе с развитием С++ нужно изобретать лекарство от смерти. Почему не придумать простой и понятный интерфейс для создания статических массивов?