解读PropertyHelper
前文
最近感兴趣的一个项目中,需要通过C#来实现一个上位机,网上的参考资料中,有关于仓库温控系统这样的实例可以参考借鉴。虽然该实例教程号称从0开始,但实际来看,在前期交代项目中使用的公共类库上,对这些类库的解释与说明基本上回避了诸如反射,特性等C#中比较难理解,也是中高阶的语法。作为一个小白,我看到这觉得非常难受,因为不喜欢这种看不懂的感觉,而且后续的代码只要依赖了这些公共类库代码的部分都有可能看不懂,这实在是一个隐患,于是乎,在潜下心来后,查看了特性,以及泛型等有关概念后,尝试为和我一样的小白,做一些解读,希望看到这篇博文的小伙伴能从中得到一些帮助,也希望多交流,一起提高。
正文
PropertyHelper
代码
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
namespace Common
{
/// <summary>
/// 获取指定类型的指定列名的属性数组
/// ||
/// 实体类
/// </summary>
public class PropertyHelper
{
public static PropertyInfo[] GetTypeProperties<T>(string cols)
{
Type type = typeof(T);//获取T的类型,并将类型传给type,Type是一种特殊类,C#中通过Type类可以访问任意数据类型信息
List<string> listCols = StringHelper.GetStrArray(cols, ',',true);//将cols按逗号分割转换为string列表
PropertyInfo[] properties = type.GetProperties();
if (listCols.Count>0&&listCols != null)
{
properties = properties.Where( p => listCols.Contains( p.GetColName().ToLower() ) ).ToArray();//where约束,起到了过滤器的作用,将properties满足where约束条件的枚举类型转换为数组传回properties
}
return properties;
}
}
}
作用
获取指定类型的指定列名的属性数组
- 指定类型:这里指代的是实体模型层(Model)中用以描述仓库相关信息的类
- 指定列名:cols包含的指定的列名
其实这句话是不好理解的,不妨举个例子:
namespace STMS.Models.Dmodels
{
public class ProductInfos
{
public int ProductID { get; set; }
public string ProductName { get; set; }
public string ProductNo { get; set; }
public decimal FitLowTemp { get; set; }//合适的最低温度
public decimal FitHighTemp { get; set; }//合适的最高温度
public int IsDeleted { get; set; }
}
}
上面是我声明的一个产品信息的实体类,现在我需要知道他当中包含了哪些属性,当然通过代码可以直观的看到,也可以通过智能索引看到,但是实际上当你有很多个这样的类的时候,得知它里面包含哪些属性,哪些属性我们需要,就很繁琐了,那么我为何不做一个属性的访问器呢?PropertyHelper要解决的就是这样一个问题,当我需要查看ProductInfos中是否包含了ProductID
这个属性的时候,我就可以通过以下语句进行查询访问。
PropertyInfo[] pi = GetTypeProperties<ProductInfos>('ProductID');
大致明白了,这个类的作用后,我们对其中的代码实现,做一个比较详细的解读。
详细解读
//为了方便解读,解读的的内容将在代码块中进行,尽量做到详实
using System.Reflection;
/*PropertyHelper当中因为使用到了PropertyInfo这个类,所以使用到了反射,反射你可以简单理解为一种特性,它可以帮助我们了解对象本身的一些特性,这样说就比较绕口了,简而言之我们这里只需要知道PropertyInfo可以收集类的属性*/
using System.Text;//StringHelper.GetStrArray()使用到了正则表达式和文本处理内容
using System.Threading.Tasks;
namespace Common
{
/// <summary>
/// 获取指定类型的指定列名的属性数组
/// ||
/// 实体类
/// </summary>
public class PropertyHelper
{
public static PropertyInfo[] GetTypeProperties<T>(string cols)
{
Type type = typeof(T);//获取T的类型,并将类型传给type,Type是一种特殊类,C#中通过Type类可以访问任意数据类型信息
List<string> listCols = StringHelper.GetStrArray(cols, ',',true);//将cols按逗号分割转换为string列表
PropertyInfo[] properties = type.GetProperties();/*这里其实经将type中的所有类型全部保存了,事实上下文的代码主要起的还是过滤的作用,把需要的属性保留下来,当然如果没有过滤,properties会返回type中所有的属性*/
if (listCols.Count>0&&listCols != null)
{
properties = properties.Where( p => listCols.Contains( p.GetColName().ToLower() ) ).ToArray();/*where约束,起到了过滤器的作用,将properties满足where约束条件的枚举类型转换为数组传回properties,where当中的代码是一个lambda表达式,也就所谓的匿名方法,p将properties作为参数传到箭头指向的方法*/
}
return properties;
}
}
}
后文
要理解以上代码,需要PropertyInfo相关的一些信息,我建议阅读MSDN,当然即便理解了代码运作的实现原理,可能还是不太理解它具体使用的场景,这一点我我认为可以在后续再进行补充。