Как мы можем вернуть переменную по ссылке, в то время как область видимости - PullRequest
0 голосов
/ 20 мая 2018

Как мы можем вернуть переменную по ссылке, если область возвращаемой функции ушла, а ее переменные были уничтожены сразу после возвращения переменной?

И если мы сделаем следующее, чтобы избежать этого:

int fr = 9;
int& foo() {
    //const int& k = 5;
    return fr;
};

Я спрашиваю, должны ли мы объявить возвращенную переменную как глобальную переменную?

Ответы [ 5 ]

0 голосов
/ 20 мая 2018

Я предполагаю, что это академический пример для изучения принципа, потому что в противном случае очевидным способом кодирования было бы возвращение по значению.

С учетом этого предварительного условия это выглядит как сценарий использования интеллектуальных указателей.,Вы бы обернули переменную в умный указатель и вернули бы значение.Это похоже на ответ @Acorns, но переменная будет автоматически удалена, если на нее больше не ссылаются, поэтому нет необходимости в явном удалении.

0 голосов
/ 20 мая 2018

Примечание: OP и другие ответы предлагают варианты возврата ранее существующего объекта (глобальный, static в функции, переменная-член).Однако в этом ответе обсуждается возвращение переменной, время жизни которой начинается в функции, что, как я думал, было духом вопроса, а именно:

как мы можем вернуть переменную по ссылке, в то время какобласть действия возвращаемой функции исчезла, и ее переменные были уничтожены сразу после возвращения переменной.

Единственный способ вернуть по ссылке новый объект - это динамически выделить его:

int& foo() {
    return *(new int);
}

Затем, позже:

delete &myref;

Теперь, конечно, это не обычный способ делать вещи, или то, что люди ожидают, когдаони видят функцию, которая возвращает ссылку.См. Все предупреждения на Удаление ссылки .

Это может иметь некоторый смысл, хотя, если объект является одним из тех, которые "совершают самоубийство" позже, вызываяdelete this.Опять же, это тоже не типичный C ++.Больше информации об этом на Разрешено ли это удаление? .

Вместо этого, когда вы хотите вернуть объект, созданный внутри функции, вы обычно либо:

  • Возврат по значению (возможно, с использованием copy elision ).
  • Возвращает динамически размещенный объект (либо возвращает необработанный указатель на него, либо класс, обертывающий его, например,умный указатель).

Но ни один из этих двух подходов не возвращает реальный объект по ссылке.

0 голосов
/ 20 мая 2018

Используйте ключевое слово static, чтобы его область действия оставалась в коде.Пример: -

  int& fun(){
  static int a =5;
  return a;
  }

 int main()
 {
  int &b=fun();
  cout<<b;
 }
0 голосов
/ 20 мая 2018

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

class Foo {
public:
   Foo() ;
   int& getFoo() {return myFoo;} 
private:
   int myFoo;
};
0 голосов
/ 20 мая 2018

Вы можете вернуть локальную переменную static функции вместо глобальной переменной, конечно:

int& foo() {
    static int rc = 9;
    return rc;
}

Обратите внимание, однако, что у вас все еще есть глобальная переменная свсе его проблемы, например, потенциально одновременный доступ из нескольких потоков.По крайней мере, начиная с C ++ 11, инициализация переменной функции local static является поточно-ориентированной: переменная local static функции инициализируется при первом выполнении оператора объявления.

...