标准对 char 数组作为模板参数有何规定?

2024-01-27

在我研究答案的过程中这个问题 https://stackoverflow.com/q/57003010/9883438我发现(我之前不知道)gcc 和 clang 允许char如果声明了数组,则它们将成为模板参数static。例如。此代码使用 gcc 和 clang 编译:

#include <type_traits>

template <int N, const char (&string)[N]>
auto foo()
{
    if constexpr (string[0] == 'i')
        return 0;
    else
        return 3.14f;
}

void bar()
{
    static constexpr char string1[] = "int";
    static constexpr char string2[] = "float";

    auto i = foo<sizeof(string1), string1>();
    auto f = foo<sizeof(string2), string2>();

    static_assert(std::is_same_v<decltype(i), int>);
    static_assert(std::is_same_v<decltype(f), float>);
}

MSVC 也允许这样做。但是,为了使其与 MSVC 一起工作,我必须在全局命名空间中声明这两个字符串。那么它也同样有效。

所以我的问题是:标准对此有何规定?哪个编译器(如果有)是正确的?


Update:

此问题已在 VS 2019 版本 16.4 (msvc v19.24) 中修复:https://developercommunity.visualstudio.com/content/problem/341639/very-fragile-ice.html https://developercommunity.visualstudio.com/content/problem/341639/very-fragile-ice.html


这是从 C++14 到 C++17 的变化,看起来 MSVS 还没有跟上。以前在[temp.arg.nontype] https://timsong-cpp.github.io/cppwp/n4140/temp.arg.nontype非类型参数必须是

非类型、非模板模板参数的模板参数应为以下之一:

  • 对于整型或枚举类型的非类型模板参数,模板参数类型的转换常量表达式([expr.const]);或者

  • 非类型模板参数的名称;或者

  • 常量表达式 ([expr.const]),指定具有静态存储持续时间和外部或内部链接的完整对象的地址或具有外部或内部链接的函数,包括函数模板和函数模板 ID,但不包括非静态类成员,表示(忽略括号)为 & id-表达式,其中 id-表达式 是对象或函数的名称,但如果名称引用函数或数组,则可以省略 &;如果相应的模板参数是引用,则应省略 &;或者

  • 计算结果为空指针值的常量表达式 ([conv.ptr]);或者

  • 计算结果为空成员指针值的常量表达式 ([conv.mem]);或者

  • 指向成员的指针,如 [expr.unary.op] 中所述表达;或者

  • 类型的常量表达式std::nullptr_t.

emphasis mine

由于第 3 点,您无法使用块作用域变量,因为块作用域变量没有链接[基本.链接]/10 https://timsong-cpp.github.io/cppwp/basic.link#10

这些规则未涵盖的名称没有任何联系。此外,除非另有说明,在块作用域中声明的名称没有链接。

在 C++17 中,情况发生了变化。[temp.arg.nontype] https://timsong-cpp.github.io/cppwp/n4659/temp.arg.nontype now has

非类型模板参数的模板参数应是模板参数类型的转换后的常量表达式。对于引用或指针类型的非类型模板参数,常量表达式的值不应引用(或对于指针类型,不应是以下地址):

  • 一个子对象,

  • 一个临时的物体,

  • 字符串文字,

  • typeid 表达式的结果,或

  • 一个预定义的­func__ 变量。

现在允许您使用块作用域静态变量

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

