我的叶子节点上有一个带有矩形的树,还有一个' V'或者是' H'在内部节点中。考虑到它们的宽度和高度,我想打包矩形。如果有一个' V',我会打包左右孩子,如果是' H',我想把左孩子打包在右孩子的上面。最后,我想确定每个矩形的坐标。我附上了一张图片,显示了树和构造的包装。
我正在做的是,我正在浏览树中的每个节点。当它到达叶节点时,它会构建一个结构矩形并将其存储到一个数组中。然后当它到达一个V'时,我只需通过添加数组中第二个最后一个矩形的宽度来更改数组中最后一个矩形的x坐标。我构造了一个新的矩形,它适合整个最后一个矩形集并将其放入数组中。如果我得到一个' H,我会增加数组中特定矩形的y坐标。但是,我在这方面遇到了麻烦,因为我不知道哪个矩形y坐标应该改变。可以有任何数量的这种矩形。 PLEASEE HELP !!
答案 0 :(得分:0)
在仔细检查了你的问题后,我想我可能已经理解了你的问题。
您的包装有一条规则(您没有声明),对于左/右包装,矩形需要底部对齐。对于顶部/底部包装,矩形需要左对齐。你的坐标系使用左下角为(0,0)
我还假设在打包完成后你需要生成每个矩形的坐标(假设每个矩形的尺寸都是已知数据,对于每个矩形,你只需要产生1个坐标,例如左下角的坐标)
使用数组来保存这些数据可能不起作用。您的输入打包关系存储在树中,您可以使用完全相同的树来存储打包结果。
树中的每个节点都代表一个矩形。内部节点将表示“打包”子矩形的矩形。对于每个节点,您需要定义变量来存储它的维度,它是绝对坐标,它是相对坐标(相对于它的直接父级)。
然后,您可以在树中进行两次遍历,首先遍历从下到上计算所有相对坐标(深度优先搜索),第二次遍历从上到下扣除绝对坐标。
下面的是第一次遍历的伪代码(在DFS的递归函数中)
packtree(treeroot)
{
if(treeroot is a leaf) return; // do nothing and return the function
packtree(leftchild);
packtree(rightchild);
if(treeroot is V type)
{
treeroot.width = leftchild.width+rightchild.width
treeroot.height = leftchild.height > rightchild.height ? leftchild.height : rightchild.height
leftchild.relative_cor = (0,0)
rightchild.relative_cor = (leftchild.width, 0)
}
else if(treeroot is H type)
{
treeroot.width = leftchild.width> rightchild.width ? leftchild.width:rightchild.width
treeroot.height = leftchild.height + rightchild.height
leftchild.relative_cor = (0, rightchild.height) // because he is sitting on top of the rightchild
rightchild.relative_cor = (0,0)
}
}
我会把第二次遍历留给你。 :)
答案 1 :(得分:0)
我明白了!
我使用firemana的建议不使用数组。但是我只在一次遍历中完成了它。我去了树的每个节点。如果它是一个叶子节点,我什么也没做。如果它是'H',我首先去右边然后去左边的孩子。如果它是'V',我先向左转,然后向右转。如果节点是'H',我将所有左子节点的y坐标更改为右子节点的高度。如果它是'V',我将正确孩子的x坐标更新为左孩子的宽度。
一旦我们找出逻辑,解决方案就很容易了。谢谢大家!