为什么我可以在 constexpr 函数内调用非 constexpr 函数?

2024-01-30

考虑以下代码:

#include <stdio.h>

constexpr int f()
{
    return printf("a side effect!\n");
}

int main()
{
    char a[f()];
    printf("%zd\n", sizeof a);
}

我本以为编译器会抱怨调用printf inside f, 因为f应该是constexpr, but printf不是。为什么程序编译并打印15 https://ideone.com/QNL5u8?


该计划是不规范的并且不需要根据以下诊断C++11 标准草案 http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3485.pdf部分7.1.5 constexpr 说明符段落5其中说:

对于 constexpr 函数,如果不存在这样的函数参数值 函数调用替换会产生一个常量 表达式(5.19),程序格式错误;无需诊断。

并提供以下示例:

constexpr int f(bool b)
  { return b ? throw 0 : 0; } // OK
constexpr int f() { return f(true); } // ill-formed, no diagnostic required

和部分5.19段落2 says:

条件表达式是核心常量表达式,除非它 涉及以下内容之一作为潜在评估的子表达式 [...]

包括:

— 调用除 constexpr 构造函数之外的函数 文字类或 constexpr 函数 [注意:重载解析 (13.3)照常应用——尾注];

在这种情况下,我们可能更喜欢进行诊断,这可能只是一个疏忽,我有一个类似情况的错误报告,其中gcc不会产生错误,但我们可能希望它:编译器在常量表达式中认为未定义的行为是否允许有余地? https://stackoverflow.com/questions/21502017/is-the-compiler-allowed-leeway-in-what-it-considers-undefined-behavior-in-a-cons.

Update

使用-fno-builtin标志将导致gcc产生以下错误:

 error: call to non-constexpr function 'int printf(const char*, ...)'
 return printf("a side effect!\n");
                                 ^

So gcc确实考虑到这一点不规范的当它使用内置版本时它只是忽略它printf.

虽然使用起来有些不一致-pedantic产生以下警告:

warning: ISO C++ forbids variable length array 'a' [-Wvla]
 char a[f()];
           ^

请注意,使用f()初始化一个常量表达式多变的:

constexpr int x = f() ;

确实会产生错误:

error: 'printf(((const char*)"a side effect!\012"))' is not a constant expression

请注意,另外在更一般的情况下,不允许编译器将标准库函数标记为常量表达式 除非标准明确允许 https://stackoverflow.com/q/27744079/1708801.

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

为什么我可以在 constexpr 函数内调用非 constexpr 函数? 的相关文章