标准对 char 数组作为模板参数有何规定? 的相关文章

  • 以文化中立的方式将字符串拆分为单词

    我提出了下面的方法 旨在将可变长度的文本拆分为单词数组 以进行进一步的全文索引处理 删除停止词 然后进行词干分析 结果似乎不错 但我想听听关于这种实现对于不同语言的文本的可靠性的意见 您会建议使用正则表达式来代替吗 请注意 我选择不使用 S
  • 为什么 C# Array.BinarySearch 这么快?

    我已经实施了一个很简单用于在整数数组中查找整数的 C 中的 binarySearch 实现 二分查找 static int binarySearch int arr int i int low 0 high arr Length 1 mid
  • Clang 3.1 + libc++ 编译错误

    我已经构建并安装了 在前缀下 alt LLVM Clang trunk 2012 年 4 月 23 日 在 Ubuntu 12 04 上成功使用 GCC 4 6 然后使用此 Clang 构建的 libc 当我想使用它时我必须同时提供 lc
  • 将 VSIX 功能添加到 C# 类库

    我有一个现有的单文件生成器 位于 C 类库中 如何将 VSIX 项目级功能添加到此项目 最终目标是编译我的类库项目并获得 VSIX 我实际上是在回答我自己的问题 这与Visual Studio 2017 中的单文件生成器更改 https s
  • 使用 WebClient 时出现 System.Net.WebException:无法创建 SSL/TLS 安全通道

    当我执行以下代码时 System Net ServicePointManager ServerCertificateValidationCallback sender certificate chain errors gt return t
  • 重载<<的返回值

    include
  • 如何设计以 char* 指针作为类成员变量的类?

    首先我想介绍一下我的情况 我写了一些类 将 char 指针作为私有类成员 而且这个项目有 GUI 所以当单击按钮时 某些函数可能会执行多次 这些类是设计的单班在项目中 但是其中的某些函数可以执行多次 然后我发现我的项目存在内存泄漏 所以我想
  • SolrNet连接说明

    为什么 SolrNet 连接的容器保持静态 这是一个非常大的错误 因为当我们在应用程序中向应用程序发送异步请求时 SolrNet 会表现异常 在 SolrNet 中如何避免这个问题 class P static void M string
  • 如何在整个 ASP .NET MVC 应用程序中需要授权

    我创建的应用程序中 除了启用登录的操作之外的每个操作都应该超出未登录用户的限制 我应该添加 Authorize 每个班级标题前的注释 像这儿 namespace WebApplication2 Controllers Authorize p
  • 如何在 C 中调用采用匿名结构的函数?

    如何在 C 中调用采用匿名结构的函数 比如这个函数 void func struct int x p printf i n p x 当提供原型的函数声明在范围内时 调用该函数的参数必须具有与原型中声明的类型兼容的类型 其中 兼容 具有标准定
  • 如何序列化/反序列化自定义数据集

    我有一个 winforms 应用程序 它使用强类型的自定义数据集来保存数据进行处理 它由数据库中的数据填充 我有一个用户控件 它接受任何自定义数据集并在数据网格中显示内容 这用于测试和调试 为了使控件可重用 我将自定义数据集视为普通的 Sy
  • 垃圾收集器是否在单独的进程中运行?

    垃圾收集器是否在单独的进程中启动 例如 如果我们尝试测量某段代码所花费的进程时间 并且在此期间垃圾收集器开始收集 它会在新进程上启动还是在同一进程中启动 它的工作原理如下吗 Code Process 1 gt Garbage Collect
  • 什么时候虚拟继承是一个好的设计? [复制]

    这个问题在这里已经有答案了 EDIT3 请务必在回答之前清楚地了解我要问的内容 有 EDIT2 和很多评论 有 或曾经 有很多答案清楚地表明了对问题的误解 我知道这也是我的错 对此感到抱歉 嗨 我查看了有关虚拟继承的问题 class B p
  • 如何查看网络连接状态是否发生变化?

    我正在编写一个应用程序 用于检查计算机是否连接到某个特定网络 并为我们的用户带来一些魔力 该应用程序将在后台运行并执行检查是否用户请求 托盘中的菜单 我还希望应用程序能够自动检查用户是否从有线更改为无线 或者断开连接并连接到新网络 并执行魔
  • Windows 窗体:如果文本太长,请添加新行到标签

    我正在使用 C 有时 从网络服务返回的文本 我在标签中显示 太长 并且会在表单边缘被截断 如果标签不适合表单 是否有一种简单的方法可以在标签中添加换行符 Thanks 如果您将标签设置为autosize 它会随着您输入的任何文本自动增长 为
  • 对现有视频添加水印

    我正在寻找一种用 C 在视频上加水印的方法 就像在上面写文字一样 图片或文字标签 我该怎么做 谢谢 您可以使用 Nreco 视频转换器 代码看起来像 NReco VideoConverter FFMpegConverter wrap new
  • 为什么编译时浮点计算可能不会得到与运行时计算相同的结果?

    In the speaker mentioned Compile time floating point calculations might not have the same results as runtime calculation
  • 如何将带有 IP 地址的连接字符串放入 web.config 文件中?

    我们当前在 web config 文件中使用以下连接字符串 add name DBConnectionString connectionString Data Source ourServer Initial Catalog ourDB P
  • 如何在Xamarin中删除ViewTreeObserver?

    假设我需要获取并设置视图的高度 在 Android 中 众所周知 只有在绘制视图之后才能获取视图高度 如果您使用 Java 有很多答案 最著名的方法之一如下 取自这个答案 https stackoverflow com a 24035591
  • 基于 OpenCV 边缘的物体检测 C++

    我有一个应用程序 我必须检测场景中某些项目的存在 这些项目可以旋转并稍微缩放 更大或更小 我尝试过使用关键点检测器 但它们不够快且不够准确 因此 我决定首先使用 Canny 或更快的边缘检测算法 检测模板和搜索区域中的边缘 然后匹配边缘以查

