C ++ 0x вложенные списки инициализаторов - PullRequest
6 голосов
/ 30 апреля 2011

Я хотел бы использовать новую функцию списка инициализаторов C ++ 0x для инициализации std :: vector с определенным временем компиляции элементов для нового API, над которым я сейчас работаю.Примерно так:

template<int n>
std::initializer_list<std::string> duplicate(std::string s) {
  // return s duplicated n times
  return { s, s, s };
}

std::vector<std::string> v = { "foo",  duplicate<3>("bar") };

У вас есть идеи, как этого добиться?Это вообще возможно?Я знаю, что мне нужно будет использовать TMP и рекурсию, чтобы создать список дублированных строк и, наконец, каким-то образом получить к нему доступ через константу (например, enum).Но, похоже, я даже не могу вложить такой список инициализаторов.

1 Ответ

8 голосов
/ 30 апреля 2011

Вы не можете вкладывать списки инициализаторов для их расширения, а также не можете добавлять / объединять их.Они - лишь немного синтаксического сахара для доступа к массиву размера компиляции.Даже копирование initializer_lists не копирует их элементы.Самое главное, это означает, что вы не можете использовать возвращаемое значение дубликата!Указанный массив уничтожается при возврате функции в 8.5.4p6 в N3290:

Время жизни массива такое же, как и у объекта initializer_list.

(В операторе return создается временный объект, а затем возвращается по значению. Даже если исключено копирование, все остальные семантики копирования не изменяются.)

Сравните, например, с созданным здесь временным initializer_list, которыйзатем переданный в ctor и уничтоженный после инициализации объекта, в тот же момент все другие временные объекты в том же полном выражении (если они были) будут уничтожены:

vector<string> v {"foo"};

Вместо манипулирования списками инициализатора, используйте метод vector для вставки N копий:

v.insert(v.end(), 3, "bar");
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...