2015-06-08 158 views
0

在當前狀態下,程序驗證數據類型的輸入:int和string。函數模板重載(不同數據類型驗證函數作爲參數)

//valid score range between 0 and 100 
bool validScore(int value) 
{ 
    if(value < 0 || value > 100) 
     return false; 
    return true; 
} 
//valid name composed of letters 
bool validName(string word) 
{ 
    for(int i = 0; i < word.length(); i++) 
    { 
    if(!isalpha(word[i])) 
     return false; 
    } 
    return true; 
} 

輸入是通過兩種函數爲每種數據類型獲取的:get_int()和get_word()。

對於int範圍未指定且名稱可能包含任何字符的情況,驗證函數是可選參數。

bool get_int(const string&, int&, bool(*validScore)(int) = 0); 
bool get_word(const string&, string&, bool(*validWord)(const string) = 0); 

// bool get_int(const string& prompt, int&n, (*validScore)(int)) 
bool get_word(const string& prompt, string&word, bool(*validWord)(const string)) 
{ 
    while(1) 
    { 
    string line; 
    cout << prompt; 

    if(!getline(cin, line) 
     break; 

    istringstream iss(line); 

    if(iss >> word) // iss >> n 
    { 
     // validScore == 0 || validScore(n) 
     if(validWord == 0 || validWord(word)) 
     return true; 
    } 
    } 
    return false; 
} 

我在想,如果可能的話,如何正確聲明一個函數模板,可以簡化流程時需要驗證。

template<typename T> bool get_item(const string&, T&, ???); 

將函數模板get_item重載與不同的驗證函數是一個潛在的解決方案嗎?

+0

好像你只是想要一個模板函數'valid(const T&)',它只支持它所支持的類型的專門化? – dwcanillas

回答

3

如果你很喜歡函數指針,然後

template<typename T> bool get_item(const string&, T&, bool (*)(const T&) = nullptr); 

template<typename T> bool get_item(const string&, T&, bool (*)(T) = nullptr); 

,以匹配您的valid*功能存在的簽名(注意,這會招致複印件)。

你也可以把它完全通用:

template<typename T, typename F> bool get_item(const string&, T&, F); 

來處理情況,不需要驗證的情況下,單獨的過載,可以用:

template<typename T> bool get_item(const string &s, T &t){ 
    return get_item(s, t, [](const T&){return true;}); 
} 
+0

你應該改爲「如果你真的喜歡函數指針語法。」通用版本仍然使用函數指針(如果通過的話)。在沒有傳遞函數指針的情況下,原始版本也不起作用(除了函子提供相應轉換操作符的小部分情況外)。 – Columbo

+0

我有時使用'[](T const&) - > std :: true_type {return {};}'作爲額外的提示給優化器。不知道它有什麼不同。 – Yakk

0

以驗證作爲模板類型:

template<class T> 
bool get_item(const string& prompt, T& item); 

template<class T, class Validator> 
bool get_item(const string& prompt, T& item, Validator validator); 

這裏有一個隱含的模板策略,可以調用Validator用T並返回一個布爾值。由於C++還沒有的概念,你可以評論模板策略。

相關問題