C++14 和 C++17 之间的区别使用:“*p++ = *p”

Difference between C++14 and C++17 using: `*p++ = *p`

本文关键字:p++ C++17 之间 区别 C++14      更新时间:2023-10-16

在编写一些代码时,我遇到了一个问题,即我设置的值设置错误。我最终找到了罪魁祸首,在测试时发现它在 C++14 和 C++17 上的行为不同。代码如下:

#include <stdio.h>
#include <cstdint>
#include <cstring>
int main()
{
    uint8_t *p = new uint8_t[3];
    memset(p, 0x00, 1);
    p++;
    memset(p, 0xF0, 1);
    p++;
    memset(p, 0xFF, 1);
    p--;
    p--;
    // This line in particular
    *p++ = *p;
    *p++ = 0x0F;
    p--;
    p--;
    printf("Position 0 has value %un", *p);
    p++;
    printf("Position 1 has value %un", *p);
    p++;
    printf("Position 2 has value %un", *p);
    return 0;
}

在 C++14 上,它打印:

Position 0 has value 240
Position 1 has value 15
Position 2 has value 255

在 C++17 上,它打印:

Position 0 has value 0
Position 1 has value 15
Position 2 has value 255

我很好奇为什么它在不同的C++版本上有不同的作用。看起来好像在 C++14 上,作业的右侧*p是在++之后评估的。这改变了吗?如果++具有优先级,为什么它没有发生在赋值运算符左侧的取消引用之前?

读取和写入变量(通过后增量(曾经具有未定义的行为,因为=没有引入序列点。您可能在 C++14 中收到行为(或没有,或爆炸(。

现在,为这种情况定义了排序顺序,并且您的 C++17 结果是可靠的。

虽然它仍然很糟糕,但不应该编写的不清楚的代码!