Для удобства я буду ссылаться на параметр, который будет изменен функцией как «out-param».
Исходящие параметры могут передаваться как неконстантные ссылки. Нет никаких технических причин. В стандартных библиотеках, например, std::swap
принимает два параметра по ссылке и изменяет оба.
В прошлом я видел, как правило, в руководстве по стилю, что out-params должны передаваться указателем, а не ссылкой. Мотивация заключается в том, что некоторые люди [*]
хотят вызвать вызов функции, который появляется, чтобы передать объект по значению, чтобы оставить объект неизменным. Это облегчает для них рассуждение о части кода, просто глядя на вызывающий код, без необходимости искать то, что фактически выполняет функция. Например:
int foo(int a) {
return a + 1;
}
int bar(int &a) {
return ++a;
}
Теперь данный int i = 0;
, звонки foo(i)
и bar(i)
выглядеть точно так же, но один из них ведет себя как хороший, простой функции C, тогда как другая использует пройти по ссылке, чтобы изменить i
,
Некоторые люди [*]
хотят эти различные вещи, чтобы быть явно отличается на месте вызова, поэтому они предпочитают писать bar(&i)
, чтобы понять, что i
может быть изменен [**]
. В принципе, они предпочли бы, чтобы C++ не содержал неконстантных ссылок в качестве параметров функции вообще.
Не обязательно что-то не так, что эти люди хотят делать. Вы можете, например, придерживаться его в случае std::swap
, всегда используя вместо этого std::iter_swap
. Но большинство руководств по стилю C++ не имеют такого правила.
[*]
, например Программисты
[**]
На самом деле в моей bar
функции, a
является и в-парам и из-парам. Их предпочтительная функция int bar(int *pa);
технически не имеет out-param, хотя для удобства они, вероятно, будут ссылаться на referand pa
(то есть i
) как out-param, и все знают, что это значит.
Вы можете передать указатель по ссылке: 'void foo (obj * & x)' –
ОК, но тогда вы все равно передаете указатель. Смешивание указателя и эталонной семантики может быть очень запутанным, ИМО. –
@BlagovestBuyukliev: А? Здесь нет ничего смешанного. Вы ссылаетесь на указатель. Это намного проще, чем указатель на указатель. – GManNickG