随机推荐

  • 什么是 .inc 以及为什么使用它?

    我经常在 PHP 中看到包含 inc 文件的示例 inc 是什么意思 它是用来做什么的 使用它有什么缺点和优点 它没有任何意义 只是一个文件扩展名 如果该文件被设计为被其他 PHP 文件包含 则某些人习惯用 inc 扩展名命名该文件 但这只
  • Nuxt3生成类型错误:无法读取null的属性(读取'isCE')

    我在我的应用程序中使用 Nuxt3 Vite Leaflet Bootstrap 该应用程序在开发中运行良好 但是当我尝试使用生成静态站点时npm run generate 我收到以下错误 类型错误 无法读取 null 的属性 读取 isC
  • 通过 python 使用 Google Drive API V3 获取 Google Drive 文件所有者电子邮件地址

    我无法通过 Google Drive API v3 获取 Google 云端硬盘上文件的所有者 我可以在 v2 下做到这一点 但事情已经改变了 根据文档 https developers google com drive api v3 re
  • 在Android Studio中使用自定义框架库(android.jar)

    我有自己的定制框架 android jar 并想在 Android Studio 中使用它 我的 build gradle 中有如下描述 dependencies compile files myandroid jar 但Android S
  • 如何将material-ui时间选择器更改为24小时格式

    目前使用的是Timepicker来自材料用户界面 我已将其设置为type time 它允许我通过 AM PM 选项选择一天中 12 小时内的时间 我希望我的选择器采用 24 小时格式 从而删除 AM PM 选项 我查看了material u
  • 为什么变量在更改其因变量后没有更新? [复制]

    这个问题在这里已经有答案了 我不明白为什么当我更改 x 时变量 y 不更新 y 变量依赖于 x 对吧 x 5 y x 2 print x print y x 3 Expect it to print 3 and 6 instead it p
  • 我可以在 robots.txt 中使用“Host”指令吗?

    Searching for specific information on the robots txt I stumbled upon a Yandex help page http help yandex com webmaster c
  • 为什么此保存方法不调整图像大小?

    我重写保存方法以便在上传后调整图像大小 以下代码似乎并未调整图像大小 我仔细检查了媒体文件夹 发现上传图像的原始尺寸 900x850 只有一份副本 Django 没有抛出任何错误 所以我不知道如何解决这个问题 需要明确的是 我可以毫无问题地
  • SQLAlchemy 自定义查询列

    我有一个如下定义的声明表 class Transaction Base tablename transactions id Column Integer primary key True account id Column Integer
  • Request.Url.Authority 未返回预期的域

    我正在网站的控制器中生成一封电子邮件 其中包含指向我的网站的链接 http Request Url Authority some page 当我在本地计算机上测试它时 这是有效的 返回localhost 12345 和生产中 返回www c
  • Angular 6 httpClient 使用凭据发布

    我有一些代码可以发布一些数据来创建数据记录 它在一个服务中 这是代码 import Injectable from angular core import HttpClient HttpHeaders from angular common
  • CakePHP 2.1 测量页面执行时间

    如何测量 CakePHP 2 1 中的页面执行时间 在 1 3 中 它在调试模式下呈现在代码中 你可以使用调试工具包插件 https github com cakephp debug kit找出执行时间 或者您可以在 app 中编辑 ind
  • 在 Windows 10 IoT 上使用 UWP 进行 LDAP 查询

    经过几个小时的搜索后 似乎无法从 UWP 应用程序查询本地 LDAP 目录 Microsoft Active Directory 或其他 这似乎是 UWP 产品中的一个相当奇怪的漏洞 因此我希望我只是错过了明显的漏洞 通用 Windows
  • 如何在构建的电子应用程序中获取开发工具?

    是否可以在构建的电子应用程序中显示开发工具 我使用构建的可执行文件electron packager与使用运行的应用程序的行为不同electron在命令行中 我无法看到抛出了哪些类型的异常 是的 可以在打包的应用程序中显示 DevTools
  • Android:单击时更改按钮颜色

    基本上 我正在尝试创建一个单击时的按钮 注意 NOT按下 会将颜色从 color1 更改为 color2 再次单击时 颜色将从 color2 变回 color1 我疯狂地搜索 我设法提取的唯一信息是如何在按下按钮时改变颜色 即当用户按住按钮
  • 将构造函数添加到 deftype 创建的类中

    为了与 Java 实现互操作性 我需要一个具有执行初始化的空构造函数的类 此类的对象需要具有类似于可变java字段的东西 即该对象代表游戏的后端 并且需要保持游戏状态 deftype 确实一切我想要做except提供一个无效构造函数 因为我
  • 如何检索高质量的指南针方向(如 Google 地图)?

    我发现的所有在 Android 中获取指南针方向的指南都有一个错误 当您以纵向模式握住手机并 看 地平线上方时 指南针箭头会从正确方向旋转 180 度 谷歌地图方向指示器不存在这个问题 谷歌地图的另一个好处是它们可以以某种方式估计指南针的准
  • Vue.js 对数组进行过滤

    我正在尝试使用 vue js 中的计算属性来过滤数组 我想搜索多个字段 名称 状态 标签等 My data events id 1 name Name of event url datetime 2017 05 10T00 00 00Z d
  • 不完整类型的静态字段 - 合法吗?

    在 C 中声明在类定义时不完整的类型的静态字段是否合法 例如 Foo h class Foo public private class Bar static Bar something Foo cpp class Foo Bar Foo B
  • 标准对 char 数组作为模板参数有何规定?

    在我研究答案的过程中这个问题 https stackoverflow com q 57003010 9883438我发现 我之前不知道 gcc 和 clang 允许char如果声明了数组 则它们将成为模板参数static 例如 此代码使用