0

我在不同的命名空间中有两个同名的类。我无法修改类的名称。我想向其中一个类添加一个方法,但不允许将其添加为公共方法。另一个类是用 C++/CLI 作为 ref 类编写的,需要访问此方法。我尝试使用朋友类,但我不知道应该如何使用它。

标准 C++ 中的 dll:

namespace X
{
    class A
    {
        protected:
        __declspec(dllexport) void method();
    }
}

C++/CLI 中的应用程序

namespace Y
{
    ref class A
    {
        void someMethod()
        {
            X::A otherClass;
            otherClass.method();
        }
    }
}

我尝试了以下方法:朋友类 Y::A; // 编译器错误 C2653: Y 不是类或命名空间名称

当我声明命名空间 YI 得到错误 C2039: 'A' : is not a member of 'Y'

我无法在命名空间 Y 中添加类 A 的前向声明,因为类 A 是使用标准 C++ 编译的,并且在前向声明中我必须将其声明为 ref 类。

编译器:Visual Studio 2008

有人有想法吗?

谢谢

解决方案(感谢 Sorayuki):

#ifdef __cplusplus_cli
    #define CLI_REF_CLASS ref class
#else
    #define CLI_REF_CLASS class
#endif

namespace Y { CLI_REF_CLASS A; }

namespace X
{
    class A
    {
        protected:
        friend CLI_REF_CLASS Y::A;
        __declspec(dllexport) void method();
    }
}
4

1 回答 1

1

我不确定这种伎俩是否被允许。

但也许你想看看这种“黑客”:

在 c++/cli

namespace Y
{
    class HackA : public X::A {
        public:
        void CallMethod() { method(); }
    };
    ref class A
    {
        void someMethod()
        {
            X::A otherClass;
            assert(sizeof(HackA) == (X::A));
            HackA* p = (HackA*) &otherClass;
            p->CallMethod();
        }
    };
};

编辑:

我已经测试过这可以通过编译

namespace Y { ref class A; };

namespace X
{
    class A
    {
        friend ref class Y::A;
        protected:
        __declspec(dllexport) void method();
    };
};

namespace Y
{
    ref class A
    {
        void someMethod()
        {
            X::A otherClass;
            otherClass.method();
        }
    };
};

也许您只需要复制 X::A 的头文件并通过在命名空间 X. 之前添加声明(未定义) Y::A 来编辑副本,并包含“副本”。

于 2013-04-24T08:50:17.577 回答