• C# 中枚举的一点研究(跳过一些net的小坑而已)


    之前一直使用Enum.Parse()将字符串转为枚举,没有深究,后面发现一个问题后对下面的Enum有了一个初步研究(.net 4.0).

    枚举是一个指定的常数集,其基础类型可以是除 Char 外的任何整型。 如果没有显式声明基础类型,则使用 Int32。 Enum 是 .NET中所有枚举的基类。

    永远不要创建基础类型为非整形的枚举类型。 虽然可以通过使用反射来创建这一枚举类型,但使用得出的类型的方法调用是不可靠的,也可能会引发其他异常。

    看下面代码.

    (留意,枚举类型是值类型,其值不能为Null,所以我们定义一个枚举类型,其默认值通常为该枚举的第一个元素,或值为0的元素)

    首先定义一个test枚举

    enum test { aaa,bbb,ccc,ddd}

    (1)现在对比Parse方法(留意,parse方法里面value参数是区分大小写的,如果想忽略大小写,一定要使用带ignoreCase参数的覆写方法) private void button1_Click(object sender, EventArgs e) {
    test te;
    string typeStr;

    te = (test)Enum.Parse(typeof(test), "4"); //4
    typeStr = te.GetType().Name; //test
        te = (test)Enum.Parse(typeof(test), "2"); //ccc
    typeStr = te.GetType().Name; //test

        te = (test)Enum.Parse(typeof(test), "ddd"); //ddd
        te = (test)Enum.Parse(typeof(test), "ddd1"); //System.ArgumentException("未找到请求的值“ddd1”。")
    }
    那么看看TryParse方法呢?

    //(留意,TryParse方法未经初始化即被赋值为默认值,如果不想TryParse方法改变Out的枚举值,先调用 IsDefined()(IsDefined对于字符串区分大小写的)方法
    //以确保整数的特定字符串表示形式实际是 TEnum 的成员。)
    test te = test.bbb; 
    if (Enum.TryParse("aaa", out te)) //aaa 返回值为True
     MessageBox.Show(te.GetType().Name); //test
    if (Enum.TryParse("111", out te)) //111 返回值为False
        MessageBox.Show(te.GetType().Name);
    TryParse方法的定义:
    public static bool TryParse<TEnum>(
        string value,
        out TEnum result
    )
    where TEnum : struct
    TryParse方法有点奇特,只要是value能转换为数字,那么一定会成功,如果不能,则根据大小写(默认区分大小写)去转换.不存在就返回false.

    结论,对于Enum.Parse() 方法,即使是想通过TryParse()方法判断返回的bool值,也建议首先使用Enum.IsDefined()判断是否存在.

    (2)Enum.ToObject()方法

    te = (test)Enum.ToObject(typeof(test), 4); //4
    由此可见,ToObject()也同Parse方法一样,对于数值,都不会引发ArgumentException,而转换成功,所以也建议首先使用Enum.IsDefined()判断是否存在.

    (3)Enum.GetValues()方法

      这个方法并不能获取结果为{0,1,2,3}的数组,而是返回和GetNames()方法一样的,只不过GetNames返回值类型为string[].
    如果想获取{0,1,2,3},参考这个方法

    public static Array getValuesArray(Type enumType)
    {
        Array tempArry;
        tempArry = Enum.GetValues(enumType);
        //tempArry = enumType.GetEnumValues();
        Array result = Array.CreateInstance(typeof(int), tempArry.Length);
        int j = 0;
        foreach (int i in tempArry)
        {
            result.SetValue(i, j++);
        }
        return result;
     }
    (4) 一直说用Enum.IsDefined()方法判断是否存在,那么还是看看这个方法吧.
    bool b;
    b = Enum.IsDefined(typeof(test), 3);//True
    b = Enum.IsDefined(typeof(test), 4);//false
    b = Enum.IsDefined(typeof(test), "aaa");//true
    b = Enum.IsDefined(typeof(test), "aaA");//false
    b = Enum.IsDefined(typeof(test), "aaA1");//false
    (5)现在在看看Enum.GetName(Type enumType, Object value)
    方法对于字符串和整形是怎么样处理的
    string s;
    s = Enum.GetName(typeof(test), 3);//ddd
    s = Enum.GetName(typeof(test), 4);//null
    //s = Enum.GetName(typeof(test), "3");//System.ArgumentException(传入的值必须是枚举的枚举基或基础类型,如 Int32)            
    //s = Enum.GetName(typeof(test), "aaa");//System.ArgumentException(传入的值必须是枚举的枚举基或基础类型,如 Int32)
     
    基于以上的总结,以后但凡是想将字符串或整形转为枚举,那么首先用Enum.IsDefined()方法判断,
    对于字符串,用Parse或TryParse转换,由于.net方法太多常见是不区分大小写的,所以记得使用ignoreCase参数的覆写方法.
    对于整形,可以使用Parse和ToObject方法.将整数转换为枚举值时,可以分配一个实际并非枚举成员的值。 为防止该情况,可在执行转换前将该整数传递至 IsDefined() 方法。
    将枚举转为字符串或整形值,可使用可通过调用静态 Format 方法以及重载实例 ToString()方法.或GetName().
    Enum 类提供 IConvertible 接口的显式接口实现以从枚举值转换为整数类型,所以可以使用Convert.ToInt32.
    Convert.ToInt32(test.aaa);
    

    如果想将枚举元素或(值)转为字符串(整形),可用Enum.GetValues用(int)转换一下.
  • 相关阅读:
    Uva 11401 数三角形
    Uva 11538 象棋中的皇后
    数学基础——基本计数方法
    八数码问题
    python 爬poj.org的题目
    python 爬图片
    hiho 第135周 九宫
    Uva 11464 偶数矩阵
    BZOJ 1001 [BeiJing2006]狼抓兔子
    LA 3708 墓地雕塑
  • 原文地址:https://www.cnblogs.com/span06/p/7993850.html
Copyright © 2020-2023  润新知