我看到很多C#,.net问题在这里使用反射解决了.对我来说,很多它们看起来像是以优良设计(OOP)为代价而弯曲规则.许多解决方案看起来不可维护且"脚本".
使用反射一般是一种好习惯吗?有些事情只能通过反思来解决吗?
编辑:
请举例说明反射是唯一的好解决方案.
例子:
通过配置动态加载类型
使用"约定"样式注册(在容器中注册实现接口的组件或具有某种命名约定)
检查/使用自定义属性/类型元数据
反射是一种工具,就像"抛出"一样.你应该到处使用扔?没有!那么使用抛出的代码气味是什么?
对我来说,很多它们看起来像是以优良设计(OOP)为代价而弯曲规则.许多解决方案看起来不可维护且"脚本".
老实说,"好的设计"与OOP几乎没有关系.我想说一个更大的设计气味要关注的是,良好的设计与OOP完全相同.如果没有OOP,我们就无法拥有良好的设计,并且如果没有成为优秀的设计,我们就无法遵循OOP的规则.这几乎和人们对"气味"的痴迷一样糟糕.程序员应该使用他们的大脑,而不是他们的鼻子.
使用反射一般是一种好习惯吗?有些事情只能通过反思来解决吗?
我看待它的方式,反思主要是语言缺陷的症状.理想情况下,语言应该允许您在不通过反射"弯曲规则"的情况下做您想做的事情.但大多数人没有,而C#肯定没有,所以反思偶尔也是你明智的选择.
反射有很多"正确"的用法.动态加载类型/库将是显而易见的.或检查属性.大多数单元测试框架也依赖于反射,这很好,因为它们必须有点干扰,以便易于使用并获得对我们希望测试的代码的访问.
但是大多数用户代码执行某种类型的检查,在运行时测试类型是否实现某个接口或具有某个成员函数,这是一种在理想语言中不应该是必需的东西的标志.
如果你想把它看成是一种气味,那就把它称为语言气味,而不是设计气味.(当然它也可能在设计中被过度使用,但在我经常遇到的地方,由于缺乏语言的表现力,这是必要的)
反思有时是做某些事情的唯一方法.它是一个非常强大的工具,有时可能会被那些知道反思的人过度使用,但也许不是别的东西.当其他东西更好地工作时过度使用反射可能是一种设计气味......但更常见的是编码错误.
曾经有一个处理文件的程序(该描述的通用性)
通过使用反射你只需要将DLL放入一个文件夹中,应用程序会选择它并使用反射来查找实现某个接口的类并检查一些属性.不需要配置文件.只需放手即可,这对于生产系统来说非常方便,因为我们不需要任何停机时间.
与大多数解决方案一样 还有很多其他方法可以实现相同的目的,但反思确实使这很容易.
我不会说使用反射是一种设计气味.框架的一个有用特性使静态语言更具动态性.从实际的角度来看,如果没有它我可以解决我的问题,我会尽量避免反思.
从概念上讲,反射是一种强大的工具,可用作从非代码到代码的网关以及多态工具.
例如...
获取类型的字符串表示并将其转换为对象.
没有硬编码框架或插件在一起.
动态使用来自不同组件的对象,而不事先知道它们是什么.
无需编写专用代码即可序列化数据.
如果使用得当,它是一种巧妙的工具,可以将代码提升到更高级别的可重用性和灵活性.没有错.
这是设计气味的唯一时间,它被用来做传统功能已经涵盖的事情.(也就是说,您不希望使用Reflection来获取DataRow的值等).
以我的拙见,反思应该是最后的手段.反射使代码真的难以理解,仅仅通过查看它,因为语言的语义可以用非常奇怪的方式改变.
我认为这是一种气味.也许不是不好的练习,但会引起人们的注意.