随机推荐

  • 在不使用索引的情况下替换 pandas DataFrame 中选定单元格的值

    这是一个非常相似的问题这个问题 https stackoverflow com questions 13842088 set value for particular cell in pandas dataframe但有一个关键的区别 我选
  • GitHub:如何将开放的拉取请求添加到本地存储库?

    我正在使用NSDate 扩展 https github com erica NSDate Extensions我的 iOS Xcode 项目中的插件 主存储库有一些错误 似乎在两个 Pull 请求中得到了修复 https github co
  • django TypeError:get() 获得关键字参数“invoice_id”的多个值

    我对 python 和 django 比较陌生 我有以下其余 api 视图 class InvoiceDownloadApiView RetrieveAPIView This API view will retrieve and send
  • 缺少rabbitMQ配置文件

    我正在使用 Rabbitmq 3 7 2 和 Erlang 20 2 并且 bydefualt RMQ 配置文件丢失 在以下路径 C Users vxadmin AppData Roaming RabbitMQ config 基于我采取的步
  • 在 Android 上添加的文件夹通过 USB 不可见

    我正在尝试将图片保存在 Android 上的子文件夹中 这是我的一些代码 File path Environment getExternalStoragePublicDirectory Environment DIRECTORY DCIM
  • R - 按列名 AS CHARACTER 对 data.frame 进行排序

    我知道我可以这样订购 data frame test data frame A c 4 2 4 B c 8 3 2 ordered test with test order A B 但是 当列由列名指定为字符变量时 如何完成同样的事情呢 这
  • Lua - 初始化[重复]

    这个问题在这里已经有答案了 我无法在 Arch Linux 下正确初始化 lua Lua 最新版本 这是我的代码 include
  • 为特定风格和 buildType 定义 buildconfigfield

    我有两种口味 比如说香草和巧克力 我还有 调试 和 发布 构建类型 并且我需要 Vanilla Release 的字段为 true 而其他 3 个组合应该为 false def BOOLEAN boolean def VARIABLE VA
  • 检测 window.location 的变化

    我正在尝试检测 window location 中的更改 例如 如果用户尝试重新加载页面 则会收到通知 但我似乎找不到方法来做到这一点 有一些与之相关的事件吗 Thanks The unload当用户离开页面时触发该事件 还有一个befor
  • 异步/同步 JavaScript

    我在理解异步和同步 Javascript 之间的区别时遇到了一些困难 希望有人能对此有所了解 我知道 Javascript 本质上是同步的 但您可以使用异步事件 回调来改变程序流程 但是 如果您调用包含 AJAX 且没有回调的函数 会发生什
  • 通过 url 将参数传递给 python azure 函数

    我试图通过 azure 函数使 hello world 示例适用于 python 基本函数尝试通过 url 检索输入的名称 然后响应 Hello Name 事实证明 通过天蓝色门户提供的示例模板不能开箱即用 基本示例如下所示 import
  • 在 SwiftUI 中根据宽度计算每行的项目数

    这是我之前问题的延伸 在 SwiftUI 中使用获取视图的宽度 https stackoverflow com questions 57577462 get width of a view using in swiftui 57591483
  • apache 到 tomcat:mod_jk 与 mod_proxy

    使用有什么优点和缺点mod jk and mod proxy用 apache 来处理 tomcat 实例 我多年来一直在生产中使用 mod jk 但我听说这是前端 tomcat 的 旧方法 我应该考虑改变吗 会有什么好处吗 这些模块的优缺点
  • 触摸屏平板电脑上的 WPF Scrollviewer

    我正在编写一个 WPF 应用程序 它将在完整的 Windows 8 触摸屏平板电脑 而不是 RT 上运行 但是触摸滚动似乎不起作用 所以我想知道我是否做错了什么或者是否有可能 所以 我有一个带有滚动查看器的 WPF 窗口 在该滚动查看器中
  • pandas 3x3 散点矩阵缺少标签

    我使用以下代码创建一个 pandas 散点矩阵 import numpy as np import pandas as pd a np random normal 1 3 100 b np random normal 3 1 100 c n
  • Jenkins 环境变量在构建后步骤中可用

    据我所知 Jenkins 在构建执行期间设置了某些环境变量 但我的问题是我可以在构建后脚本中访问这些变量吗 我进行了快速测试 但无法从构建后步骤 python 脚本访问 PROJECT NAME 和 BUILD URL 等 有没有办法可以从
  • 如何在linq中直接执行SQL查询

    在 C 和 VS 2008 中 我有一个查询 在这个查询中我连接了多个表 所以我不知道类型 我想知道如何在 linq 中直接运行 sql 查询 IEnumerable
  • tomcat中connectionTimeout的含义

    这个参数对于tomcat来说意味着什么 它被宣布于server xml如下
  • OpenCV K 均值 (kmeans2)

    我正在使用 Opencv 的 K means 实现来对一大组 8 维向量进行聚类 它们聚类得很好 但我找不到任何方法来查看聚类过程创建的原型 这可能吗 OpenCV 似乎只提供对集群索引 或标签 的访问 如果没有 我想是时候自己实现了 我不
  • 为什么我可以在 constexpr 函数内调用非 constexpr 函数?

    考虑以下代码 include