объявление переменной в функции, возвращающей спецификатор типа c ++ type

Я пробовал codefights.com и заметил, что кто-то ответил на вопрос, который включал в себя передачу всех самых длинных строк в векторе:

std::vector<std::string> r, allLongestStrings(std::vector<std::string> a) {
int b=0;
for (s:a) if (s.size()>b) b=s.size();
for (s:a) if (s.size()==b) r.push_back(s);
return r;
}

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

2

Решение

Глядя на ссылка (Децл-спецификатор-сл), Я не вижу, как можно было бы объявить возвращаемую переменную перед именем функции.

С C ++ 14 вы можете использовать auto ключевое слово для удаления повторяющегося упоминания типа возвращаемого значения:

auto allLongestStrings( const std::vector<std::string>& a ) {
std::vector<std::string> r;
std::size_t b = 0;
for( const auto& s : a ) if( s.size() > b ) b = s.size();
for( const auto& s : a ) if( s.size() == b ) r.push_back( s );
return r;
}

Я исправил некоторые другие вещи кода:

  • повысить эффективность, объявить параметр a как постоянная ссылка, поэтому он не будет скопирован
  • объявлять b как std::size_t соответствовать типу возвращаемого значения std::vector::size()
  • в цикле range-for необходим спецификатор типа (даже если он auto); добавлена ​​постоянная ссылка для эффективности

Живая демоверсия.

1

Другие решения

Кажется, что смешанное объявление переменной / функции в порядке, хотя gcc жалуется, что определения функции там не должно быть, но я думаю, что это нормально в глобальной области видимости. Но это допустимый синтаксис на 100% даже в неглобальной области, если не дано определение функции. Это объявление является обычным объявлением нескольких элементов одного и того же начального типа. Например, мы можем объявить несколько элементов разных видов, но с одинаковыми ведущими, вот так:

// single line declaration
int i = 0, * p_i = nullptr, ai[2] = {42,42}, geti(void), * * getppi(void);
// the same as
int i = 0;
int * p_i = nullptr;
int ai[2] = {42, 42};
int geti(void);
int ** getppi(void);

Так r это просто обычная переменная типа std::vector<std::string>Затем следует функция allLongestStrings, которая возвращает тот же тип std :: vector.

Эта компактная форма декларации существует по историческим причинам. В основном это помогло сохранить довольно много байтов для хранения и компиляции исходного файла.

Эта форма for цикл, вероятно, входит в число более ранних экспериментальных расширений до того, как текущая форма была стандартизирована.

0

По вопросам рекламы [email protected]