Ссылка на очередь, которая находится в стеке функций - PullRequest
0 голосов
/ 02 октября 2018

Вот некоторый код C ++, который использует очередь.

#include <iostream>
#include <queue>
using namespace std;

void print(queue<int>& q){
    int n = q.size();
    for (int i = 0; i < n; ++i){
        int front = q.front();
        cout<<front<<" ";
        q.pop();
        q.push(front);
    }
    cout<<endl;
}

template <typename T>
void foo(queue<T>& q){
    queue<T> q2;
    for(int i=4;i<7;i++)
        q2.push(i);
    q = q2;
}

int main(){

    queue<int>q;
    for(int i=1;i<4;i++)
        q.push(i);
    print(q);

    foo(q);
    print(q);

}

Очередь q объявлена ​​в функции main и передана в качестве ссылки в функцию foo.Но он переназначается в другую очередь q2, которая занимает память в пространстве стека функций.

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

Может ли кто-нибудь помочь мне с этими двумя вопросами?
1. Почему q содержит правильные элементы q2, хотя очередь q2 была уничтожена после завершения вызова функции.
2. Ссылочная переменная инициализируется только один раз.Но, похоже, мы можем присвоить ему разные значения столько раз, сколько захотим.Почему это разрешено?

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

1 Ответ

0 голосов
/ 02 октября 2018

Ваше понимание того, что ссылка может быть назначена только один раз, является правильным.Ссылки псевдонимы относятся к объектам в том смысле, что они сами не являются объектами, но всегда ссылаются на другой объект.По своему замыслу, их синтаксическое использование в большинстве случаев является заменой конкретных объектов.С другой стороны, указатели могут указывать на другой объект или на nullptr.

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

Документацию для queue operator= можно найти здесь .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...