有关C#表达式树的建议
我正在研究一种将表达式树作为参数以及类的类型(或者实例)的方法。
基本思想是,此方法会将某些东西添加到用于验证的集合中。
public interface ITestInterface { //Specify stuff here. } private static void DoSomething<T>(Expression<Func<T, object>> expression, params IMyInterface[] rule) { // Stuff is done here. }
该方法的调用方式如下:
class TestClass { public int MyProperty { get; set; } } class OtherTestClass : ITestInterface { // Blah Blah Blah. } static void Main(string[] args) { DoSomething<TestClass>(t => t.MyProperty, new OtherTestClass()); }
我这样做是因为我希望传入的属性名称是强类型的。
我正在努力的几件事。
- 在DoSomething中,我想从传递的主体中获取T的" PropertyInfo"类型,并将其与rule []一起添加到集合中。目前,我正在考虑使用expression.Body并从" Convert。([propertyname])"中删除[propertyname],并使用反射来获取所需的内容。这似乎很麻烦而且是错误的。有没有更好的办法?
- 这是我正在使用的特定模式吗?
- 最后,感谢我们对我对自己正在做的事情的误解的任何建议或者澄清,并且/或者感谢C#表达式树上的资源或者良好信息。
谢谢!
伊恩
如果在上面的示例中调用了" expression.Body.ToString()"在DoSomething方法中返回的示例,则该字符串包含" Convert(t.MyProperty)"。
我确实需要对它进行强类型化,因此如果我更改属性名称,它将无法编译。
感谢建议!
解决方案
从Expression.Body收集PropertyInfo对象似乎类似于我对另一个问题的解决方案。
感谢我们在此尝试使用此物业。我遇到了这个难题。总是觉得很奇怪:
DoSomething("MyProperty", new OtherClass());
如果该属性更改了名称,或者在调用中键入了错误的文本,则将出现问题。我了解到的是,这可能是我们必须通过测试处理的事情。具体来说,是单元测试。我会编写单元测试以强制执行" DoSomething"调用。
我们可能尝试的另一件事是用属性装饰属性,然后在构造类时使用类来反映,以寻找具有属性的属性并加载规则。
[DoSomething(typeof(OtherClass), typeof(OtherClass2))] public int MyProperty { get; set; }
在这种情况下,构造函数(也许在基类中?)将动态创建OtherClass对象和OtherClass2对象,并将它们与属性名称一起加载到集合中。
我在很大程度上依赖于表达式树来将我当前应用程序要做的很多事情推到编译时,即静态类型检查。
我遍历表达式树以将其转换为其他"有意义的"东西。
最后我做了很多事情,就是我不是使用URL,而是使用类似于MVC的方法声明lambda函数,并将其转换为...解释,编译器将生成的表达式树转换为URL。调用此URL时,我做相反的事情。这样,我就可以对链接断开进行编译时检查了,这在重构和重载方面也非常有用。我认为以这种方式使用表达式树很酷。
我们可能想检查访客模式,开始时很麻烦,因为一开始它没有多大意义,但将所有内容联系在一起,这是解决编译器构造中类型检查的一种非常正式的方式。我们可以执行相同的操作,但是无需进行类型检查即可发出所需的内容。
我目前正在反对的是建立一个简单的框架来翻译(或者实际上我应该说解释)表达发束并发出JavaScript的能力。想法是,编译器生成的表达式树将转换为有效的JavaScript,该JavaScript与某些对象模型接口。
令人兴奋的是,当我出错时,编译器总是能够告诉我,并确保最终结果只是一堆字符串,但重要的是如何创建这些字符串。他们经过了验证,这意味着某些事情。
一旦掌握了这些,就几乎无法使用表达式树了。
在使用System.Reflection.Emit时,我发现自己使用表达式树创建了一个轻量级的框架来进行动态编译,该框架在编译时基本上可以说出我动态创建的程序集是否也可以进行编译,并且可以与反射无缝地协同工作。和静态类型检查。这一步一步走到了最后,最终节省了很多时间,并且被证明是非常敏捷和健壮的。
所以我喜欢这种东西,这就是元编程的全部内容,在执行程序的程序中编写程序。我说让它来吧!