2012-01-05 57 views
3

我只用字符串成员一类是这样的:如何检查类成员是否不为空或空

public class MyClass 
{ 
    public string MyProp1 { get; set; } 
    public string MyProp2 { get; set; } 
} 

我创建一个实例:

Var myClass = new MyClass(); 

稍后在代码中,我d想知道所有成员(MyProp1和MyProp2)是否为空或空。我知道我当然可以使用if,但是在我的真实代码中有更多的属性超过2。

有没有办法做到这一点?

谢谢,

+0

你需要知道哪些属性为null或的String.Empty或只是其中至少有一个是? – ChrisBD 2012-01-05 08:25:55

+0

属性不能为空,不能为空 – 2012-01-05 08:28:29

回答

10

使用您的特性基于字典的店很可能是这样做的最简单的方法:

public class MyClass 
{ 
    private IDictionary<String, String> _store; 

    public MyClass() 
    { 
     _store = new Dictionary<String, String>(); 
    } 

    public string MyProp1 { 
     get { return GetOrDefault("MyProp1"); } 
     set { _store["MyProp1"] = value; } 
    } 
    public string MyProp2 { 
     get { return GetOrDefault("MyProp2"); } 
     set { _store["MyProp2"] = value; } 
    } 

    public Boolean HasData() 
    { 
     return _store.Any(x => !String.IsNullOrWhiteSpace(x.Value)); 
    } 

    public Boolean IsEmpty() 
    { 
     return _store.All(x => String.IsNullOrWhiteSpace(x.Value)); 
    } 

    private String GetOrDefault(String propertyName) 
    { 
     if (_store.ContainsKey(propertyName)) 
     { 
      return _store[propertyName]; 
     } 

     return String.Empty; 
    } 
} 

这样做的另一种方法将其与默认实例比较:

public class MyClass 
{ 
    public string MyProp1 { get; set; } 
    public string MyProp2 { get; set; } 

    public static readonly MyClass Empty = new MyClass(); 

    public Boolean HasData() 
    { 
     return !Empty.Equals(this); 
    } 

    public Boolean IsEmpty() 
    { 
     return Empty.Equals(this); 
    } 
} 
+1

请注意:在您的代码中,如果您没有设置第一个参数,您将调用'MyProp1',将会得到'System.Collections.Generic.KeyNotFoundException!至少使用'get {return _store.ContainsKey(“MyProp1”)? _store [“MyProp1”]:String.Empty; }' – balexandre 2012-01-05 08:51:39

+0

@balexandre:好点,我已经用你的建议更新了答案。 – Pondidum 2012-01-05 09:03:07

+2

与默认实例比较:极好的想法。 – 2012-12-20 14:27:00

0

如果在类许多性质,处理的一种方式是将它们存储在集合中,诸如数组或字典,代替声明每个属性为一体的一个单独的构件类。

然后,您可以通过键访问字典中的数据,这与访问类的属性一样简单。优点是你可以遍历字典并检查循环中的所有属性。

0

我会建议在你的班级中创建一个功能,你可以检查String.IsNullOrEmpty(MyProp1)等所有你的属性。这样你至少可以在一个地方收集所有的Ckecking功能。而且,只要添加新属性,您就只能修改这个位置。

+0

这只是我不想做......一个 – 2012-01-05 08:15:50

+0

