Если я правильно понимаю, мотивация ссылок состояла в том, чтобы было проще и понятнее работать «по ссылке», не беспокоясь о разыменовании указателя. Но они имеют постоянный характер, они могут указывать только на один объект, даже если фактически ссылка является указателем, а переназначение технически возможно. Также может показаться полезным, если ссылка может быть нулевой, например, проверьте правильность возвращенной ссылки перед ее использованием, но это не функция.
Что может быть особой мотивацией для того, чтобы опустить такие функции и представить функцию как она есть?
Есть две части мотивации:
1) Ссылка концептуально является псевдонимом для объекта, поэтому она ведет себя (насколько это возможно и полезно) подобно имени переменной. Пока он находится в области видимости, он ссылается на один и тот же объект и всегда ссылается на объект. Таким образом, не пересаживается и не является нулевым.
2) Ссылки были придуманы с целью передачи параметров перегруженным операторам. Нет особой необходимости переназначать такие параметры, и они, безусловно, всегда должны ссылаться на объект, потому что у оператора всегда есть операнды (или только один операнд для унарных операторов). Особенностью, которая удовлетворяла потребности, был псевдоним для операнда, и именно поэтому ссылки были задуманы как псевдонимы.
Будучи задуманным таким образом, они имеют другое применение. Ни одно из этих применений не получило бы достаточной выгоды от того, что они были переназначены или были бы нулевыми, чтобы обосновать необходимость изменения концепции от имени объекта. Наиболее близким является, вероятно, их использование в качестве нестатических элементов данных в классах. В этом случае они мешают таким вещам, как назначение копирования, но опять же неясно, как «эталонный» элемент данных «должен» вести себя при назначении копии, поэтому нет четкого способа справиться с этим. Указатели будут иметь дело со случаями, которые ссылки не могут.
Такова мотивация: сосредоточиться на том, что уже нельзя сделать другими способами.
Ссылки, которые нельзя обнулять, — это хорошо, это позволяет вам сделать более надежные гарантии ввода ваших функций и так далее. Это позволяет передавать объекты без необходимости проверки нулевого указателя.
Если вам нужна изменяемая ссылка, используйте либо указатель, либо std::reference_wrapper
, Если вы хотите необязательное возвращаемое значение, вы можете использовать что-то вроде boost::optional
,
Я бы сказал, что существуют ограничения на то, что можно сделать со ссылками, потому что это позволяет:
Таким образом, указатели для ситуаций, когда вы знать Вы хотите делать с ними сложные вещи. Ссылки относятся к типичному случаю «я просто хочу передать часть данных», не беспокоясь о том, чтобы сделать это правильно.