2011-04-12 71 views
8

如何從流輸入枚舉類型?輸入從流到枚舉類型

我能做到這樣

unsigned int sex = 0; 
stream >> sex; 
student.m_bio.sex = static_cast<Sex>(sex); 

否則?

回答

13
inline std::istream & operator>>(std::istream & str, Sex & v) { 
    unsigned int sex = 0; 
    if (str >> sex) 
    v = static_cast<Sex>(sex); 
    return str; 
} 

如果你想確保該值是有效的,你可以做這樣的事情:

enum Sex { 
    Male, 
    Female, 
    Sex_COUNT 
}; 

inline std::istream & operator>>(std::istream & str, Sex & v) { 
    unsigned int sex = 0; 
    if (!(str >> sex)) 
    return str; 
    if (sex >= Sex_COUNT) { 
    str.setstate(str.rdstate() | std::ios::failbit); 
    return str; 
    } 
    v = static_cast<Sex>(sex); 
    return str; 
} 
+0

我認爲你的意思'V =的static_cast (性);'......也就是說,參數的演員是「性」,而不是「v」。 :D – Nawaz 2011-04-12 10:34:02

+0

@Nawaz:是的,更正了,謝謝。 – Erik 2011-04-12 10:35:00

+0

這個答案缺少'return str;'。 – 2011-04-12 10:35:04

3

這個問題是問一個更一般的形式在這裏:How to read enums from a std::istream in a generic fashion。 OP幾乎有一個工作的解決方案,因爲它是;他在const和一些不必要的尖括號中遇到了一些麻煩。這裏的工作解決方案躍然紙上:

#include <iostream> 
#include <type_traits> 

enum enSide { eLeft, eRight }; 
enum enType { eConUndefined, eConRoom }; 

template<typename Enum> 
class EnumReader 
{ 
    Enum& e_; 

    friend std::istream& operator>>(std::istream& in, const EnumReader& val) { 
     typename std::underlying_type<Enum>::type asInt; 
     if (in >> asInt) val.e_ = static_cast<Enum>(asInt); 
     return in; 
    } 
    public: 
    EnumReader(Enum& e) : e_(e) {} 
}; 

template<typename Enum> 
EnumReader<Enum> read_enum(Enum& e) 
{ 
    return EnumReader<Enum>(e); 
} 

class MyClass { 
    enSide mSide; 
    enType mType; 
    int mTargetId; 
    public: 
    friend std::istream& operator>>(std::istream& in, MyClass& val) { 
     in >> read_enum(val.mSide) >> read_enum(val.mType) >> val.mTargetId; 
     return in; 
    } 
}; 

read_enum函數模板這裏有異曲同工之妙的std::make_pair或標準庫std::make_shared:它讓我們用尖括號免除。你同樣可以寫in >> EnumReader<enSide>(val.mSide) >> EnumReader<enType>(val.mType),但這是更多的打字(雙關意圖)。

據稱一些供應商的標準庫仍然從其<type_traits>標頭中缺少std::underlying_type。如果您有其中一個不完整的庫,則可以使用How to know underlying type of class enum?中列出的其中一種解決方法。

0

這是不漂亮,但要做到這一點

stream >> reinterpret_cast<std::underlying_type<Sex>::type &>(student.m_bio.sex); 

乾杯, CC