检查一个除非你想在类中创建遍历所有成员的功能(例如,如这里http://stackoverflow.com/questions/721441/c-sharp-how-to-iterate-through-classes-fields-and-set-properties描述),你必须这样做以某种方式。只要你为它创建一个函数,你只需要做一次...反射是一个更通用的解决方案,创建你自己的函数手动检查每个属性产生更好的性能(并给你更多的控制)。 – Nailuj 2012-01-05 08:17:47

0

通过使用Attribute Base编程,您可以实现此目的。在这种方法中,您需要将属性放在类成员上,并且可以完成验证。您也可以使用Microsoft Enterprise Library

1

你可以总是初始化类像

public class MyClass 
{ 
    public MyClass() { 
     this.MyProp1 = this.MyProp2 = String.Empty; 
    } 

    public string MyProp1 { get; set; } 
    public string MyProp2 { get; set; } 
} 

,除非你的程序分配一个null值吧,new MyClass()将永远在他们的2个性能String.Empty ...


来自评论:

我在做什么例子是调用助手,例如:string name = myHelper。CheckNode(的xmlNode);并且在辅助我检查它是否为空,其他任何检查,我可以很容易地tweek辅助方法,这将是提供给所有的元素,你可以扩展它不仅支持字符串,但是所有其他数据类型以及

所以,想象一下,你是从你的XML阅读节点,你写他们喜欢:

string name = myHelper.CheckNode(node); 
放在你的助手

,你可以有这样的:

XmlNodeList datasourceNodes = rootNode.SelectNodes("dataSources/dataSource"); 
foreach (XmlNode datasourceNode in datasourceNodes) 
{ 
    DataSource dataSource = new DataSource(); 
    dataSource.Name = myHelper.CheckAttr(datasourceNode.Attributes["name"]); 
    dataSource.ODBC = myHelper.CheckNode(datasourceNode.SelectSingleNode("odbc")); 

    // or a variant (Extension Method) 
    dataSource.UID = datasourceNode.CheckNode("user"); 
    dataSource.PWD = datasourceNode.CheckAttr("password"); 

    ds.Add(dataSource); 
} 

你的助手,那么可以有一个方法如:

public static string CheckAttr(XmlAttribute attr) 
{ 
    return attr == null ? "" : attr.Value.Trim(); 
} 
public static string CheckNode(XmlNode node) 
{ 
    return node == null ? "" : node.InnerText.Trim(); 
} 

或变体(扩展方法)

public static string CheckAttr(this XmlNode, string attrName) 
{ 
    return attrName[attrName] == null ? "" : attrName[attrName].Value.Trim(); 
} 
public static string CheckNode(this XmlNode, string nodeName) 
{ 
    return node.SelectSingleNode(nodeName) == null ? 
       "" : 
       node.SelectSingleNode(nodeName).InnerText.Trim(); 
} 
+0

我的解释是不好。通过读取XML文件来设置成员,但我想确保所有成员都不为空或空 – 2012-01-05 08:19:34

+0

我在这些情况下做的是调用助手,例如:'string name = myHelper.CheckNode(xmlNode) ;'和那个帮助程序中,我检查它是否为null,任何其他检查,我可以轻松地调用帮助器方法,它将适用于所有元素,并且可以将其扩展为不仅支持字符串,还支持其他所有元素数据类型也是如此。 – balexandre 2012-01-05 08:22:44

+0

为我的解释添加了代码... – balexandre 2012-01-05 08:34:41

0

要检查所有的元素都设置您可以添加一个IsEmpty()方法到类,将检查内部属性。那么你就不需要在你的代码中遍历所有if语句。

在您的IsEmpty()方法中,您可以使用常规if语句来检查所有字段,或者您可以使用反射来自动检索所有字符串属性并检查其值。反射的性能会差那么一个正常的,如果检查,但如果这不是一个问题,你可以重复使用所有的实体反射代码来检查它们的值。

-1

您可以尝试使用以下样式。我以前没有尝试过,但你可以看看是否有帮助

If (String.IsNullOrEmpty(string1 && string2 && string3)) 
0

也许最好的办法是:

以字符串字典的形式重构您的属性。循环访问字典以使用string.IsNullOrEmpty()来测试字符串。您可以通过它设置,并直接从基于键

4

你可以尝试使用反射来检查属性的字典检索串一个索引属性替换N个的getter/setter方法。您应该确认所有属性都是公共的,并且类型是字符串。这是代码。

public static bool IsNullOrEmpty(MyClass prop) 
    { 
     bool result = true; 

     PropertyInfo[] ps = prop.GetType().GetProperties(); 

     foreach (PropertyInfo pi in ps) 
     { 
      string value = pi.GetValue(prop, null).ToString(); 

      if (string.IsNullOrEmpty(value)) 
      { 
       result = false; 
       break; 
      } 
     } 

     return result; 
    } 
+0

任何框架都为我们做这项工作? Nunit?或moq?还是应该由用户检查? ?? – 2014-03-28 10:10:09

2

要检查,如果你的类包含“任何”性能,这是空:

System.Reflection.PropertyInfo[] properties = myClass.GetType().GetProperties 
         (BindingFlags.Public | BindingFlags.Instance);   

bool hasNullProperty = properties.Any(y => y.GetValue(x, null) == null);