gpt4 book ai didi

c++ - 跨 C++ 模块传递指向成员函数的指针

转载 作者:行者123 更新时间:2023-11-30 05:19:11 25 4
gpt4 key购买 nike

给定两个类:XYX 包含类型Y * 的成员,并将指向其成员函数的指针传递给Y 的实例。所以在 C++ 中它看起来像这样:

x.h

#pragma once

class Y;

class X
{
public:
X();
private:
Y *y;
void myfunc(int);
};

x.cpp

#include "x.h"
#include "y.h"

X::X()
{
this->y = new Y(*this, &X::myfunc);
}

void X::myfunc(int dummy)
{
dummy = dummy;
}

y.h

#pragma once

//#include "x.h" // this would fix the issue!

class X;

class Y
{
public:
Y(X &x, void (X::*pMyCallback)(int));
~Y();

private:
X &x;
void (X::*pMyCallback)(int) = nullptr;
};

y.cpp

#include "y.h"
#include "x.h"

Y::Y(X &x, void (X::*pMyCallback)(int))
: x(x), pMyCallback(pMyCallback)
{
(x.*pMyCallback)(3);
}

Y::~Y()
{
}

当我运行此代码时,Visual Studio 2015 引发异常:“MYPROGRAM.exe 已触发断点”。有时它会因访问冲突异常而崩溃。

int main(int argc, char *argv[])
{
X x;
return 0;
}

我注意到这个问题在某种程度上与编译单元有关,因为如果我在同一个文件中定义 XY 它不会崩溃。此外,如果我将 X(即“x.h”)的声明包含到“y.h”中,它也不会崩溃。

这种行为有合理的理由吗?

最佳答案

问题似乎是在声明类之后定义指向成员的指针时,但在定义之前,MSVC 必须猜测类的继承模型。有四种方法可以解决这个问题:

  • 在声明 class X 中使用 MS 特定关键字 __single_inheritance__multiple_inheritance__virtual_inheritance in "y.h",强制它使用特定的模型。其中,__single_inheritance 效率最高,但仅在类没有多重继承或虚拟继承时可用;因为 X 没有基类,所以这很好。

    // y.h

    #pragma once

    //#include "x.h" // this would fix the issue!

    class __single_inheritance X;

    class Y
    {
    public:
    Y(X &x, void (X::*pMyCallback)(int));
    ~Y();

    private:
    X &x;
    void (X::*pMyCallback)(int) = nullptr;
    };
  • 使用 MS 专用编译指示 pointers_to_members , 为了同样的原因。同样,我们可以使用“单继承”,这是最高效的选择。

    // y.h

    #pragma once

    #pragma pointers_to_members(full_generality, single_inheritance)

    //#include "x.h" // this would fix the issue!

    class X;

    class Y
    {
    public:
    Y(X &x, void (X::*pMyCallback)(int));
    ~Y();

    private:
    X &x;
    void (X::*pMyCallback)(int) = nullptr;
    };
  • 更改 IDE 中的Pointer-to-member representation 选项;不幸的是,我不确定该怎么做,因为我找不到该选项。

  • 指定命令行选项 /vmg

关于c++ - 跨 C++ 模块传递指向成员函数的指针,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41287056/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com