[英]Computing the factorial of a small integer at compile time
我剛剛(再次)實現了一個遞歸模板,用於在編譯時計算整數的階乘(誰曾想過有一天我真的需要它!)。 盡管如此,我還是去找Boost尋找答案,而不是自己動手。 但是,特殊數學中的階乘函數特別禁止它使用整數類型,所以我只寫了自己的。
仍然,我應該使用Boost中的另一個功能嗎? 我應該將我的整數轉換為double
並使用boost::factorial
函數嗎? 計算是在編譯時執行的嗎?
你不需要Boost,如果你有C ++ 11,這只是1-liner:
constexpr uint64_t factorial(uint64_t n) {
return n == 0 ? 1 : n * factorial(n-1);
}
即使你的arg也不是編譯時間常量,它也會工作。 uint64_t適用於n <21。
如果您在編譯時執行此操作並乘以浮點值 - 則不會產生轉換開銷(轉換也將在編譯時進行)。
由於可以在整數內部使用有限數量的因子,因此您可以手動預先計算前20個值並將它們存儲在全局或靜態數組中。 然后使用全局或靜態函數來查找數組中的階乘:
#include <iostream>
const int factorials[] =
{
1,
1,
2,
6,
24,
// etc...
};
inline const int factorial(int n) {return factorials[n];}
int main()
{
static const int fourFactorial = factorial(4);
std::cout << "4! = " << fourFactorial << "\n";
}
如果使用文字作為factorial
的參數,則編譯器應該簡單地用函數調用替換結果(啟用優化時)。 我在XCode 4.4中嘗試了上面的例子(在Mac上),我在程序fourFactorial
看到它用常量24初始化了fourFactorial
:
.loc 1 20 38 ## /Users/emile/Dev/sandbox/sandbox/main.cpp:20:38
movl $24, __ZZ4mainE13fourFactorial(%rip)
與使用遞歸編譯時技巧相比,此方法可能導致更快的編譯。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.