繁体   English   中英

如果我尝试在 c++ 中打印类的非静态成员函数的地址,为什么会创建 object?

[英]Why an object is created if I try to print a class's non-static member function's address in c++?

我在检查非静态成员变量的偏移量时发现了一种有趣的行为

看起来如果我尝试在指针中打印非静态成员函数的地址
它只是为具有成员 function 的 class 创建一个新的 object

这是我可以忽略的正常行为还是未定义的行为?

例如,如果我尝试下面的代码

#include <iostream>

typedef void(*FP)();

class AAA {
public:
    int var1;
    int var2;

    void foo() {
        std::cout << &var1 << std::endl;
        std::cout << &var2 << std::endl;
    }
};

int main() {
    FP fp = reinterpret_cast<FP>(&AAA::foo);
    std::cout << fp << std::endl;
    fp();
}

它的结果如下

$ ./a.out
0x56001ea8d940
0x7fe36c93c760
0x7fe36c93c764

所以我删除了cout语句然后它只是像我预期的那样打印成员的偏移量

#include <iostream>

typedef void(*FP)();

class AAA {
public:
    int var1;
    int var2;

    void foo() {
        std::cout << &var1 << std::endl;
        std::cout << &var2 << std::endl;
    }
};

int main() {
    FP fp = reinterpret_cast<FP>(&AAA::foo);
    fp();
}

结果如下

$ g++ main.cpp (with some warnings anyway)
$ ./a.out
0x1
0x5

您看到的奇怪行为是由以下行引起的未定义行为:

FP fp = reinterpret_cast<FP>(&AAA::foo);

即使不调用fp这已经是未定义的行为! 只有列出的转换reinterpret_cast[expr.reinterpret.cast] )有效,而您正在使用的转换(成员 function 指针指向 function 指针)不是其中之一。

一个常见的误解是reinterpret_cast是一种允许以任何可以想象的方式规避类型安全的“任何事情”转换。 根据标准,情况并非如此; 只有少数特定的转换是有效的。 所有其他人都不是(但不需要诊断,这导致它们无论如何都被使用)。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM