有一次要做一个行业分类的菜单,获取级联关系,由于是个新手,没有这方便的经验,做了很久才整出来一个蹩脚的方法,下面展示一下:
数据库:
CREATE TABLE `enterprise_type` (
`c_id` int(11) NOT NULL auto_increment COMMENT '企业类型编号',
`c_name` varchar(100) NOT NULL COMMENT '企业类型名称',
`c_parentid` int(11) default NULL COMMENT '父类型编号',
PRIMARY KEY (`c_id`),
KEY `FK_enterprise_type` (`c_parentid`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
用Myeclipse的工具生成的实体类为:
// default package
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;
import javax.persistence.Table;
/**
* EnterpriseCategory entity. @author MyEclipse Persistence Tools
*/
@Entity
@Table(name = "enterprise_type", catalog = "")
public class EnterpriseCategory implements java.io.Serializable {
// Fields
private Integer CId;
private EnterpriseCategory parentCategory;
private String CName;
private List<EnterpriseCategory> childCategory = new ArrayList<EnterpriseCategory>();
// Property accessors
@Id
@GeneratedValue(strategy = IDENTITY)
@Column(name = "c_id", unique = true, nullable = false)
public Integer getCId() {
return this.CId;
}
public void setCId(Integer CId) {
this.CId = CId;
}
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "c_parentid")
public EnterpriseCategory getParentCategory() {
return this.parentCategory;
}
public void setParentCategory(EnterpriseCategory parentCategory) {
this.parentCategory = parentCategory;
}
@Column(name = "c_name", nullable = false, length = 100)
public String getCName() {
return this.CName;
}
public void setCName(String CName) {
this.CName = CName;
}
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "EnterpriseCategory")
public List<EnterpriseCategory> getChildCategory() {
return this.childCategory;
}
public void setChildCategory(
List<EnterpriseCategory> childCategory) {
this.childCategory = childCategory;
}
}
其他的不展示了,直接展示实现方法:
import org.apache.log4j.Category;
import org.hibernate.Criteria;
import org.hibernate.FetchMode;
import org.hibernate.criterion.Restrictions;
import org.springframework.stereotype.Repository;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
/**
* Created with IntelliJ IDEA.
* User: Administrator
* Date: 12-7-13
* Time: 上午11:35
* To change this template use File | Settings | File Templates.
*/
@Repository("enterpriseCategoryDao")
public class EnterpriseCategoryDaoHobernate extends EnterpriseAutoInjectGenericHibernateDAO<EnterpriseCategory, Integer> implements EnterpriseCategoryDao {
/**
* 根据给定的类别获取所有级联的cid
*
* @param id
* @return
*/
public List<Integer> getList(Integer id) {
List<Integer> result = new ArrayList<Integer>(); //存放最终结果
if (id == null) {
return result;
}
List list = this.getSession().createCriteria(EnterpriseCategory.class)
.setFetchMode("parentCategory", FetchMode.JOIN)
.add(Restrictions.eq("parentCategory.CId", id))
.list();
if (list.size() == 0) {
result.add(id);
} else {
result.add(id);
result.addAll(add(list));
}
return result;
}
/**
* @param list 得到的enterpriseCategory对象的集合
* @return
*/
public List<Integer> add(List list) {
List<Integer> result = new ArrayList<Integer>(); //存放最终结果
if (list.size() == 0) {
return result;
}
try {
for (int i = 0; i < list.size(); i++) {
EnterpriseCategory childCategory = (EnterpriseCategory) list.get(i);
result.add(childCategory.getCId());
List<EnterpriseCategory> childList = childCategory.getChildCategory();
if (childList.size() != 0) {
result.addAll(add(childList));
}
}
} catch (Exception e) {
e.printStackTrace();
}
return result;
}
}
这样就能获取到级联关系的类型Tree,这个方法可以实现N层级联关系
下面是其他高手写的
实体类:
import javax.persistence.*;
import static javax.persistence.GenerationType.IDENTITY;
@Entity
@Table(name = "enterprise_type", catalog = "")
public class EnterpriseCategory implements java.io.Serializable {
// Fields
private Integer CId;
private String CName;
private Integer parentId;
// Property accessors
@Id
@GeneratedValue(strategy = IDENTITY)
@Column(name = "c_id", unique = true, nullable = false)
public Integer getCId() {
return this.CId;
}
public void setCId(Integer CId) {
this.CId = CId;
}
@Column(name="c_parentid")
public Integer getParentId() {
return parentId;
}
public void setParentId(Integer parentId) {
this.parentId = parentId;
}
@Column(name = "c_name", nullable = false, length = 100)
public String getCName() {
return this.CName;
}
public void setCName(String CName) {
this.CName = CName;
}
}
实现方法:
private List<Integer> getCidList(Integer catId, boolean includeSelf) {
List<Integer> ret = new ArrayList<Integer>();
List<Integer> list = getSubCatList(catId);
ret.addAll(list);
if (!includeSelf) ret.remove(catId);
return ret;
}
/**
* 指定分类ID的所有子节点
*
* @param catId
* @return
*/
private List<Integer> getSubCatList(Integer catId) {
List<EnterpriseCategory> allCats = enterpriseCategoryDao.loadAll();
return getSubCatList(catId, allCats);
}
private List<Integer> getSubCatList(Integer cid, List<EnterpriseCategory> allCats) {
Map<Integer, List<Integer>> FK_Parent_Child = new HashMap<Integer, List<Integer>>();
for (EnterpriseCategory cat : allCats) {
// 建立所有带有子节点的节点对应关系
List<Integer> list = FK_Parent_Child.get(cat.getParentId());
if (list == null) {
list = new ArrayList<Integer>();
list.add(cat.getCId());
FK_Parent_Child.put(cat.getParentId(), list);
} else {
list.add(cat.getCId());
}
}
return getSubCats(cid, FK_Parent_Child);
}
private List<Integer> getSubCats(Integer cid, Map<Integer, List<Integer>> FK_Parent_Child) {
List<Integer> nodes = new ArrayList<Integer>();
if (FK_Parent_Child.containsKey(cid)) {
// 非叶子节点
nodes.add(cid);
List<Integer> childNodes = FK_Parent_Child.get(cid);
for (Integer childId : childNodes) {
nodes.addAll(getSubCats(childId, FK_Parent_Child));
}
} else {
// 叶子节点
nodes.add(cid);
}
return nodes;
}
可以根据指定的ID获取下面的所有的子节点的id。
记下来,说不定以后会用到。虽然自己写的不怎么的,单也是辛苦的成果,记下来