2012-02-13 123 views
4

我有一個功能:bool inBounds(int value, int low, int high)。是否有一個STL等價物可以做有用的事情(特別是不同類型的變量)?我找不到使用Google的人,我寧願重複使用,而不是重新編寫。STL函數來測試一個值是否在某個範圍內?

+0

也許我建議'within'作爲一個簡單的名字嗎? – 2012-02-13 07:04:10

回答

10

在C++ 14,有這樣的功能沒有直接等同,但對於較小型快速平等的比較,你可以使用std::clamp

if (val == std::clamp(val, low, high)) { 
    ... 
} 

或者,你可以只寫你自己的功能測試此:

template <typename T> 
    bool IsInBounds(const T& value, const T& low, const T& high) { 
    return !(value < low) && (value < high); 
} 

該檢查,如果是value在範圍[低,高)。如果你想的範圍[低,高],你會寫爲

template <typename T> 
    bool IsInBounds(const T& value, const T& low, const T& high) { 
    return !(value < low) && !(high < value); 
} 

注意這是如何的operator <方面純粹定義,這意味着任何支持類只是operator <可以在這裏使用。

同樣,這裏有一個使用自定義的比較:

template <typename T, typename R, typename Comparator> 
    bool IsInBounds(const T& value, const R& low, const R& high, Comparator comp) { 
    return !comp(value, low) && comp(value, high); 
} 

後者一個具有很好的優勢lowhigh不必是同一類型爲value,只要比較可以處理它會工作得很好。

希望這會有所幫助!

+0

謝謝。我仍然試用模板 - 這些例子非常感謝。 – simont 2012-02-13 05:18:52

+0

是包含性的下限/排他性上限故意嗎? – tzaman 2012-02-13 05:20:21

+0

@ tzaman-我只是假設這就是想要的。如果需要不同的邊界,我會發布更新。 – templatetypedef 2012-02-13 05:20:47

0

我幾乎認爲你最好不要試圖用整個函數來完成這樣一個看似平凡的任務,而只是內聯行爲。

事情是這樣的:

1 #include <iostream> 
    2 
    3 int main() { 
    4  int value = 5; 
    5  bool inside = false; 
    6  int lower = 0; 
    7  int upper = 10; 
    8  inside = lower < value && value < upper; 
    9  printf("inside: %d", inside); 
10  return 0; 
11 } 

如果你不寫代碼只是這樣的理由,請讓我知道,我可以提供一個更復雜的答案。

+1

您需要修正第8行:'lower templatetypedef 2012-02-13 05:19:58

+0

這不是一個關於我的情況的表現,我只是很難用目前可用的信息將其抽象化。 – bitemyapp 2012-02-13 05:25:51

+0

我目前正在使用它來檢查4個值,它出現在一個相當大的'if'語句中 - 如果將測試包裝到一個函數中,讀取起來更容易,而且印刷失敗的可能性也更小。 – simont 2012-02-13 05:27:23

4
bool inBounds(int value, int low, int high) 

有一個小小的缺點,你必須記住哪個參數去哪裏。
我不能成爲唯一一個完美合理的參數順序在一段時間後返回代碼時撲朔迷離的人。

你可以多走一英里,並定義

template<typename T> 
class Interval 
{ 
public: 
    Interval(T lo, T hi) : low(lo), high(hi) {} 
    bool contains(T value) const { return low <= value && value < high; } 
private: 
    T low; 
    T high; 
}; 
template<typename T> 
Interval<T> interval(T lo, T hi) { return Interval<T>(lo, hi); } 

然後你就可以更加明確你的意思:

if (interval(a, b).contains(value)) 
    // ... 

如果一個抽象模式下,它不是太難推廣到可容納不同的包容性/獨特組合。

當然這可能是爲你的目的矯枉過正。
YMMV,等等。

1

你可以從std::less,std::more,std::bindstd::compose組成一個,但這確實是矯枉過正。

拉姆達的要簡單得多:

[](int value, int low, int high){return !(value < low) && (value < high);}

,或者,如果低和高的範圍

[low, high](int value){return !(value < low) && (value < high)};

相關問題