2010-08-02 59 views
1

我试图使用示例表单http://blogs.msdn.com/b/davidebb/archive/2009/10/23/using-c-dynamic-to-call-static-members.aspx来消除代码重复。如何使用动态删除重复代码

if (Categories != null) { 
     foreach (var item in Categories) 
     { 
      if (item.ID != 0) 
      { 
       Category category = Category.Load(item.ID); 
       category.Name = item.Name; 
       category.Project = project; 
       category.Save(); 
      } 
      else 
      { 
       if(!String.IsNullOrEmpty(item.Name)) 
       { 
        Category category = new Category(project, item.Name); 
        category.Save(); 
       } 
      } 
     } 
} 


      if (Priorities != null) 
      { 
       foreach (var item in Priorities) 
       { 
        if (item.ID != 0) 
        { 
         Priority priority = Priority.Load(item.ID); 
         priority.Name = item.Name; 
         priority.Project = project; 
         priority.Save(); 
        } 
        else 
        { 
         if (!String.IsNullOrEmpty(item.Name)) 
         { 
          Priority priority = new Priority(project, item.Name); 
          priority.Save(); 
         } 
        } 
       } 

我试图做一些事情如下,但有错误消息

在部分不能调用非委托类型

if (!String.IsNullOrEmpty(item.Name)) 
       { 
        dynamic newObject = typeDynamic(project, item.Name); 
        newObject.Save(); 
       } 

SaveObjects(typeof(Category), Categories.ToList(), project); 
SaveObjects(typeof(Priority), Priorities.ToList(), project); 

任何帮助请。

谢谢。

什么是错,我该如何纠正?

private void SaveObjects(Type type, dynamic currentItems, Project project) 
    { 
     dynamic typeDynamic = new StaticMembersDynamicWrapper(type); 
     foreach (var item in currentItems) 
     { 
      if (item.ID != 0) 
      { 
       dynamic classValues = typeDynamic.Load(item.ID); 
       classValues.Name = item.Name; 
       classValues.Project = project; 
       classValues.Save(); 

      } 
      else 
      { 
       if (!String.IsNullOrEmpty(item.Name)) 
       { 
        dynamic newObject = typeDynamic(project, item.Name); 
        newObject.Save(); 
       } 
      } 
     } 

    } 

回答

0

您已经定义typeDynamic是一个动态的类型,但后来尝试使用它作为实际类型(使用它作为一个构造typeDynamic(...))。这不是他们打算如何使用,只是使用点(typeDynamic.someMember)访问成员。通过使用StaticMembersDynamicWrapper阅读,它不会让您访问构造函数,只有静态成员。您需要在StaticMembersDynamicWrapper类中实现TryInvoke以将该类型用作构造函数。添加到课程:

public override bool TryInvoke(InvokeBinder binder, object[] args, out object result) 
{ 
    ConstructorInfo ctor = _type.GetConstructor(args.Select(arg => arg.GetType()).ToArray()); 
    if (ctor == null) 
    { 
     result = null; 
     return false; 
    } 

    result = ctor.Invoke(args); 
    return true; 
} 

不是非常强大,但应该为你工作足够。不过,我强烈建议使用ck或其他非动态方法建议的更简单的方法。


不同的(非动态)的方式,你可以采取的使用委托给你的静态功能。请参阅我在此问题中的回答,Curious problem involving generics and static methods

+0

它'的代码错误的代码 如果 { 动态NEWOBJECT = typeDynamic(项目,item.Name)(String.IsNullOrEmpty(item.Name)!); newObject.Save(); } – learning 2010-08-02 07:54:53

2

通过声明一个暴露所有需要的共享属性和方法的接口,然后为每个类实现接口,并编写共享代码以在接口上工作,这可能会容易得多。