gpt4 book ai didi

MSVC 19.37 doesn't consistently warn on assignment in if statements(MSVC 19.37在IF语句中的赋值时不一致地发出警告)

转载 作者:bug小助手 更新时间:2023-10-28 13:26:00 24 4
gpt4 key购买 nike



A colleague prefers Yoda Conditionals:

一位同事更喜欢尤达的条件:



if (0 == x) // as a safer alternative to (x == 0), to prevent the typo (x = 0)


This is a controversial style in the team, and one argument brought up against it is that compilers can consistently emit warnings to detect the buggy pattern if (x = 0).

这在团队中是一种有争议的风格,并且提出的一个论点是,如果(x=0),编译器可以一致地发出警告来检测错误模式。


However, MSVC doesn't appear to detect this pattern for classes (https://godbolt.org/z/qqo9ee5n5):

然而,msvc似乎没有检测到类(https://godbolt.org/z/qqo9ee5n5):)的这种模式


struct wrapper {
int x;
operator int();
};

void foo(wrapper w, int x) {
if (w = wrapper{}) {} // OK ?!
if (x = 0) {} // warning C4706: assignment within conditional expression
}

Am I doing something wrong? Is this a known bug? I have enabled /Wall, but maybe there is some other flag I am missing. IntelliSense also doesn't detect this.

我是不是做错了什么?这是一个已知的错误吗?我已经启用了/WALL,但可能还缺少其他标志。智能感知也不会检测到这一点。


If there is no way to detect this with MSVC and IntelliSense, how can I flag this automatically?

如果没有办法用MSVC和智能感知检测到这一点,我如何自动标记这一点?




Note: I am aware that if this was compiled in a CI with multiple compilers, one of them ought to catch it. However, the goal is to detect this issue locally (ideally with a linter).

注意:我知道,如果这是在具有多个编译器的CI中编译的,其中一个应该会捕获它。但是,目标是在本地检测此问题(理想情况下使用短绒)。




Update: it's becoming clear that I haven't simply missed some flag, so I have submitted a bug report in the Microsoft Developer Community.

更新:越来越明显的是,我并没有简单地错过一些标志,所以我在微软开发人员社区提交了一份错误报告。


更多回答

Looks like an issue, to me. Even running the in-built static code analysis doesn't give a warning on the w assignment. Although, for that line, Yoda won't help: using if (wrapper{} = w) {} also generates no warning.

在我看来,这是个问题。即使运行内置的静态代码分析,也不会对w赋值发出警告。不过,对于这一行,Yoda不会有帮助:使用if(wrapper{}=w){}也不会生成任何警告。

One idiosyncratic alternative I've seen is void return for assignment, void operator=(wrapper const& from) { x = from.x; }, on the basis it prevents this very problem, and doing idiomatic return *this; for chaining is—arguably—a bad thing. Better than yoda conditionals, imo.

我见过的一种特殊的替代方法是为赋值而返回的VOID,VOID运算符=(包装器const&from){x=From.x;},因为它防止了这个问题,而进行惯用的返回*This;对于链接来说--可以说--是一件坏事。比尤达条件赛好,国际海事组织。

@Eljay you can't explicitly default an assignment operator which returns void (and it's not the default implementation in the first place), so this seems unattractive. It does catch the bug, but with some cost. Would you actually do this for simple structs that otherwise wouldn't have needed any assignment operator definition?

@eljay您不能显式地默认返回空的赋值操作符(而且这本来就不是默认的实现),所以这看起来并不吸引人。它确实抓住了这个漏洞,但要付出一些代价。对于原本不需要任何赋值操作符定义的简单结构,您真的会这样做吗?

The clang-cl compiler that you can (optionally) install in Visual Studio flags it: warning : using the result of an assignment as a condition without parentheses [-Wparentheses] Perhaps not really an ideal solution, but I have my major projects set up with a "use clang-cl" configuration that I run from time to time, just to get other/extra warnings like this.

您可以(可选地)安装在Visual Studio中的clang-cl编译器对其进行标记:警告:使用赋值结果作为不带括号的条件[-Wparenkets]可能不是一个理想的解决方案,但我的主要项目设置了“use clang-cl”配置,我不时地运行该配置,只是为了得到其他/额外的警告。

@Osyotr that would be a declaration inside an if statement, which is perfectly fine. It wouldn't be fine if you wrote if (p = GetObject()) because it's likely a typo and it was meant to be if (p == GetObject()). Compilers should warn you unless you parenthesize it like if ((p = GetObject()) to express intent. The problem is that MSVC fails to warn in some cases.

@Osyotr这将是if语句中的声明,这是完全没有问题的。如果您写的是if(p=GetObject()),那就不好了,因为它很可能是一个打字错误,本来应该是if(p==GetObject())。编译器应该警告您,除非您像if((p=GetObject()那样将它括起来以表示意图。问题是,在某些情况下,MSVC未能发出警告。

优秀答案推荐
更多回答

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com