C# 什么时候使用反射?模式/反模式
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/429962/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
When do you use reflection? Patterns/anti-patterns
提问by StackUnderflow
I understand the reflection API (in c#) but I am not sure in what situation would I use it. What are some patterns - anti-patterns for using reflection?
我了解反射 API(在 c# 中),但我不确定我会在什么情况下使用它。有哪些模式 - 使用反射的反模式?
采纳答案by Harper Shelby
The only place I've used the Reflection stuff in C# was in factory patterns, where I'm creating objects (in my case, network listeners) based on configuration file information. The configuration file supplied the location of the assemblies, the name of the types within them, and any additional arguments needed. The factory picked this stuff up and created the listeners based on that.
我在 C# 中使用反射的唯一地方是在工厂模式中,我根据配置文件信息创建对象(在我的例子中是网络侦听器)。配置文件提供了程序集的位置、其中类型的名称以及所需的任何其他参数。工厂选择了这些东西,并在此基础上创建了监听器。
回答by Randolpho
I'm not about to drop any patterns, but I would suggest that it's a good idea to avoid reflection until you actually need it. It's especially useful for interop and extensibility situations where you cannot control ahead of time the type of an object.
我不打算放弃任何模式,但我建议避免反射是一个好主意,直到你真正需要它。对于无法提前控制对象类型的互操作和可扩展性情况,它特别有用。
回答by Otávio Décio
I don't know if it is a pattern but I use reflection to generate SQL from DAO's class definitions.
我不知道这是否是一种模式,但我使用反射从 DAO 的类定义生成 SQL。
回答by Andru Luvisi
There is no hard and fast rule. Basically, you don't use reflection without a good reason. Use reflection when you can't do what you want without it, or when your code would be much longer or more difficult to understand without reflection.
没有硬性规定。基本上,您不会在没有充分理由的情况下使用反射。当没有反射你就不能做你想做的事时,或者当你的代码在没有反射的情况下会更长或更难理解时,请使用反射。
回答by Garry Shutler
I went for 2 years of development without understanding the purpose of reflection. It has very niche uses, but is extremely powerful when it is the right tool for the job.
我在不理解反思目的的情况下进行了 2 年的开发。它有非常小众的用途,但当它是工作的正确工具时,它的功能非常强大。
I think what I'm trying to say is only use it when you are sure it's the only way to achieve what you want.
我想我想说的是只有在你确定这是实现你想要的唯一方法时才使用它。
回答by ctacke
In one product I'm working on we use it a lot, but Reflection is a complex, slow beast. Don't go looking for places to use it just because it sounds fun or interesting. You'll use it when you run into a problem that can't be solved in any other way (dynamically loading assemblies for plug ins or frameworks, assembly inspection, factories where types aren't know at build, etc). It's certainly worth looking at reflection tutorials to see how it works, but don't fall into the trap of "having a hammer and everything looking like a nail." It's got very specialized use cases.
在我正在开发的一个产品中,我们经常使用它,但 Reflection 是一个复杂、缓慢的野兽。不要仅仅因为它听起来有趣或有趣就去寻找使用它的地方。当您遇到无法通过任何其他方式解决的问题(动态加载插件或框架的程序集、程序集检查、构建时类型未知的工厂等)时,您将使用它。看看反射教程当然值得一看,看看它是如何工作的,但不要陷入“拿着锤子,一切看起来都像钉子”的陷阱。它有非常专业的用例。
回答by JSB????
I use it in a case similar to that mentioned by Harper Shelby, in which a configuration file specifies at runtime which object to instantiate. In my particular case there's nothing as elaborate as a factory--only a set of classes that implement a common interface, and a simple function that reads the configuration file and creates the proper object, returning the interface.
我在类似于 Harper Shelby 提到的情况下使用它,其中配置文件在运行时指定要实例化的对象。在我的特殊情况下,没有什么比工厂更复杂的了——只有一组实现公共接口的类,以及一个读取配置文件并创建正确对象并返回接口的简单函数。
回答by P Daddy
I most often use it when I need to break somebody else's (usually the framework's) encapsulation. That is, I need to change some private field, or call a private method, or create an instance of some internal class in a library I have no power to change. A good example is the code in my answerto this question. In this case, the behavior of the framework method ServiceBase.Run
was unacceptable, so I used reflection to do the same thing it does in a more acceptable manner.
当我需要打破其他人(通常是框架)的封装时,我最常使用它。也就是说,我需要更改某些私有字段,或调用私有方法,或在我无权更改的库中创建某个内部类的实例。一个很好的例子是我对这个问题的回答中的代码。在这种情况下,框架方法的行为ServiceBase.Run
是不可接受的,所以我使用反射以更可接受的方式来做同样的事情。
Reflection has many other uses, though, including duck typing, working with attributes, and late binding.
回答by tvanfosson
I use reflection a fair amount in my unit tests, especially when the things I'm checking are anonymous types. I've also used it as a way to easily clone/copy model objects. Rather than write the code to do this for every model object, I can easily create an object of a particular type using reflection, interrogate the incoming object's public properties and invoke the settors on the cloned objects corresponding properties. I also use it with designer generated classes that implement the same method signatures, but don't have an associated interface. In those cases, I can interrogate the object to see if it has the required method and invoke it if it does. LINQ2SQL entities are like this so in my fake data context wrapper OnSubmit method I use reflection to get the OnValidate method and invoke it for unit testing.
我在单元测试中大量使用反射,尤其是当我检查的内容是匿名类型时。我还使用它作为一种轻松克隆/复制模型对象的方法。无需为每个模型对象编写代码来执行此操作,我可以使用反射轻松创建特定类型的对象,询问传入对象的公共属性并调用克隆对象对应属性上的设置器。我还将它与实现相同方法签名但没有关联接口的设计器生成的类一起使用。在这些情况下,我可以询问对象以查看它是否具有所需的方法,如果有则调用它。LINQ2SQL 实体就是这样,所以在我的假数据上下文包装器 OnSubmit 方法中,我使用反射来获取 OnValidate 方法并调用它进行单元测试。
回答by Marc Gravell
I use it in a binary serializer (protobuf-net). I use reflection only to build the model - when it is used (i.e. during [de]serialization) it is using delegates etc for maximum performance.
我在二进制序列化程序 ( protobuf-net) 中使用它。我只使用反射来构建模型 - 当它被使用时(即在 [反] 序列化期间),它使用委托等来获得最大性能。
I also used it (along with ComponentModel and Reflection.Emit) in HyperDescriptor, to build accelerated property access (~100x the speed of regular reflection).
我还在HyperDescriptor 中使用它(以及 ComponentModel 和 Reflection.Emit)来构建加速的属性访问(大约是常规反射速度的 100 倍)。
And by necessity, you need to use reflection if you are building your own Expression
s.
并且必要时,如果您要构建自己的Expression
s,则需要使用反射。