jjzjj

c++ - 匿名命名空间中模板化类的友元

coder 2024-02-24 原文

声明类时A作为类(class)的 friend B , 而 A在匿名命名空间和 B 中定义在外部,一些编译器会产生错误“protected member inaccessible”,而其他编译器不会产生任何错误或警告。如果AB或者两者都是模板:

namespace {
  template <class T>
  struct A {
    template <class BB>
    void foo(BB const& b) { b.bar(); }
  };
} // end anonymous namespace

template <class T>
class B {
  template <class> friend struct A;

protected:
  void bar() const {}
};

int main() {
  A<int> a;
  a.foo(B<int>{});
}
  1. AB都是模板。然后 Intel icc 18: error #308: function "B<T>::bar [with T=int]" is inaccessible , gcc 7.2: 没有错误, clang 5.0: 没有错误
  2. A B 时没有模板是模板:Intel icc 18:没有错误,gcc 7.2:错误:'void B<T>::bar() const [with T = int]' is protected within this context , clang 5: 没有错误
  3. A是一个模板,而 B不是:英特尔 icc 18:错误 #308 , gcc 7.2: 错误, clang 5: 没有错误
  4. 都不是A也不B是模板:Intel icc 18:没有错误,gcc 7.2:错误,clang 5:没有错误
  5. 都不是A也不B是模板(如 4.)但是 A 的位置和 B已交换:英特尔 icc 18:错误 #308 , gcc 7.2: error, clang 5: error: 'bar' is a protected member of 'B'
  6. AB都是模板(如 1.)但是 A 的位置和 B已交换:英特尔 icc 18:错误 #308 , gcc 7.2: 没有错误, clang 5: error

请参阅编译器资源管理器中的示例:https://godbolt.org/g/6Zdr3chttps://godbolt.org/g/BRqf78对于案例 6.

那么,什么是正确的行为呢?哪个编译器是正确的?

最佳答案

据我从标准判断,给定的代码在情况 1-4 中是正确的,并且应该在没有诊断的情况下编译:

未命名命名空间的定义 (7.3.1.1:1) 声明未命名命名空间定义等同于使用翻译单元唯一的名称定义命名命名空间,然后使用 using 指令导入此命名空间。

这将使 A 的声明在全局范围内可访问,并根据段落 11.3:9

A name nominated by a friend declaration shall be accessible in the scope of the class containing the friend declaration.

因此参数化类 AB 的友元,应该能够访问 B::bar

情况 5 有所不同。据我所知,友元声明在封闭范围内声明了一个新的参数化类 A,它不同于未命名命名空间中的类 A

关于c++ - 匿名命名空间中模板化类的友元,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48270533/

