2013-06-28 33 views
6

我写了下面的方法与follwing要求 -返回可空类型通用的方法值

  1. 输入的XMLNode和的attributeName
  2. 回报,一旦发现与传递
  3. 相关的属性名称值
  4. 如果在传递的attributeName中没有值,则应返回 -

    3.1。对于int -1 3.2。对于日期时间DateTime.MinValue 3.3。对于字符串,null 3.4。对于布尔,null

下面的方法在案例3.4中失败。

public T AttributeValue<T>(XmlNode node, string attributeName) 
     { 
      var value = new object(); 

      if (node.Attributes[attributeName] != null && !string.IsNullOrEmpty(node.Attributes[attributeName].Value)) 
      { 
       value = node.Attributes[attributeName].Value; 
      } 
      else 
      { 

       if (typeof(T) == typeof(int)) 
        value = -1; 
       else if (typeof(T) == typeof(DateTime)) 
        value = DateTime.MinValue; 
       else if (typeof(T) == typeof(string)) 
        value = null; 
       else if (typeof(T) == typeof(bool)) 
        value = null; 



      } 
      return (T)Convert.ChangeType(value, typeof(T)); 
     } 

当改变这

public System.Nullable<T> AttributeValue<T>(XmlNode node, string attributeName) where T : struct 
     { 
      var value = new object(); 

      if (node.Attributes[attributeName] != null && !string.IsNullOrEmpty(node.Attributes[attributeName].Value)) 
      { 
       value = node.Attributes[attributeName].Value; 
      } 
      else 
      { 

       if (typeof(T) == typeof(int)) 
        value = -1; 
       else if (typeof(T) == typeof(DateTime)) 
        value = DateTime.MinValue; 
       else if (typeof(T) == typeof(string)) 
        return null; 
       else if (typeof(T) == typeof(bool)) 
        return null; 



      } 
      return (T?)Convert.ChangeType(value, typeof(T)); 
     } 

它无法为字符串类型,即3.3的情况下

期待一些帮助。

+0

你如何_call_在你的第一套代码中的方法?您需要将它称为'AttributeValue (...)'如果您只是调用'AttributeValue (...)',那么'null'不是'bool'的有效值。编辑:而你的第二种情况失败,因为'字符串'不能用于'System.Nullable '因为'字符串'不是一个值类型的结构。 –

回答

4

感谢了大量的答复,这是我写的,它为我的作品..

它返回null类型。

public T AttributeValue<T>(XmlNode node, string attributeName) 
     { 
      object value = null; 

      if (node.Attributes[attributeName] != null && !string.IsNullOrEmpty(node.Attributes[attributeName].Value)) 
       value = node.Attributes[attributeName].Value; 

      if (typeof(T) == typeof(bool?) && value != null) 
       value = (string.Compare(value.ToString(), "1", true) == 0).ToString(); 

      var t = typeof(T); 
      t = Nullable.GetUnderlyingType(t) ?? t; 

      return (value == null) ? 
       default(T) : (T)Convert.ChangeType(value, t); 
     } 

我这样称呼它

const string auditData = "<mydata><data><equipmentStatiticsData><userStatistics maxUsers='100' totalUsers='1' authUsers='0' pendingUsers='' adminAddedUsers='' xmlUsers='' internalDBUsers='' webUsers='' macUsers='' vpnUsers='' xUsers8021=''></userStatistics><equipmentStatistics cpuUseNow='14' cpuUse5Sec='1' cpuUse10Sec='1' cpuUse20Sec='1' ramTotal='31301632' ramUtilization ='1896448' ramBuffer='774144' ramCached='8269824' permStorageUse='24' tempStorageUse='24'></equipmentStatistics><authStatus status='1'></authStatus></equipmentStatiticsData></data></mydata>"; 
    xmlDoc.LoadXml(auditData); 
    var userStatsNode = xmlDoc.SelectSingleNode("/mydata/data/equipmentStatiticsData/userStatistics"); 


    var intNullable = AttributeValue<int?>(userStatsNode, "vpnUsers"); 
    var nullableBoolTrue = AttributeValue<bool?>(userStatsNode, "totalUsers"); 
    var nullableBoolFalse = AttributeValue<bool?>(userStatsNode, "authUsers"); 
    var nullableString = AttributeValue<string>(userStatsNode, "authUsers"); 
    var pendingUsersBoolNull = AttributeValue<bool?>(userStatsNode, "pendingUsers"); 
    var testAttribNullableNotFoundDateTime = AttributeValue<DateTime?>(userStatsNode, "testAttrib"); 
    var testAttrib1NullString = AttributeValue<string>(userStatsNode, "testAttrib"); 
    var maxUsersNullInt = AttributeValue<int?>(userStatsNode, "maxUsers"); 

它很适合我。感谢人们...

+0

我很好,现在返回空值。这看起来更好的解决方案, – Ashish

5

对于3.4,您需要使用bool?作为T的类型,因此您可以返回null。

然后,您可以使用default关键字3.3和3.4(字符串和布尔?)。根据msdn,它将返回null作为引用类型和值类型的默认值(如int或bool)。

您可以使用它像

return default(T); 
+0

对'bool'情况(3.4)的要求是返回null。这将返回'false'而不会与未找到匹配属性的情况以及提供“false”的情况区分开来。 –

+0

你不需要用'bool?'作为泛型参数来使用它,在这种情况下返回null?我的意思是,如果T是'bool',那么你不能返回false,所以你需要使用'bool?'... –

+0

只是为了澄清,当然,'bool?'的默认值(T)将会返回NULL –

0

你需要使用bool?bool因为null不是不可为空bool有效值打电话给你的第一个代码集。因为你不能使用string为通用型的Nullable<T>,因为它需要一个价值型structstring是引用类型类

你的第二个代码块失败。

你需要改变你的第一个方法块找typeof(bool?),并用可空​​布尔类型称之为:

public T AttributeValue<T>(XmlNode node, string attributeName) 
{ 
    var value = new object(); 

    if (node.Attributes[attributeName] != null && !string.IsNullOrEmpty(node.Attributes[attributeName].Value)) 
    { 
     value = node.Attributes[attributeName].Value; 
    } 
    else 
    { 
     if (typeof(T) == typeof(int)) 
      value = -1; 
     else if (typeof(T) == typeof(DateTime)) 
      value = DateTime.MinValue; 
     else if (typeof(T) == typeof(string)) 
      value = null; 
     else if (typeof(T) == typeof(bool?)) 
      value = null; 
    } 

    var type = Nullable.GetUnderlyingType(typeof(T)) ?? typeof(T); 
    return (T)Convert.ChangeType(value, type); 
} 

然后称其为:

bool? value = AttributeValue<bool?>(node, "myAttributeName"); 

您还需要因为Convert.ChangeType不适用于可为空的类型。从here快速修复可以解决此问题。(它被包含在上面的代码中)

编辑:这是你的方法的改进/清洁版本:

public T AttributeValue<T>(XmlNode node, string attributeName) 
{ 
    if (node.Attributes[attributeName] != null && !string.IsNullOrEmpty(node.Attributes[attributeName].Value)) 
    { 
     var value = node.Attributes[attributeName].Value; 
     var type = Nullable.GetUnderlyingType(typeof(T)) ?? typeof(T); 
     return (T)Convert.ChangeType(value, type); 
    } 
    else 
    { 
     if (typeof(T) == typeof(int)) 
      return (T)(object)(-1); 

     return default(T); 
    } 
} 

可以为不存在的节点添加额外的特殊情况,但所有的情况下,除了int已经是类型的默认值,所以只需使用default(T)来代替。