/// <summary> /// 将一个或多个枚举常数的名称、描述或数字值的字符串表示转换成等效的枚举对象。 /// 一个参数指定该操作是否区分大小写。 /// </summary> /// <param name="enumType">枚举类型。</param> /// <param name="value">包含要转换的值或名称的字符串。</param> /// <param name="ignoreCase">若要忽略大小写则为 <c>true</c>; /// 否则为 <c>false</c>。</param> /// <returns><paramref name="enumType"/> 类型的对象,其值由 <paramref name="value"/> 表示。</returns> /// <exception cref="System.ArgumentNullException"> /// <paramref name="value"/> 为 <c>null</c>。</exception> /// <exception cref="System.ArgumentException"> /// <paramref name="enumType"/> 不是 <see cref="System.Enum"/>。</exception> /// <exception cref="System.ArgumentException"> /// <paramref name="value"/> 是空字符串 ("") 或只包含空白。</exception> /// <exception cref="System.ArgumentException"> /// <paramref name="value"/> 是一个名称,但不是为该枚举定义的命名常量之一。</exception> /// <exception cref="System.OverflowException"> /// <paramref name="value"/> 超出 <paramref name="enumType"/> /// 基础类型的范围。</exception> public static object ParseEx(Type enumType, string value, bool ignoreCase) { ExceptionHelper.CheckArgumentNull(enumType, "enumType"); ExceptionHelper.CheckArgumentNull(value, "value"); if (!enumType.IsEnum) { throw ExceptionHelper.MustBeEnum("enumType", enumType); } value = value.Trim(); if (value.Length == 0) { throw ExceptionHelper.MustContainEnumInfo("value"); } // 尝试对数字进行解析,这样可避免之后的字符串比较。 ulong tmpValue; if (ParseString(value, out tmpValue)) { return(Enum.ToObject(enumType, tmpValue)); } // 尝试对描述信息进行解析。 EnumCache cache = GetEnumCache(enumType); StringComparison comparison = ignoreCase ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal; ulong valueUL = 0; int start = 0; do { // 去除前导空白。 while (char.IsWhiteSpace(value, start)) { start++; } int idx = value.IndexOf(',', start); if (idx < 0) { idx = value.Length; } int nIdx = idx - 1; // 去除后面的空白。 while (char.IsWhiteSpace(value, nIdx)) { nIdx--; } if (nIdx >= start) { string str = value.Substring(start, nIdx - start + 1); int j = 0; // 比较常数值的名称和描述信息,先比较名称,后比较描述信息。 for (; j < cache.Names.Length; j++) { if (string.Equals(str, cache.Names[j], comparison)) { // 与常数值匹配。 valueUL |= cache.Values[j]; break; } } if (j == cache.Names.Length && cache.HasDescription) { // 比较描述信息。 for (j = 0; j < cache.Descriptions.Length; j++) { if (string.Equals(str, cache.Descriptions[j], comparison)) { // 与描述信息匹配。 valueUL |= cache.Values[j]; break; } } } // 未识别的枚举值。 if (j == cache.Descriptions.Length) { // 尝试识别为数字。 if (ParseString(str, out tmpValue)) { valueUL |= tmpValue; } else { // 不能识别为数字。 throw ExceptionHelper.EnumValueNotFound(enumType, str); } } } start = idx + 1; } while (start < value.Length); return(Enum.ToObject(enumType, valueUL)); }