2017-08-10 40 views
3

我使用constexpr得到斐波那契数斐波那契使用constexpr函数(编译时间与运行时间)

枚举用于计算

#include <iostream> 

constexpr long fibonacci(long long n) 
{ 
    return n < 1 ? -1 : 
     (n == 1 || n == 2 ? 1 : fibonacci(n - 1) + fibonacci(n - 2)); 
} 

enum Fibonacci 
{ 
    Ninth = fibonacci(9), 
    Tenth = fibonacci(10), 
    Thirtytwo = fibonacci(32) 

}; 

int main() 
{ 
    std::cout << Fibonacci(Thirtytwo); 
    // std::cout << fibonacci(32); 
    return 0; 
} 

我收到以下错误编译时斐波那契上执行的:

 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(12): note: while evaluating 'fibonacci(30)' 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(6): note: while evaluating 'fibonacci(31)' 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(12): note: while evaluating 'fibonacci(31)' 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(12): error C2131: expression did not evaluate to a constant 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(5): note: failure was caused by control reaching the end of a constexpr function 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(12): note: while evaluating 'fibonacci(32)' 
1>c:\users\hsingh\documents\visual studio 2017\projects\consoleapplication4\consoleapplication4\source.cpp(14): error C2057: expected constant expression 
1>Done building project "ConsoleApplication4.vcxproj" -- FAILED. 

但是当我使用运行时间 INT X = 30,Y = 2 ; 的std ::法院< <斐波纳契(X + Y); //斐波那契是在运行时计算

Run Time with memory

我不会说我有一个问题,但我有一些困惑,如:

  1. 是内存使用的编译时和运行时使用的constexpr不同?
  2. 如何知道停止利用或使用编译时数据的位置?
  3. 我仍然试图做的是如何利用编译时间和运行时间的优势共同完成类似Fibo的计算(使用编译直到可以和之后,让剩余的计算在运行时完成)。

任何示例或参考(如果可用)都将有所帮助。

+0

你是什么意思“当我使用运行时间”?是不是完全相同的代码(减两行)? – user463035818

+0

std :: cout << fibonacci(32);它的运行时间计算 –

+0

可能或可能不是[编译时何时评估constexpr函数?](https://stackoverflow.com/q/14248235/11683) – GSerg

回答

5
  1. 内存的纤维蛋白原在编译使用constexpr功能时间依赖于实现,但通常应该与运行时相比(大多数编译器会编译和执行语句)。

  2. 理论上,您应尽可能使用编译时计算的表达式。在实践中,这是一个判断的呼唤(对SE的问题来说也许是个好主题),因为不利的一面是编译时间增加(可能是内存),缺乏调试。

  3. 看来你已经达到了编译时表达式中MSVC允许的最大递归限制。我找不到有关此限制的任何文档,但可以在其他编译器上配置。您的错误是enum要求在编译时完全评估的结果,因为cout调用允许它在编译时和/或运行时执行(如果生成程序集,则应该看到编译时生成的常量较低的号码呼叫以及用于高数量呼叫的递归功能)。

2

错误的原因是,你正在试图计算Fib数为32的Fib数。这是太多了!

您遇到了constexpr函数递归的最大限制,因此您会看到编译错误。

在运行时程序会崩溃,在这一点上,但它不会因为你的运行表现是不同的 - 这是32

+0

请问您可以添加更多信息我在运行时所犯的错误 –

+0

斐波纳契(32)在enum和cout <<斐波纳契(32)是不是都相同?这两个调用相同的函数 –

+1

@HariomSingh,在枚举'ThirtyTwo'中**已经是**应用于数字'32'的Fib函数的结果。 – SergeyA