![](/img/trans.png)
[英]What is Cmake file and why do we use it when we have VIsual studio
[英]What's the use of <ratio> when we have contexpr values?
<ratio>
header 允許您使用模板元編程來處理和操縱理性值。
然而 - 它是在 C++11 中引入的,當時我們已經有了constexpr
。 為什么為有理數提供一個完全構造的庫類型還不夠好,即基本上:
template<typename I>
struct rational {
I numerator;
I denominator;
};
並改用它?
使用std::ratio
是否有一些具體的好處,而 C++11 constexpr 功能還不夠適合? 如果是這樣,它在 C++20 中是否仍然相關(隨着 constexpr 的擴展“范圍”)?
使用 std::ratio 是否有一些具體的好處,而 C++11 constexpr 功能還不夠適合?
您可以將ratio
作為模板類型參數傳遞,這就是std::chrono::duration
所做的。 要使用基於值的比率來做到這一點,您需要 C++20 或更新版本。
在 C++20 和更新版本中,我看不到當前設計的任何好處。
這里有幾個答案和評論,但我認為它們都沒有真正說明std::ratio
的要點。 讓我們從std::ratio
的定義開始。 它大致相當於:
template<int Num, int Den>
struct ratio {
static constexpr int num = Num;
static constexpr int den = Den;
};
不過,您可能可以用作std::ratio
的替代方法,如下所示:
template<typename I>
struct ratio {
I num;
I den;
};
使用一堆constexpr
函數來執行該類型的算術運算。
請注意,這兩個定義之間存在細微但非常重要的區別。 而在第二個定義中,比率的實際值( num
和den
)存儲在類型的實例中,而在第一個定義中,值實際上存儲在類型本身中。
如果你有一個像std::chrono
這樣的庫,你想要一個類型,它可以將時間存儲為毫秒數(例如std::chrono::milliseconds
)。 如果您稍后想將此數字轉換為秒,則不希望將轉換比率編碼到std::chrono::milliseconds
的實例中,而是編碼到類型本身中。 這就是為什么std::chrono
使用第一種形式而不是第二種形式(或簡單的浮點值)的原因。
要將數字存儲到類型而不是實例中,您需要一個非類型模板參數。 在 C++20 之前,您只能對非類型模板參數使用整數值。 盡管如此,為了將合理的轉換因子存儲在標准庫中,指定了std::ratio
class 模板。
在 C++20 中,潮流發生了一點變化,因為您現在可以使用浮點數作為非類型模板 arguments。例如, std::chrono::duration
可以重寫為:
template<..., double conversion_factor, ...>
duration {
...
};
但是,此 C++20 功能與您在問題中提到的“constexpr 的擴展范圍”無關。 編譯時間計算不同於在類型本身中存儲數值,盡管您需要第一個來執行第二個。
使用std::ratio
class 模板(專門)用於將值存儲到類型中。
boost::rational
與boost::ratio
大約同時提供。 然而,由於后者被boost::chrono
使用,而后者又被boost::thread
使用,因此將整個束一起添加到標准中更容易。 如果要尋找一個成熟的運行時可用有理數 class, boost::rational
就在那里。 boost::multiprecision
也可用於提供非常長的整數類型作為boost::rational
的參數。 關於boost::random
等 boost 其他部分的標准化,對我來說,為什么boost::rational
尚未添加到標准庫中一直是個大問題。
問候,調頻。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.