[英]Design issue on static initialization block
我有一个设计问题:让我在简单的例子中解释一下:
Public class A()
{
public static HashMap map = new HashMap();
public static String url = "default";
static {
getJson();
}
//url getters and setters are defined
public static getJson() {
//code which uses url to get json and populate hashmap
}
public string getresult(String key) {
//uses hashmap to send result.
}
我正在使用静态初始化块,因为我只想一次获取json。
public class B {
//这里我要更改url并调用getJson方法。 如果我调用A.setUrl(),那么在设置url之前,将在静态初始化块中按原样调用A.getJson()方法。我该如何先设置url然后再调用getJson()。
//is this a bad design?
}
我猜这应该工作。 添加新方法。
public static void getJson(String url) {
setUrl(url);
getJSon();
}
静态初始化器通常是一个坏主意,因为单元测试变得困难。
您可以通过执行以下操作来重新设计:
public class A {
//Add generics
private Map map = new HashMap();
public A(Map map){
this.map = map;
}
public String getresult(String key) {
//uses hashmap to send result.
}
}
//Helper Class
public class URLToJSon() {
//Add private constructor
public static Map convertUrlToJSon(String url) {
//do the conversion and return a hashmap
}
}
通过这种方式,我们可以遵循单一责任原则 。
现在,这两个类也都可以测试。
是的,这是糟糕的设计:
如果必须通过静态字段访问A
,我建议:
public class A {
private static Map<String, String> map;
/** must be invoked before get is first called */
public static void init(Map<String, String> newmap) {
map = newmap;
}
public static String get(String key) {
return map.get(key);
}
}
这将使用数据的关注与获取数据的关注区分开了,从而允许分别替换和测试每个数据。
还应考虑摆脱static
,因为它强制在整个应用程序中同时只有一个映射,这非常不灵活。 (有关方法,请参见Ajay答案中的第二个代码示例)
URL在哪里设置? 在构造函数中? 如果是这样,只需做
//Normal init stuff like set url here, followed by
if (! some check for if json is set) {
setJson();
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.