gpt4 book ai didi

c# - 在编译时评估表达式

转载 作者:太空狗 更新时间:2023-10-29 21:32:57 25 4
gpt4 key购买 nike

我知道很多人都问过这个问题,但仅限于 C/C++ 和 Java。这个问题与使用常量表达式的性能优势有关:

当我调用一个仅使用常量作为参数的静态函数时,有没有办法告诉编译器它应该在编译时评估调用并用结果替换调用?

示例:

const double pi = Math.PI; //works as Math.PI is a constant  
const double spi = Math.Sin(Math.PI); //compiler error, because expression must be constant

是否没有指令(更好:属性)明确地告诉编译器像 Math.Sin() 这样的静态方法不会在内部修改或读取任何数据,以便在技术上可以在编译时评估调用?

哦,请不要像“只做const double spi = 0”这样的回答:),因为我的示例只是我遇到的问题的简化版本:提高代码可维护性,同时保持最佳性能。

感谢您的帮助 - 非常感谢!

最佳答案

对于数字常量,我看到两个选项:

选项一:使用static readonly(启动时计算一次):

class MyCalc
{
private static readonly double spi = Math.Sin(Math.PI);
private static readonly double pi = Math.PI;

public void Execute()
{
// .. whatever
}
}

选项二:使用袖珍计算器进行计算并对这些常量进行硬编码:

class MyCalc
{
// Math.Sin(Math.Pi)
private const double spi = 0;
// Math.Pi
private const double pi = 3.141592653589793;

public void Execute()
{
// .. whatever
}
}

我不确定,如果编译器可以在计算中完全优化选项一,但它应该是最可读和可维护的方式。

如果您希望在编译时做尽可能多的事情,事情就会变得更难。在 C++ 下你有模板。我发现它们写起来很麻烦,但人们得到了 amazing things完成它。使用 compile time functions 似乎变得更容易了但我还没有尝试过。 D有CTFE这真的很强大。但 D 是一个小众市场,我会避免在其中编写任何严肃的代码。我不知道其他语言有相当多的显式预编译评估,但我确信有一些。

如今的编译器非常聪明。编译器很有可能会看到机会在没有提示的情况下内联优化函数调用。使用 DotNet 4.5,我们得到了 AggressiveInlining -attribute 这样我们就可以强制编译器进入正确的方向。 C/C++ 有类似的东西并且有 problems .我这边的一般建议是避免内联,直到您确切地知道自己在做什么。

如果您真的不想从 C# 走这条路,我认为最好的选择是使用上述功能在 C++ 中编写您的功能,编写一个易于使用的 C 接口(interface)并通过 PInvoke 调用它。 .但是,如果真的值得,请先帮自己一个忙并衡量一下。永远不要忘记两个优化规则:

  1. 不要
  2. 还没有(仅限专家)

关于c# - 在编译时评估表达式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33518474/

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