__assume 的一些示例会导致比“无默认值”更快的代码在开关?

发布于 2024-09-07 07:43:15 字数 298 浏览 2 评论 0原文

__assume 的文档表示“__assume 最常见的用法是使用 switch 语句的默认情况,如以下示例所示。 ”。

  • 是否有任何其他情况下 __assume 可以导致更高效(甚至不同)的代码?
  • 当在 if / else 内部时,编译器是否不会由于 if 条件而自动“假设”已知的内容?

我无法找到任何显示上述任何内容的重要示例 - 我希望其他人可以。

The documentation for __assume says "The most common use of __assume is with the default case of a switch statement, as shown in the following example.".

  • Is there any other case where __assume can lead to more efficient (or even different) code?
  • When inside of an if / else, isn't the compiler automatically "assuming" what is already known because of the if condition?

I was unable to find any non-trivial examples that show any of above - I hope someone else could.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

昨迟人 2024-09-14 07:43:16

请考虑使用 /Ox< 编译的以下代码/a> 开关:

if (1) {
  printf("live code\n");
} else {
  printf("dead code\n");
}

优化器将优化掉 else。现在考虑一下:

int x = 1;
if (x == 1) {
  printf("live code\n");
} else {
  printf("dead code\n");
}

优化器将再次优化掉else。还要考虑:

int x = 1;
__assume(x != 1);
if (x == 1) {
  printf("live code\n");
} else {
  printf("dead code\n");
}

优化器这次将优化掉 if ——这是错误的。

要进行测试,请在发布模式下构建一个测试程序(使用 /Ox/Zi 选项)并查看生成的程序集(在 Visual Studio 中为 Alt+8)。

现在考虑在内联方法中测试上述 if/else 条件。在某些情况下,程序员可能知道内联方法是使用特定值调用的,而优化器可能没有意识到这一事实。在调用内联方法之前,按照上面所示的方式在调用者级别使用 __assume 理论上可以帮助优化器。

来自优化最佳实践(引自旧版本) :

__assume 已在 Visual C++ 中使用了
多次发布,但已成为
在 Visual C++ 2005 中更有用。
通过 __assume,开发人员可以判断
编译器做出假设
某个变量的值。

例如 __assume(a < 5);告诉
优化器在那行代码
变量 a 小于 5。再次
这是对编译器的承诺。如果
此时 a 实际上是 6
然后编程的行为
编译器之后的程序
优化可能不是你想要的
预计。 __assume 在之前最有用
切换语句和/或
条件表达式。

有一些限制
__认为。首先,像__restrict一样,它只是一个建议,所以编译器
可以随意忽略它。另外,__假设
目前仅适用于变量
常数的不等式。它
不传播象征性
例如,不等式假设(a <
b).

Consider the following code, compiled with the /Ox switch:

if (1) {
  printf("live code\n");
} else {
  printf("dead code\n");
}

The optimizer will optimize away the else. Now consider:

int x = 1;
if (x == 1) {
  printf("live code\n");
} else {
  printf("dead code\n");
}

The optimizer will once again optimize away the else. Also consider:

int x = 1;
__assume(x != 1);
if (x == 1) {
  printf("live code\n");
} else {
  printf("dead code\n");
}

The optimizer will optimize away the if this time -- incorrectly so.

To test, build a test program in Release mode (with the /Ox and /Zi options) and look at the generated assembly (Alt+8 in Visual Studio.)

Now consider the above if/else condition being tested in an inline method. In certain contexts, the programmer may know that the inline method is called with a particular value and the optimizer may not have realized this fact. Using __assume at the caller level in the manner illustrated above, just before the inlined method is called, can theoretically help the optimizer.

From Optimization Best Practices (quote from older version):

__assume has been in Visual C++ for
multiple releases, but it has become
much more usable in Visual C++ 2005.
With __assume, a developer can tell
the compiler to make assumptions about
the value of some variable.

For example __assume(a < 5); tells the
optimizer that at that line of code
the variable a is less than 5. Again
this is a promise to the compiler. If
a is actually 6 at this point in the
program then the behavior of the
program after the compiler has
optimized may not be what you would
expect. __assume is most useful prior
to switch statements and/or
conditional expressions.

There are some limitations to
__assume. First, like __restrict, it is only a suggestion, so the compiler
is free to ignore it. Also, __assume
currently works only with variable
inequalities against constants. It
does not propagate symbolic
inequalities, for example, assume(a <
b).

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文