【问题标题】:Is it possible to tell if a method is publicly accessible at compile-time是否可以在编译时判断一个方法是否可以公开访问
【发布时间】:2014-04-04 22:17:44
【问题描述】:

在 C++ 中,如果类具有命名字段、typedef 或方法,则在编译时可以使用 SFINAE 技巧。

我的问题是:我们也可以以某种方式查询方法是否可访问吗?就像区分私有方法和公共方法一样。

例如,如果我有一个从 std::vector 私下继承的类,例如 class T : private std::vector<int> { ... };,我不想检测它的 begin 方法,因为它不可公开访问。

当搜索 arround 时,我只获得检测方法的代码,与可见性无关......我得到的最接近的 was this 解决了继承的方法,但尚不清楚它如何与可见性交互。显然我可以测试,但我担心编译器特定的行为,因为我正在开发一个关于旧 Microsoft 编译器的项目:\

编辑 / 澄清:says here C++ 标准改变了它对这个问题的看法:对于 C++03,任何可见或不可见的成员都是可替代的,但由于 C++11 仅可见成员是。这是正确的吗?

我用下面的代码做了一些测试,它检测到value_type typedef。我不确定标准是怎么说的,但我用不同的编译器编译,结果如下:

  • gcc : 4.4 true | 4.5 true | 4.6 true | 4.7 true | 4.8 false | 4.9 之前的false
  • Clang : 3.3 fail
  • icc : 13 true
  • msvc : 2005 true | 2010true | 2012true

代码如下:

#include <vector>

typedef char yes;
typedef int no;

template<class T> struct has_value_type {
   template<class U> static yes test(typename U::value_type*);
    template<class U> static no  test(...);
    static const bool value = sizeof(test<T>(0)) == sizeof(yes);
};

class C : private std::vector<int> {  };

int main() {
   return has_value_type<C>::value;
}

【问题讨论】:

  • 如果对存在的方法的 sfinae 检查成功,也应该意味着该方法是公共的(否则在 sfinae 检查期间调用它会导致 sfinae 失败),不是吗?
  • 这里有一些你可以用来测试它的东西:coliru.stacked-crooked.com/a/630e969edc491662
  • 我的 This answer 可能会有所帮助。如果由于某种原因无法调用该函数,则检查报告为 false。 Pre C++11,它认为这是不可能的。
  • 访问检查在替换期间完成,但仅从 C++11 开始。 C++03 明确表示未完成访问检查。因此,您的示例将无法按 C++03 规则编译并在 C++11 中正确报告(即返回 false)。 This way 适用于这两种标准,也应该在旧编译器上编译,但遗憾的是它没有告诉我们关于 value_type 的可见性。你不能两者兼得。

标签: c++ visibility sfinae


【解决方案1】:

正如您找到的example 的 cmets 所述:

“建议的 SFINAE 仅在方法公开时才有效”

因此,它只会检测应该解决您问题的公共方法。

【讨论】:

  • 那是从 C++11 开始的吗? This post 似乎在向那个方向倾斜。
猜你喜欢
  • 1970-01-01
  • 2011-03-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-07-04
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多