看大神怎样带你一劳永逸——封装之美

来源:互联网 发布:linux uboot启动过程 编辑:程序博客网 时间:2024/05/17 00:58

        最近做项目,由于好多地方需要树形显示,所以需要封装一个树形结构的显示,将代码重复降到最低。树形结构的显示用的是dwz框架中自带的。

需要树形结构显示的类:Organization、Module,只列出二者的公共属性,其它属性不列,

@Entity@Table(name = "security_organization")public class Organization{private static final long serialVersionUID = 1775351000271333679L;@Id      @GeneratedValue(generator = "hibernateuuidgenerator")      @GenericGenerator(name = "hibernateuuidgenerator", strategy = "uuid")  protected String id;private String name;@ManyToOne()@JoinColumn(name="pid")private Organization parent;@OneToMany(mappedBy="parent",fetch=FetchType.EAGER)private List<Organization> children;private boolean isleaf;//其它属性}@Entity@Table(name="security_module")public class Module{/** 描述  */private static final long serialVersionUID = -6926690440815291509L;@Id      @GeneratedValue(generator = "hibernateuuidgenerator")      @GenericGenerator(name = "hibernateuuidgenerator", strategy = "uuid")  protected String id;private String name;@ManyToOne()@JoinColumn(name="pid")private Module parent;@OneToMany(mappedBy="parent",fetch=FetchType.EAGER)private List<Module> children;private boolean isleaf;//其它属性}

        大家可以看到,里面列的都是树所必须的属性:id、父id、是否为叶子结点,还可以考虑再往里面加。其实除了parent和children外,其它的都可以提到一个类里,这样,就可以再减少代码的重复。

        下面再来再来看看我对生成树代码的封装:

public class GenerateTree {private String target = "navTab";private String style = "tree";public String generate(String style, String parentURL, String sonURL, String target,String rel, Object parent) {StringBuffer sbTreeHTML = new StringBuffer();if (style.equals("")) {style = this.style;}if (target.equals("")) {target = this.target;}if (parent == null) {return "";}try {sbTreeHTML.append("<ul class='" + style + "'>");sbTreeHTML.append("<li><a href='" + (isIsleaf(parent) ? sonURL : parentURL)+ "?id=" + getId(parent) + "' target='" + target + "' rel='" + rel+ "'>" + getName(parent) + "</a>");//如果子不为空,那么对子进行遍历if (getChildren(parent) != null && getChildren(parent).size() > 0) {sbTreeHTML.append(generateSon(style, parentURL, sonURL, target, rel,getChildren(parent)));}sbTreeHTML.append("</li>");sbTreeHTML.append("</ul>");} catch (Exception e) {return "";}return sbTreeHTML.toString();}private String generateSon(String style, String parentURL, String sonURL,String target, String rel, List<Object> objects)throws IllegalArgumentException, SecurityException, IllegalAccessException,InvocationTargetException, NoSuchMethodException {StringBuffer sbTreeHTML = new StringBuffer();sbTreeHTML.append("<ul>");for (Iterator<Object> iter = objects.iterator(); iter.hasNext();) {Object tree = iter.next();sbTreeHTML.append("<li><a href='" + (isIsleaf(tree) ? sonURL : parentURL)+ "?id=" + getId(tree) + "' target='" + target + "' rel='" + rel+ "'>" + getName(tree) + "</a>");//如果不为空,对其进行递归if (getChildren(tree) != null && getChildren(tree).size() > 0) {sbTreeHTML.append(generateSon(style, parentURL, sonURL, target, rel,getChildren(tree)));}sbTreeHTML.append("</li>");}sbTreeHTML.append("</ul>");return sbTreeHTML.toString();}//获取对象的idprivate String getId(Object o) throws IllegalArgumentException, SecurityException,IllegalAccessException, InvocationTargetException, NoSuchMethodException {return (String) o.getClass().getDeclaredMethod("getId").invoke(o);}//获取对象的childrenprivate List<Object> getChildren(Object o) throws IllegalArgumentException,SecurityException, IllegalAccessException, InvocationTargetException,NoSuchMethodException {return (List<Object>) o.getClass().getDeclaredMethod("getChildren").invoke(o);}//获取对象的isleafprivate boolean isIsleaf(Object o) throws IllegalArgumentException,SecurityException, IllegalAccessException, InvocationTargetException,NoSuchMethodException {return Boolean.parseBoolean((String) o.getClass().getDeclaredMethod("isIsleaf").invoke(o));}//获取对象的nameprivate String getName(Object o) throws IllegalArgumentException, SecurityException,IllegalAccessException, InvocationTargetException, NoSuchMethodException {return (String) o.getClass().getDeclaredMethod("getName").invoke(o);}}

        生成是生成了,那么应该怎样调用呢?再来看下面的吧:

public String generate(){GenerateTree gt=new GenerateTree();Module module=new Module();module.setId("");String treeModule=gt.generate("", "parentURL", "sonURL", "", "jbsx", module);Organization org=new Organization();org.setId("");String treeOrg=gt.generate("", "parentURL", "sonURL", "", "jbsx", module);request.setAttribute("treeModule", treeModule);request.setAttribute("treeOrg", treeOrg);return "success";}

        看到调用,不知细心、耐心的你是否已经发现,这个树形结构代码生成具有很好的扩展性:

        若现在又有一个需要树形显示:Tree,那么Tree只需要按着开关写的属性名进行扩展,那么就可以用封装好的方法生成树形结构代码。这样,递归只需要出现一次即可。

        经过这次的封装,我感觉提取需要的是一个过程,而提取的实现,需要的是知识面的宽阔。一如如果不是这次项目的封装,我还不知道参数后面可以加三个点呢。

        封装的过程是痛苦的,但结果是美好的~~

7 0