私有继承、友元和异常处理

2024-01-05

当类 A 私有地继承自类 B 时,意味着 B 是 A 的私有基类子对象。但对于友元来说不是这样,对于友元来说,它是公共子对象。当有多个 catch 处理程序时,第一个匹配的处理程序(即,如果异常类型可以隐式转换为处理程序的参数类型)将被调用。那么有人会向我解释为什么下面的代码不能按我的预期工作吗?这是标准的预期行为还是 MSVC 错误?

class A
{
};
class B:A //private inheritance 
{
    friend void g();
}; 

void f()
{

    B b;
    //A* pa = &b; // error, conversion exists, but is inaccessible
    throw b;
}

void g()
{
    B b;
    A* pa = &b; //ok, private inheritance, but g() is B's friend so it is as though public
    try
    {
        f();
    }
    catch(A&)
    {
        //WHY ISN'T THIS HANDLER INVOKED?! B&->A& conversion exists in this function
    }
    catch(B&)
    {       
    }
}

int main()
{
    g();
}

附:这不是真正的代码,这是一个理论实验,也就是说,不要告诉我诸如朋友不好、组合优于私有继承之类的东西。

提前致谢


不,标准不是这么说的。它说(C++0x):

处理程序是异常的匹配 E 类型的对象 if

— 处理程序的类型为 cv T 或 cv T& E和T是同一类型 (忽略顶级简历限定符), 或者

— 处理程序的类型为 cv T 或 cv T& T 是一个明确的公众基础 班级E 的,或

— 处理程序的类型为 cv1 T* cv2 E 是一个指针类型,可以是 转换为处理程序的类型 由其中之一或两者

— 标准指针转换 (4.10)不涉及到指针的转换 私有或受保护或含糊不清 类

— 资格转换

— 处理程序是一个指针或指向 成员类型,E 是 std::nullptr_t

理由:实施复杂。您可以将其视为转换发生在 throw 和 catch 之间的某个位置,而不是发生在 g 本身中。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

私有继承、友元和异常处理 的相关文章

随机推荐