我在一个相当大的项目中使用Java。我的问题是如何最好地为我的应用程序构建一组属性。
方法1:拥有一些每个类都可以访问的静态Properties对象。 (缺点:那么,如果某些类被从应用程序的上下文中取出,它们将失去它们的一般性;它们还需要显式调用位于不同类中的某个静态对象,并且可能在将来消失;它只是不会感觉是对的,我错了吗?)
方法2:让属性由主类实例化并传递给其他应用程序类。 (缺点:你最终将指向Properties对象的指针传递给几乎每个类,它似乎变得非常冗余和繁琐;我不喜欢它。)
有什么建议吗?
答案 0 :(得分:7)
我喜欢对许多属性使用Spring依赖注入。您可以将应用程序视为构建块,并将属性直接注入需要它们的组件中。这保留了(鼓励)封装。然后,将组件组装在一起并创建“主类”。
依赖注入的一个很好的副作用是你的代码应该更容易测试。
答案 1 :(得分:2)
实际上,方法2的效果非常好。
我尝试在最近的项目中使用Singleton属性对象。然后,当需要添加功能时,我需要修改Singleton,并后悔必须找到我使用MySingleton.getInstance()
的每个地方。
通过各种构造函数传递全局信息对象的方法2更容易控制。
使用显式设置器也有帮助。
class MyConfig extends Properties {...}
class SomeClass {
MyConfig theConfig;
public void setConfi( MyConfig c ) {
theConfig= c;
}
...
}
它运行良好,您会很高兴您能够精确地控制哪些类实际需要配置信息。
答案 2 :(得分:2)
如果许多类需要属性,我会选择方法1.或者也许是使用Singleton设计模式而不是所有静态方法的变体。这意味着您不必继续传递一些属性对象。另一方面,如果只有少数类需要这些属性,您可以选择方法2,原因如上所述。您可能还想问自己,您编写的类实际上将被重用的可能性有多大,如果是这样,那么重用属性对象的问题是多少。如果不可能重复使用,请不要现在烦恼并选择最适合当前情况的解决方案。
答案 3 :(得分:1)
听起来你需要一个配置管理器组件。它可以通过某种服务定位器找到,它可以像ConfigurationManagerClass.instance()
一样简单。这将封装所有有趣的东西。或者您可以使用像Spring这样的依赖注入框架。
很大程度上取决于组件如何在您的架构中找到彼此。如果您的其他组件作为参考传递,请执行此操作。只是保持一致。
答案 4 :(得分:1)
如果您正在寻找快速的东西,可以使用系统属性,它们可供所有类使用。您可以存储String值,或者如果需要存储'stuff'列表,可以使用System.Properties()方法。这将返回一个'Properties'对象,它是一个HashTable。然后,您可以将所需内容存储到表中。它并不漂亮,但它是拥有全球属性的快捷方式。 YMMV
答案 5 :(得分:0)
我通常会寻找一个驻留在一个公共项目中的单例对象,并且包含一个自己键入命名空间的哈希表,从而为每个项目生成一个属性类。
依赖注入也是一种很好的方法。
答案 6 :(得分:0)
当我有一个指向我的内存属性的静态指针时,我感觉更舒服。有时您希望在运行时重新加载属性,或者使用静态引用更容易实现的其他功能。
请记住,没有一个班级是一个岛屿。一个可重用的类可以有一个客户端类,以保持核心不受单重参考。
你也可以使用接口,尽量不要过度使用它。
答案 7 :(得分:0)
方法2非常好。
无论如何,你不应该让其他类搜索配置对象。您应该在配置对象的对象中使用配置。
请查看apache commons configuration以获取有关配置Impl的帮助。
所以在main()中你可以拥有
MyObject mobj = new MyObject();
mobj.setLookupDelay(appConfig.getMyObjectLookupDelay);
mobj.setTrackerName(appConfig.getMyObjectTrackerName);
而不是
MyObject mobj = new MyObject();
mobj.setConfig(appConfig);
其中appConfig是apache配置库的包装器,它根据配置文件中值的名称执行所有值的查找。
这样你的对象就变得非常容易测试了。
答案 8 :(得分:0)
暂时还没有完成Java,但是你不能把你的属性放到java.lang.System属性中吗?这样,您可以从任何地方访问值,并避免使用“全局”属性类。