使用 `volatile` 会产生意想不到的结果。

huangapple go评论70阅读模式
英文:

Using `volatile` has unexpected results

问题

我对尝试复制不同的错误时发现的以下差异感到困惑。此程序按预期工作:

#include <memory>
#include <string>
#include <iostream>

int main() {
    std::string s = "Hi\n";
    std::cout << s;

    auto p = std::make_unique<const char *>(s.c_str());
    std::cout << *(p.get());

    return 0;
}

它打印:

Hi
Hi

但是添加单个volatile关键字:

#include <memory>
#include <string>
#include <iostream>

int main() {
    std::string s = "Hi\n";
    std::cout << s;

    auto p = std::make_unique<volatile const char *>(s.c_str());
    std::cout << *(p.get());

    return 0;
}

会使其打印:

Hi
1

这也没有帮助:

#include <memory>
#include <string>
#include <iostream>

int main() {
    std::string s = "Hi\n";
    std::cout << s;

    auto p = std::make_unique<volatile const char *>(reinterpret_cast<volatile const char *>(s.c_str()));
    std::cout << *(p.get());

    return 0;
}

为什么?

英文:

I am puzzled by following difference discovered by trying to replicate different bug. This program works as expected:

#include &lt;memory&gt;
#include &lt;string&gt;
#include &lt;iostream&gt;


int main() {
    std::string s = &quot;Hi\n&quot;;
    std::cout &lt;&lt; s;

    auto p = std::make_unique&lt;const char *&gt;(s.c_str());
    std::cout &lt;&lt; *(p.get());

    return 0;
}

It prints

Hi
Hi

But adding single volatile keyword:

#include &lt;memory&gt;
#include &lt;string&gt;
#include &lt;iostream&gt;


int main() {
    std::string s = &quot;Hi\n&quot;;
    std::cout &lt;&lt; s;

    auto p = std::make_unique&lt;volatile const char *&gt;(s.c_str());
    std::cout &lt;&lt; *(p.get());

    return 0;
}

makes it print:

Hi
1

This did not help either:

#include &lt;memory&gt;
#include &lt;string&gt;
#include &lt;iostream&gt;


int main() {
    std::string s = &quot;Hi\n&quot;;
    std::cout &lt;&lt; s;

    auto p = std::make_unique&lt;volatile const char *&gt;(reinterpret_cast&lt;volatile const char *&gt;(s.c_str()));
    std::cout &lt;&lt; *(p.get());

    return 0;
}

Why?

答案1

得分: 4

答案在评论中,由Jarod42提供:

std::ostreamconst char*bool(指针可以转换为bool)重载了运算符<<,但没有重载volatile const char*

然后,可以通过以下方式简单复制差异:

#include <iostream>

int main() {
    /*volatile*/ const char * s = "abc\n";
    std::cout << s;

    return 0;
}

取消注释volatile后,输出为abc,注释它后输出为1(没有换行符)。

英文:

The answer is in the comment by Jarod42:

> std::ostream has overload for operator &lt;&lt; for const char* and bool (pointer has conversion to bool), not for volatile const char *

The difference then can be replicated simply by:

#include &lt;iostream&gt;

int main() {
    /*volatile*/ const char * s = &quot;abc\n&quot;;
    std::cout &lt;&lt; s;

    return 0;
}

Gives abc with volatile commented out and 1 (without newline) with uncommenting it.

huangapple
  • 本文由 发表于 2023年7月12日 23:32:16
  • 转载请务必保留本文链接:https://go.coder-hub.com/76672245.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定