我想知道在C ++程序中是否存在任何情况,其中更改代码中的访问说明符(公共/受保护/私有)会导致该程序的行为发生变化?
答案 0 :(得分:4)
模板使您可以根据成员或方法是否可访问来做不同的事情。仅作为一个随机示例,请考虑以下问题:
#include <type_traits>
#include <iostream>
struct foo_private {
private:
foo_private() {}
};
struct foo_public {
public:
foo_public() {}
};
int main() {
std::cout << std::is_default_constructible<foo_private>::value;
std::cout << std::is_default_constructible<foo_public>::value;
}
答案 1 :(得分:3)
一个有趣的示例,该示例基本上只在运行时发生,这意味着程序需要以某种方式知道一些从访问级别派生的信息:对于[except.handle]/3.2,如果异常处理程序接受明确且 > public 异常对象的类类型的基类。
http://myserver2/?PatientID=123456
此打印:
#include <iostream>
class Base {};
void test(void (*thrower)()) {
try {
thrower();
} catch (Base&) {
std::cout << "Caught a Base." << std::endl;
} catch (...) {
std::cout << "Not a Base?" << std::endl;
}
}
class D1 : public Base {};
class D2 : private Base {};
int main() {
std::cout << "Test D1" << std::endl;
test([]() { throw D1{}; });
std::cout << "Test D2" << std::endl;
test([]() { throw D2{}; });
}
...即使Test D1
Caught a Base.
Test D2
Not a Base?
和D1
之间的唯一区别是访问说明关键字的更改。
答案 2 :(得分:1)
是的,如果有人SFINAE退出了该功能,则可能会发生这种情况。例如:
class Cat {
public:
void purr() const;
public:
void hiss() const;
};
using prefer_overload_t = int;
using backup_overload_t = long;
template <typename T>
auto react(prefer_overload_t, T const& t)
-> decltype(t.purr())
{
return t.purr();
}
template <typename T>
void react(backup_overload_t, T const& t)
{
t.hiss();
}
int main() {
Cat cat;
react(prefer_overload_t{}, cat);
}
如果purr
函数具有公共可访问性,则会调用cat.purr()
。
如果purr
函数具有非公共可访问性,则会调用cat.hiss()
。