Ответ 1
Ваши две функции служат для двух разных целей.
-
Функция 1: работает как
remove_copy
. Он не будет изменять существующий контейнер; он делает копию и изменяет это. -
Функция 2: работает как
remove
. Он изменит существующий контейнер.
У меня есть функция, где мне нужно модифицировать значения вектора. это хорошая практика в С++ для возврата вектора?
vector<string> RemoveSpecialCharacters(vector<string> words)
{
for (vector<string>::iterator it=words.begin(); it!=words.end(); )
{
if(CheckLength(*it) == false)
{
it = words.erase(it);
}
else{
++it;
}
}//end for
return words;
}
void RemoveSpecialCharacters(vector<string> & words)
{
for (vector<string>::iterator it=words.begin(); it!=words.end(); )
{
if(CheckLength(*it) == false)
{
it = words.erase(it);
}
else{
++it;
}
}//end for
}
Ваши две функции служат для двух разных целей.
Функция 1: работает как remove_copy
. Он не будет изменять существующий контейнер; он делает копию и изменяет это.
Функция 2: работает как remove
. Он изменит существующий контейнер.
Это несколько субъективно. Я лично предпочел бы последнее, поскольку он не налагает затраты на копирование вектора на вызывающего абонента (но вызывающий может по-прежнему свободно делать копию, если они этого захотят).
В этом конкретном случае я бы выбрал передачу по ссылке, но не потому, что это практика на C++ или нет, а потому, что она на самом деле имеет больше смысла (функция по ее имени применяет модификацию к вектору). Кажется, нет реальной необходимости возвращать данные из функции.
Но это также зависит от цели функции. Если вы всегда хотите использовать его следующим образом:
vec = bow.RemoveSpecialCharacters(vec);
Тогда абсолютно первый вариант - это go. В противном случае, вторая кажется более подходящей. (Судя по имени функции, мне кажется, что первое мне кажется более подходящим).
С точки зрения производительности, первое решение в современном мире С++ 11 будет меньше, чем несколько назначений медленнее, поэтому влияние производительности будет незначительным.
Перейдите к опции 2, изменив вектор, переданный как параметр.
Боковое примечание: некоторые методы кодирования предлагают пройти через аргументы указателей, которые могут быть изменены (просто, чтобы на первый взгляд понять разработчикам, что функция может изменить аргумент).
Лучшей практикой является передача по ссылке вектора.
Внутри функции, которую вы ее отредактируете, и вам не нужно возвращать ее (на самом деле вы выделяете новое пространство памяти, которое не нужно).
Если вы передадите его по ссылке, стоимость будет намного меньше, и вектор также будет изменен вне области действия
Первая функция вернет копию вектора, поэтому она будет медленнее второй. Вы должны использовать второй.
На самом деле ни одна из них не является хорошей практикой для С++, если по хорошей практике это означает, что это делается в библиотеках С++. Вы в основном переопределяете то, что делает std::remove_copy_if
или std::remove_if
, поэтому хорошей практикой является реализация функций (или использование существующих), которые работают в диапазоне, а не в контейнере, либо по значению, либо по ссылке.
Опять же, это зависит от того, как вы определяете термин good practice
.