有关c++ - 匿名命名空间中模板化类的友元的更多相关文章

  1. ruby - 在 Ruby 中使用匿名模块 - 2

    假设我做了一个模块如下:m=Module.newdoclassCendend三个问题:除了对m的引用之外,还有什么方法可以访问C和m中的其他内容?我可以在创建匿名模块后为其命名吗(就像我输入“module...”一样)?如何在使用完匿名模块后将其删除,使其定义的常量不再存在? 最佳答案 三个答案:是的,使用ObjectSpace.此代码使c引用你的类(class)C不引用m:c=nilObjectSpace.each_object{|obj|c=objif(Class===objandobj.name=~/::C$/)}当然这取决于

  2. ruby-on-rails - 如何优雅地重启 thin + nginx? - 2

    我的瘦服务器配置了nginx,我的ROR应用程序正在它们上运行。在我发布代码更新时运行thinrestart会给我的应用程序带来一些停机时间。我试图弄清楚如何优雅地重启正在运行的Thin实例,但找不到好的解决方案。有没有人能做到这一点? 最佳答案 #Restartjustthethinserverdescribedbythatconfigsudothin-C/etc/thin/mysite.ymlrestartNginx将继续运行并代理请求。如果您将Nginx设置为使用多个上游服务器,例如server{listen80;server

  3. ruby - 通过 erb 模板输出 ruby​​ 数组 - 2

    我正在使用puppet为ruby​​程序提供一组常量。我需要提供一组主机名,我的程序将对其进行迭代。在我之前使用的bash脚本中,我只是将它作为一个puppet变量hosts=>"host1,host2"我将其提供给bash脚本作为HOSTS=显然这对ruby​​不太适用——我需要它的格式hosts=["host1","host2"]自从phosts和putsmy_array.inspect提供输出["host1","host2"]我希望使用其中之一。不幸的是,我终其一生都无法弄清楚如何让它发挥作用。我尝试了以下各项:我发现某处他们指出我需要在函数调用前放置“function_”……这

  4. ruby-on-rails - 如何重命名或移动 Rails 的 README_FOR_APP - 2

    当我在我的Rails应用程序根目录中运行rakedoc:app时,API文档是使用/doc/README_FOR_APP作为主页生成的。我想向该文件添加.rdoc扩展名,以便它在GitHub上正确呈现。更好的是,我想将它移动到应用程序根目录(/README.rdoc)。有没有办法通过修改包含的rake/rdoctask任务在我的Rakefile中执行此操作?是否有某个地方可以查找可以修改的主页文件的名称?还是我必须编写一个新的Rake任务?额外的问题:Rails应用程序的两个单独文件/README和/doc/README_FOR_APP背后的逻辑是什么?为什么不只有一个?

  5. ruby-on-rails - 使用 config.threadsafe 时从 lib/加载模块/类的正确方法是什么!选项? - 2

    我一直致力于让我们的Rails2.3.8应用程序在JRuby下正确运行。一切正常,直到我启用config.threadsafe!以实现JRuby提供的并发性。这导致lib/中的模块和类不再自动加载。使用config.threadsafe!启用:$rubyscript/runner-eproduction'pSim::Sim200Provisioner'/Users/amchale/.rvm/gems/jruby-1.5.1@web-services/gems/activesupport-2.3.8/lib/active_support/dependencies.rb:105:in`co

  6. ruby - rails 3 redirect_to 将参数传递给命名路由 - 2

    我没有找到太多关于如何执行此操作的信息,尽管有很多关于如何使用像这样的redirect_to将参数传递给重定向的建议:action=>'something',:controller=>'something'在我的应用程序中,我在路由文件中有以下内容match'profile'=>'User#show'我的表演Action是这样的defshow@user=User.find(params[:user])@title=@user.first_nameend重定向发生在同一个用户Controller中,就像这样defregister@title="Registration"@user=Use

  7. java - 从 JRuby 调用 Java 类的问题 - 2

    我正在尝试使用boilerpipe来自JRuby。我看过guide从JRuby调用Java,并成功地将它与另一个Java包一起使用,但无法弄清楚为什么同样的东西不能用于boilerpipe。我正在尝试基本上从JRuby中执行与此Java等效的操作:URLurl=newURL("http://www.example.com/some-location/index.html");Stringtext=ArticleExtractor.INSTANCE.getText(url);在JRuby中试过这个:require'java'url=java.net.URL.new("http://www

  8. 没有类的 Ruby 方法? - 2

    大家好!我想知道Ruby中未使用语法ClassName.method_name调用的方法是如何工作的。我头脑中的一些是puts、print、gets、chomp。可以在不使用点运算符的情况下调用这些方法。为什么是这样?他们来自哪里?我怎样才能看到这些方法的完整列表? 最佳答案 Kernel中的所有方法都可用于Object类的所有对象或从Object派生的任何类。您可以使用Kernel.instance_methods列出它们。 关于没有类的Ruby方法?,我们在StackOverflow

  9. ruby - 在匿名 block 中产生 - 2

    我没有理解以下行为(另请参阅inthisSOthread):defdef_testputs'def_test.in'yieldifblock_given?puts'def_test.out'enddef_testdoputs'def_testok'endblock_test=procdo|&block|puts'block_test.in'block.callifblockputs'block_test.out'endblock_test.calldoputs'block_test'endproc_test=procdoputs'proc_test.in'yieldifblock_gi

  10. ruby - Rails 关联 - 同一个类的多个 has_one 关系 - 2

    我的问题的一个例子是体育游戏。一场体育比赛有两支球队,一支主队和一支客队。我的事件记录模型如下:classTeam"Team"has_one:away_team,:class_name=>"Team"end我希望能够通过游戏访问一个团队,例如:Game.find(1).home_team但我收到一个单元化常量错误:Game::team。谁能告诉我我做错了什么?谢谢, 最佳答案 如果Gamehas_one:team那么Rails假设您的teams表有一个game_id列。不过,您想要的是games表有一个team_id列,在这种情况下

随机推荐