• 教你在你的应用程序中扩展使用dynamic类型


    教你在你的应用程序中扩展使用dynamic类型

        相信大家在开发中经常会接触到mvc中的ViewBag,有心的同学会,发现这就是一个dynamic类型,查看源码一谈究竟,本文也是根据dynamic来扩展一些实际中的应用,方便开发过程中使用,来提高大家的工作效率等。这里我给大家介绍一个简单的,解析xml的扩展类。

      先新建一个类,DynamicXmlNode 继承自DynamicObject,然后我们输入override,看一下,都有哪些方法可以重写的:

      

      看到其中有2个方法,感觉很接近我们要用的,我这里只有TryGetMember,这个方法,我们重写这个方法,在重写之前,我们建立一个字典类,然后TryGetMember方法里面,用来操作这个字典类:  

     1 public class DynamicXmlNode : DynamicObject
     2     {
     3         Dictionary<string, object> _objects = new Dictionary<string, object>();
     4 
     5         public override bool TryGetMember(GetMemberBinder binder, out object result)
     6         {
     7             var name = binder.Name;
     8             return _objects.TryGetValue(name, out result);
     9         }
    10 
    11         
    12     }

     

        GetMemberBinder就是获取数据的绑定名称,属性Name,就可以做为我们从字典中获取值的key,此时,获取值的方法已经写好了,那么我们要将数据绑定进来,对外提供一个Add方法,此时类就如下:  

    public class DynamicXmlNode : DynamicObject
        {
            Dictionary<string, object> _objects = new Dictionary<string, object>();
    
            public override bool TryGetMember(GetMemberBinder binder, out object result)
            {
                var name = binder.Name;
                return _objects.TryGetValue(name, out result);
            }
    
            public void Add(string name, object s)
            {
                _objects.Add(name, s);
            }
        }

    其实很简单,相信同学们都能看懂。这样一个动态类型就创建完成了,下面我们就要用这个类,来封装数据,方便调用的人直接获取数据:

      创建一个类,定义一个静态方法,用来解析xml,绑定数据:

     1 public class CreateDynamicObj
     2     {
     3         public static List<DynamicXmlNode> CreateObj(string xml, string nodeName)
     4         {
     5             List<DynamicXmlNode> xmlNodes = new List<DynamicXmlNode>();
     6             var doc = XDocument.Parse(xml);
     7             var nodes = doc.Descendants(nodeName);
     8             foreach (var node in nodes)
     9             {
    10                 //元素
    11                 if (node.HasElements)
    12                 {
    13                     var nnodes = node.Elements();
    14                     DynamicXmlNode xmlobj = new DynamicXmlNode();
    15                     foreach (var nnode in nnodes)
    16                     {
    17                         var name = nnode.Name.LocalName;
    18                         var b = nnode.Value;
    19                         xmlobj.Add(name, b);
    20                     }
    21                     xmlNodes.Add(xmlobj);
    22                 }
    23                 //属性
    24                 if (node.HasAttributes)
    25                 {
    26                     var nnodes = node.Attributes();
    27                     DynamicXmlNode xmlobj = new DynamicXmlNode();
    28                     foreach (var nnode in nnodes)
    29                     {
    30                         var name = nnode.Name.LocalName;
    31                         var b = nnode.Value;
    32                         xmlobj.Add(name, b);
    33                     }
    34                     xmlNodes.Add(xmlobj);
    35                 }
    36 
    37             }
    38             return xmlNodes;
    39         }
    40 }

    代码很简单了,大家应该都看的懂,传递一个要解析的节点名称,然后返回这个名称的所有元素,下面元素的名字或属性的名字做为键,值做为字典的值,调用DynamicXmlNode的Add方法,将键和值添加到字典中,并返回这个动态类型的集合。我这里只是简单示范了,如果同学们想让这个类更方便更适用,可以将节点解析改为递归的,这样才能适合各种格式的xml。

    下面我们来调用:

     1 class Program
     2     {
     3         static void Main(string[] args)
     4         {
     5             var xml = @"<root>
     6                             <item>
     7                                 <name>小王</name>
     8                                 <age>13</age>
     9                                 <sex>男</sex>
    10                                 <friend>
    11 
    12                                 </friend>
    13                             </item>
    14                             <item>
    15                                 <name>小张</name>
    16                                 <age>13</age>
    17                                 <sex>女</sex>
    18                             </item>
    19                         </root>";
    20 
    21             var objs = CreateDynamicObj.CreateObj(xml,"item");
    22             foreach (dynamic dynamicXmlNode in objs)
    23             {
    24                 Console.WriteLine(dynamicXmlNode.name);
    25                 Console.WriteLine(dynamicXmlNode.age);
    26                 Console.WriteLine(dynamicXmlNode.sex);
    27             }
    28             Console.ReadKey();
    29         }
    30     }

    大家可以看到,我foreach的对象是一个dynamic的类型,这样我就可以通过一个匿名属性直接获取该属性的值了,类似这个样子:dynamicXmlNode.name,而实际上我这个类型中是没用这个属性的,那就多亏了GetMemberBinder这个类了。

    好了,看下输出结果:

    好了,要去吃饭了,谢谢大家。

  • 相关阅读:
    生活不仅有诗远方,还有身体和枸杞
    星空
    住进布达拉宫,我是雪域最大的王。流浪在拉萨街头,我是世间最美的情郎。
    安得与君相决绝,免教生死作相思
    黑马程序员-传智健康项目资料
    黑马程序员-传智健康项目(第十三章)
    黑马程序员-传智健康项目(第十二章)
    黑马程序员-传智健康项目(第十一章)
    黑马程序员-传智健康项目(第十章)
    黑马程序员-传智健康项目(第九章)
  • 原文地址:https://www.cnblogs.com/nywd/p/3785556.html
Copyright © 2020-2023  润新知