网站首页
JSP空间
动态资讯
开源项目
技术文档
资源下载
J2EE资源
客户论坛
在线支付
 
  技术文档>>JAVA>>新手入门>>基础入门>查看文档  
  java程序的脏数据问题处理     
  文章作者:未知  文章来源:水木森林  
  查看:67次  录入:管理员--2007-11-17  
 
  脏数据(out-of-date data),指过时的数据。
  
  如果在您的java程序中存在脏数据,将或多或少地给软件系统带来一些问题,如:无法实时地应用已经发生改变的配置,软件系统出现一些莫名其妙的、难以重现的、后果严重的错误等等。尽量避免脏数据的存在是非常有价值的。本文希望能在这方面给同行们一点帮助。
  
  fragment 1. 缓存技术的脏数据问题
  
  /**
  * a report printer is used to print a report.
  *
  * @version 1.0 9/9/2003
  * @author bill
  */
  public class reportprinter {
  /**
  * constructs a <code>reportprinter</code> instance.
  */
  public reportprinter() {
  // do something...
  }
  
  /**
  * prints a printable.
  *
  * @param printable the specified printable object
  */
  public void print(printable printable) {
  graphics g = getgraphics();
  g.setfont(getreportfont(printable.getfont());
  
  printable.print(g);
  }
  
  /**
  * returns the corresponding report font of a java font.
  *
  * @param javafont the specified java font
  * @return the corresponding report font
  */
  private font getreportfont(font javafont) {
  font reportfont = fontmap.get(javafont);
  
  if(reportfont == null) {
  reportfont = loadfont(javafont);
  fontmap.put(javafont, reportfont);
  }
  
  return reportfont;
  }
  
  /**
  * loads the corresponding report font of a java font.
  *
  * @param javafont the specified java font
  * @param the corresponding report font
  */
  protected static font loadfont(font javafont) {
  font reportfont = null;
  
  // do something...
  
  return reportfont;
  }
  
  /**
  * the font map(java font->report font).
  */
  private static hashmap fontmap = new hashmap();
  }
  
  fragment 1中,由于装载一个java font所对应的report font开销较大,使用了缓存技术来避免这种开销。这是一种常见的提高性能的方式,而且在一般情况下运行良好。但是fragment 1的设计与实现可能是不完备的,因为极有可能一个java font所对应的report font在系统启动之后发生变化,在这种变化发生之后,只有重启软件系统才能装载之,这常常是最终用户的抱怨之一。更可怕的是,类似的这种脏数据的存在还可能带来其它严重的、无法想象的后果。
  
  如何避免使用缓存技术所带来的脏数据问题呢?
  
  在设计、实现和测试时,应该清晰定义缓存数据的更新:
  i. 不考虑缓存数据的更新,重启软件系统是一种必要的方式;
  ii. 不考虑缓存数据的更新,缓存数据不可能成为脏数据(但在软件系统中,往往“不可能”会在一次又一次的重构之后变为“可能”);
  iii. 考虑缓存数据的更新,当源数据变化时,实时更新缓存数据。
  
  fragment 2. singleton模式的脏数据问题
  
  /**
  * a storage usage handler is used to query the storage usage of users.
  *
  * @version 1.0 9/9/2003
  * @author bill
  */
  public class storageusagehandler {
  /**
  * returns a <code>storageusagehandler</code> instance.
  *
  * @return the single <code>storageusagehandler</code> instance
  */
  public static storageusagehandler getstorageusagehandler() {
  if(handler == null) {
  handler = new storageusagehandler();
  }
  
  return handler;
  }
  
  /**
  * constructs a <code>storageusagehandler</code> instance.
  */
  private storageusagehandler() {
  users = context.getallusers();
  }
  
  /**
  * returns the storage sizes of all the users.
  *
  * @return the storage sizes
  */
  public long[] getsizes() {
  long sizes[] = new long[users.size()];
  
  for(int i = 0; i < users.size(); i++) {
  sizes[i] = getonesize(users.get(i));
  }
  }
  
  /**
  * returns the storage size of a user.
  *
  * @param user the specified user
  * @return the storage size
  */
  protected long getsize(user user) {
  // do something...
  
  return 0;
  }
  
  /**
  * the <code>storageusagehandler</code> singleton.
  */
  private static storageusagehandler handler;
  
  /**
  * the users.
  */
  private list users;
  }
  
  您看出了问题所在吗?
  
  fragment 2中,由于没有必要次次实例化storageusagehandler而带来不必要的开销,采用了singleton模式以保证storageusagehandler只被实例化一次。
  
  在实例化sotrageusagehandler时,storageusagehandler的类成员users将被赋值。由于不存在任何对users重新赋值的方法,一直驻留在软件系统中的users将不会发生任何变化。在软件系统启动之后,增加、删除或修改用户的操作经常会发生,而一旦发生这类操作,users就成为了脏数据,fragment 2将无法正常工作。
  
  如何避免使用singleton模式所带来的脏数据问题呢?
  
  对于singleton类的类成员:
  i. 对于与singleton类外部无依赖关系的类成员,不存在这种问题;
  ii. 对于依赖于singleton类外部的类成员,且该类成员不存在更新机制,最好是将其去掉,需要时从singleton类外部直接获取;如果这种办法不可行,应提供机制以确保在使用该类成员之前,该类成员已经被更新过。
  
  fragment 3. 类使用的脏数据问题
  
  /**
  * a storage usage handler is used to query the storage usage of users.
  *
  * @version 1.0 9/9/2003
  * @author bill
  */
  public class storageusagehandler implements adminhandler {
  /**
  * constructs a <code>storageusagehandler</code> instance.
  */
  private storageusagehandler() {
  users = context.getallusers();
  }
  
  /**
  * returns the storage sizes of all users.
  *
  * @return the storage sizes
  */
  public long[] getsizes() {
  long sizes[] = new long[users.size()];
  
  for(int i = 0; i < users.size(); i++) {
  sizes[i] = getonesize(users.get(i));
  }
  }
  
  /**
  * returns the storage size of a user.
  *
  * @param user the specified user
  * @return the storage size
  */
  protected long getsize(user user) {
  // do something...
  
  return 0;
  }
  
  /**
  * displays the storage usage of users.
  *
  * @param req the http servlet request
  * @param res the http servlet response
  *
  * @throws ioexception
  * @throws servletexception
  */
  public void process(httpservletrequest req, httpservletresponse res)
  throws ioexception, servletexception {
  
  res.setcontenttype("text/html");
  res.setheader("cache-control", "no-cache");
  res.setheader("pragma","no-cache");
  res.setdateheader("expires", 0);
  
  printwriter writer = new printwriter(res.getoutputstream());
  long sizes[] = getsizes();
  writer.println("<html><title>storage usage</title><body>");
  writer.println("<table width='100%'>");
  
  for(int i = 0; i < sizes.length; i++) {
  writer.print("<tr><td align='center' nowrap>");
  writer.print(users.get(i) + ": " + sizes[i]);
  writer.println("</td></tr>");
  }
  
  writer.println("</body></html>");
  writer.flush();
  writer.close();
  }
  
  /**
  * the users.
  */
  private list users;
  }
  
  /**
  * an admin servlet as a http servlet to process the admin http servlet
  * request and response.
  *
  * @version 1.0 9/9/2003
  * @author bill
  */
  public class adminservlet extends httpservlet {
  /**
  * initiates the configuration.
  *
  * @param config the servlet config
  *
  * @throws servletexception
  */
  private void initconfig(servletconfig config) throws servletexception {
  // do somet
 
 
上一篇: starsuite 6.0和sdk安装以及配置指南之一    下一篇: 深入理解:全面认识java
  相关文档
javaserver pages 3rd edition 11-17
java布局管理器在现实工程中的应用 11-16
如何在tomcat配置web在线后台管理 11-17
java繁体中文处理完全攻略 11-17
关于23种设计模式的有趣见解 11-17
新版junit 4.0 抢先体验 11-17
java入门笔记3_datastructure 11-17
javamail常见问题之编程问题 11-17
adapter 模式在 j2se 事件处理中的应用 12-12
用biojava开发基于隐马尔科夫模型的应用 11-17
.net中实现彩色光标,动画和自定义光标 11-17
什么是j2me及其基本慨念 11-16
编程中的一些共同的问题 11-17
在java程序中实现对数字的格式化 11-17
开发java的又一利器-visual cafe 11-16
java中static、this、super、final用法简谈(一) 11-17
java截获标准输出 11-17
actionform的生命周期浅探 11-16
漫谈hibernate的前世今生 11-16
如何处理java及其相关字符集编码的问题 11-16
返回首页 | 关于我们 | J网章程 | JSP空间合租 | 客服中心 | 免责声明 | 常见问题 | 参观机房
本站主机空间代理至厦门市华众网络科技有限公司
《中华人民共和国增值电信业务经营许可证》
编号:闽B2-20050079
@2005-2008福建JSP技术网 版权所有 闽ICP备05000928号
厦门(总部):13616026886 福州:0591-87655121
邮箱:admin@fjjsp.com 站长QQ,点击这里给我发消息