【问题标题】:Intersection of 2 binary search trees2个二叉搜索树的交集
【发布时间】:2011-04-20 10:22:49
【问题描述】:

嘿,所以我想创建一个新树,它基本上是两个给定二叉搜索树的交集(交集的数学定义)。我有一种方法可以打印出树的特定级别的所有节点,我有一种方法可以找出树的深度。到目前为止,我正在粘贴我的工作,尽管它不完整并且我被困在logic.Help 将不胜感激。

    public static Bst<Customer> intersect (Bst<Customer> a, Bst<Customer> b){
    Bst<Customer> result = new Bst<Customer>();
    BTNode<Customer> cur1;
    BTNode<Customer> cur2;
    BTNode<Customer> cur3;
    cur1=a.root;
    cur2=b.root;
    cur3=result.root;
    int Resultdepth;
    if(a.maxDepth()<b.maxDepth())
        Resultdepth=a.maxDepth();
    else
        Resultdepth=b.maxDepth();

    if(cur1==null || cur2==null){ // Handeling the root case intially
        result = null;
    }
    else 
      cur3.item.set_account_id(cur1.item.get_accountid()+ cur2.item.get_accountid());

    cur1=cur1.left;
    cur2=cur2.left;
    cur3=cur3.left;       

    while(<some check>){

    }


    return result;

}


    public int maxDepth(){
        return mD(root);
    }

    int mD(BTNode<E> node){
       if (node==null) {
            return(0);
        }
       else {
            int lDepth = mD(node.left);
            int rDepth = mD(node.right);
            // use the larger + 1
            return(Math.max(lDepth, rDepth) + 1);
        }
    }

     // for printing the nodes at a particular level and giving the starting level
      public void PrintAt(BTNode<E> cur, int level, int desiredLevel) {
         if (cur == null) {
            return;
        }
         if (level == desiredLevel) {
             System.out.print(cur.item.toString() + "");
          }
         else {
             PrintAt(cur.left, level+1, desiredLevel);
             PrintAt(cur.right, level+1, desiredLevel);
          }
}

【问题讨论】:

  • 我在您的代码中没有看到任何与“交集”相关的内容...
  • 对不起,我忘了把我的代码放进去。它现在在那里。
  • 我强烈建议您不要尝试使用诸如cur1, cur2, cur3 等离散变量来硬编码任何最大深度。您的解决方案必须适用于所有 情况。您会发现一般情况的解决方案也比做出假设的解决方案更简单。

标签: java algorithm binary-search-tree


【解决方案1】:

您必须同时“同步”按顺序遍历两棵树。

我建议为您的类实现 Iterable 接口。然后你从两棵树中得到第一个值。如果它们相等,则将其放入新树中,并从两个迭代器中获取下一个值。如果不是,则使用较小的值迭代迭代器,直到您获得的值与另一个迭代器的最后一个值一样大。冲洗并重复。

【讨论】:

  • 我也会这样做。我想不出更有效的解决方案(除非,如果您对数据的平均密度有更多了解,那么当您遇到足够大的差距时,您可以将基本的树遍历与部分二叉搜索结合起来)。
  • 嗯,我真的不知道如何实现可迭代类,但我编写了一些代码并正在调试它。我在这里发布了一个新问题 stackoverflow.com/questions/5735806/…>
【解决方案2】:

两棵树的交集大概是两棵树中的节点吧?

鉴于您必须探索树才能做到这一点,为什么不只进行中序遍历,存储节点,然后对有序列表进行交集操作?

【讨论】:

  • 杰夫,是的,交集是两棵树中的节点。在这种情况下,我真的不想使用列表。我知道这可以通过条件检查来完成,我希望能够做到这一点。
【解决方案3】:

我对这样一个路口的建议很简单:

给定树A和树B,求树C = A \intersect B:

1:复制树 A 或 B。为了清楚起见,我们假设 A。
这个副本现在是你的树 C。现在让我们“修剪”它。
2:对于 c = C.root_node 和 b = B.root_node:
如果 b==c,
对节点 b.left、c.left 重复该过程
对节点 b.right、c.right 重复该过程
否则,
移除 c(从而移除所有后续的孩子,暗示他们不相等)

如果这个实现可行,它将避免使用迭代器等,并归结为简单的递归遍历。 (Like this!)

询问您是否需要进一步说明。

问候。

【讨论】:

  • 你为什么要“如果 b==c”。我看不出你想要达到什么目的
  • 我采取了相反的方法。复制所有内容,然后删除差异。
  • @Michael,假设有两棵树 A 和 B。A.root->data = 5, A.root->left->data = 6, A.root->right->data = 8 B.root->data = 5, B.root->left->data = 7, B.root->right->data = 8 根据你的方法,不会有交集
【解决方案4】:

对于查找两个二叉搜索树的交集的递归实现,我想出了以下代码。我不太确定时间复杂度,但它确实可以正常工作。

void BST::findIntersection(cell *root1, cell * root2) {

if(root1 == NULL ) { 
//  cout<<"Tree 1 node is null , returning"<<endl;  
    return;
}
if(root2 == NULL) {
//  cout<<"Tree 2 node is null , returning"<<endl;  
    return;
}
//cout<<"Comparing tree 1 : "<<root1->data<< "   and tree 2 : " << root2->data<<endl;
if(root1->data==root2->data) {
//  cout<<"tree 1 equal to tree 2 "<<endl;
    insert(root1->data);
//  cout<<"Inserting in new tree : "<<root1->data<<endl;
    findIntersection(root1->left,root2->left);
    findIntersection(root1->right, root2->right);
}
else if(root1->data>root2->data) {
//  cout<<"tree 1 > tree 2 "<<endl;
    findIntersection(root1,root2->right);
    findIntersection(root1->left, root2);
}
else  {
//  cout<<"tree 1 < tree 2 "<<endl;
    findIntersection(root1->right,root2);
    findIntersection(root1, root2->left);
}

}

【讨论】:

    猜你喜欢
    • 2015-08-14
    • 2021-11-27
    • 1970-01-01
    • 2011-11-24
    • 2023-03-08
    • 1970-01-01
    • 2017-10-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多