那一年你定义了一个接口

那一年,你定义了一个接口:

public interface WtfService {

public void process(WtfDto dto);

}


为了良好的扩展性,你定义了一个扩展字段,Map<String, String>类型,并且在文档里强调了“key和value都是String类型”:

public class WtfDto  implements Serializable {

//other fields

private Map<String, String> extInfo;

public Map<String, String> getExtInfo() {
return extInfo;
}

public void setExtInfo(Map<String, String> extInfo) {
this.extInfo = extInfo;
}

}



然后实现这个接口:


public class WtfServiceImpl implements WtfService {

public void process(WtfDto dto) {
Map<String, String> extInfo = dto.getExtInfo();
for (Entry<String, String> entry : extInfo.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
System.out.println(key + "=" + value);
}
}
}


测试

 @Test
public void normal() {
WtfService service = new WtfServiceImpl();
WtfDto dto = new WtfDto();
Map<String, String> extInfo = new HashMap<String, String>();
extInfo.put("name", "Kobe");
dto.setExtInfo(extInfo);
service.process(dto);
}


一切正常。世界看起来是那么完美。

直到某一天,你看到这样的一个报错:


java.lang.ClassCastException: java.lang.Double cannot be cast to java.lang.String
at com.sample.WtfServiceImpl.process(WtfServiceImpl.java:40)



你百思不得期解:
明明是Map<String, String>类型,怎么会有Double?
难道调用方还能传一个Double过来?

自己传一个Double看看:


@Test
public void error() {
WtfService service = new WtfServiceImpl();
WtfDto dto = new WtfDto();
Map<String, Object> extInfo = new HashMap<String, Object>();
extInfo.put("name", 10.999);
dto.setExtInfo(extInfo); //编译不通过
service.process(dto);
}


编译不通过。

那Double到底是怎么传过来的?

真相是:

@Test
public void warning() {

WtfService service = new WtfServiceImpl();
WtfDto dto = new WtfDto();
//Map<String, Object> extInfo = new HashMap<String, Object>();
Map extInfo = new HashMap(); //eclipse在这一行会有warning提示
extInfo.put("name", 10.99);
dto.setExtInfo(extInfo);
service.process(dto);

}
}


对于没有代码洁癖直接忽视waring或者压根就不懂得泛型的猪队友,他就那么自然而然的写出了上面的代码。
虽然有warning,但毕竟编译通过了。

于是你的服务就理所当然的报错了。

你体会到这个世界的残酷了。

你应该像王叔叔那样,定义一个key-value的类:


public class MatchVariable implements Serializable {

private String key;

private String value;

//getter/setter

}



然后把接口的参数类改成这样:


public class WtfDto implements Serializable {

//...other fields

// private Map<String, String> extInfo;
//
// public Map<String, String> getExtInfo() {
// return extInfo;
// }
//
// public void setExtInfo(Map<String, String> extInfo) {
// this.extInfo = extInfo;
// }



private List<MatchVariable> extInfoList;

public List<MatchVariable> getExtInfoList() {
return extInfoList;
}

//根据Effective java这本书的建议,你不应该直接提供setExtInfoList这样的方法
// public void setExtInfoList(List<MatchVariable> extInfoList) {
// this.extInfoList = extInfoList;
// }

public void addExtInfo(String key, String value) {
if (extInfoList == null) {
extInfoList = new ArrayList<MatchVariable>();
}
extInfo.add(new MatchVariable(key, value));
}

}


猪队友猫队友再也传不了其他类型的参数给你了。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值