当我通过引用传递一个对象并且超出范围时,在C ++中会发生什么? [英] What happens in C++ when I pass an object by reference and it goes out of scope?

查看:175
本文介绍了当我通过引用传递一个对象并且超出范围时,在C ++中会发生什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我认为这个问题最好用一个小代码片段,我刚才写:

I think this question is best asked with a small code snippet I just wrote:

#include <iostream>

using namespace std;

class BasicClass
{
public:
    BasicClass()
    {
    }
    void print()
    {
        cout << "I'm printing" << endl;
    }
};

class FriendlyClass
{
public:
    FriendlyClass(BasicClass& myFriend) :
        _myFriend(myFriend)
    {
    }
    void printFriend()
    {
        cout << "Printing my friend: ";
        _myFriend.print();
    }
private:
    BasicClass& _myFriend;
};

int main(int argv, char** argc)
{
    FriendlyClass* fc;
    {
        BasicClass bc;
        fc = new FriendlyClass(bc);
        fc->printFriend();
    }
    fc->printFriend();
    delete fc;
    return 0;
}

代码使用g ++编译和运行:

The code compiles and runs fine using g++:

$ g++ test.cc -o test
$ ./test
Printing my friend: I'm printing
Printing my friend: I'm printing

但是,这不是我期待的行为。我期待第二次调用 fc-> printFriend()时出现某种失败。我的理解是如何通过引用传递/存储工作不正确,或者这只是发生在小规模的工作,可能会在一个更复杂的应用程序中爆炸?

However, this is not the behavior I was expecting. I was expecting some sort of failure on the second call to fc->printFriend(). Is my understanding of how the passing/storing by reference works incorrect or is this something that just happens to work on a small scale and would likely blow up in a more sophisticated application?

推荐答案

它的工作原理与指针:使用指向不再存在的对象的指针/引用是未定义的行为。

It works exactly as for pointers: using something (pointer/reference) that refers to an object that no longer exists is undefined behavior. It may appear to work but it can break at any time.

警告:以下是一个快速解释为什么这样的方法调用似乎可以工作在几个场合,只是为了信息目的;

Warning: what follows is a quick explanation of why such method calls can seem to work in several occasions, just for informative purposes; when writing actual code you should rely only on what the standard says

对于你所观察到的行为:在大多数(全部?)编译器方法调用被实现为具有隐藏这个参数的函数调用,该参数指的是该方法将要在其上操作的类的实例。但是在你的情况下,这个指针根本没有被使用(函数中的代码不是指任何字段,并且没有虚拟分派),所以(现在无效)指针未使用,调用成功。

As for the behavior you are observing: on most (all?) compilers method calls are implemented as function calls with a hidden this parameter that refers to the instance of the class on which the method is going to operate. But in your case, the this pointer isn't being used at all (the code in the function is not referring to any field, and there's no virtual dispatch), so the (now invalid) this pointer is not used and the call succeeds.

在其他情况下,即使它指的是一个超范围的对象,因为它的内存还没有被重用(虽然析构函数已经运行,所以该方法可能会找到一个不一致状态的对象)。

In other instances it may appear to work even if it's referring to an out-of-scope object because its memory hasn't been reused yet (although the destructor has already run, so the method will probably find the object in an inconsistent state).

同样,你不应该依赖这些信息,只是为了让你知道为什么这个电话仍然有效。

Again, you shouldn't rely on this information, it's just to let you know why that call still works.

这篇关于当我通过引用传递一个对象并且超出范围时,在C ++中会发生什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