假设存在一棵树,为了论证而使用XML树。并且您需要一组完整的根到节点路径,但是您希望将该组划分为i的组,其中i是用户指定的。
所以例如一个html文档:
/html
/html/head
/html/head/title
/html/head/title/[text]
/html/body
/html/body/[text]
例如,当我是3时
{{1, 11, 111}, {1111, 12, 121}}
然后成为例如:
{3, 4}
使用只能获取节点名称的简化树类;获取子树的ArrayList;并检查它是否是叶节点;构建这组哈希的最佳方法是什么?
编辑:请参阅下面的示例解决方案答案,这远非最佳,因为它非常慢,甚至可能不是最好的方法。
答案 0 :(得分:1)
我自己的解决方案如下,虽然我不确定这是否是实现这一目标的最有效方式......也许其他人可以提供一些关于Java错综复杂的见解。
public ArrayList<Integer> makePathList(AbstractTree<String> tree){
StringBuilder buffer = new StringBuilder();
ArrayList<Integer> pl = new ArrayList<Integer>();
ArrayList<StringBuilder> paths = getPaths(tree, buffer);
for(StringBuilder sb : paths){
pl.add(sb.toString().hashCode());
}
return pl;
}
public ArrayList<StringBuilder> getPaths(AbstractTree<String> tree, StringBuilder parent){
ArrayList<StringBuilder> list = new ArrayList<StringBuilder>();
parent.append("/");
parent.append(tree.getNodeName());
list.add(new StringBuilder(parent));
if (!tree.isLeaf()){
int i = 0;
Iterator<AbstractTree<String>> child = tree.getChildren().iterator();
while (i < tree.getChildren().size()){
list.addAll(getPaths(child.next(), new StringBuilder(parent)));
i++;
}
}
return list;
}
public HashSet<Integer> createShingleSet(ArrayList<Integer> paths, int shingleLength){
HashSet<Integer> shingleSet = new HashSet<Integer>();
for(int i = 0; i < paths.size(); i += shingleLength){
Multiset<Integer> set = new Multiset<Integer>();
for(int j = 0; j < shingleLength; j++){
if (i + j < paths.size())
set.add(paths.get(i + j));
}
shingleSet.add(set.hashCode());
}
return shingleSet;
}
编辑:传递StringBuilder更适合大文件。
编辑:对于提供相同哈希码的相同路径,这似乎需要在之后应用
答案 1 :(得分:0)
如果我这样做,我的第一个想法是MultiMap(那里有several implementations,或者你可以自己动手)。
这个多图的关键是用于到达节点的部分路径,值数组将是列表(不是设置,除非顺序不重要 - 并且在XML中)是共享该部分的节点路径。