如何将双向链表转换为二叉树

时间:2016-03-02 23:29:49

标签: c recursion binary-tree doubly-linked-list

    struct cnode
{
  int info;
  struct cnode *next;
  struct cnode *previous;
};
typedef struct cnode cnode;

预先制作的DOUBLY LINKED LIST:1<->2<->3<->4<->5<->6<->7

所以我试图创建一个递归函数来抓取双向链表(root = 4)的中间位置并将其转换成剩余的二进制树。我还不熟悉递归,所以对代码的解释会非常感激!

EX.     4
      /  \
     2    6
    / \  / \
   1   3 5  7

这是我到目前为止的代码(由于递归困难,这个代码并不多)

void *convert(cnode *head){
  if(head == NULL)
    return;
  int count = 0;
  cnode *tempHead = head;
  while(tempHead != NULL){
    count++;
    tempHead = tempHead->next;
  }
  int move = (count/2) + (count%2);
  int i;
  for(i=1; i<move; i++){
    head = head->next;
  }
}

几乎只是将头部指针设置为中间信息(4)

3 个答案:

答案 0 :(得分:1)

我想我理解;你从 cnodes 制作一个平衡的二叉树,其中上一个下一个指针被重复用于左右子树。

...这就是你的算法。

  • 找到二叉树的中间节点(您已经完成了)。
  • 将左半边变为二叉树。左半部分是原始头部,最后一个元素(中间 - >上一个)现在有一个下一个指针为NULL。
  • 将此左半部分链接到中间&gt;上一个(被劫持为左子树)。
  • 将右半边变为二叉树;这是以中间&gt;下一个为首的。将其设为 middle-&gt; next 的新值。

  • 您必须将原始头部保留为指向左侧子树的指针。

  • 您希望您的例程返回二叉树的根目录,因此之前的调用可以将其链接到上面的级别。
  • 您仍然需要选择终止条件,例如头指针为 NULL

这会让你转向解决方案吗?

答案 1 :(得分:0)

首先,您正在尝试将DLL转换为二叉树,假设DLL是按照您必须生成的二叉树的顺序给出的。请注意,只有顺序遍历才能生成唯一的树。即使您必须生成BST,也不能仅通过顺序遍历来实现。我实际上认为你要做的是将其转换为平衡的BST。即便如此,它也不会是独一无二的 这是算法..
1)获取链表的中间部分并将其设为root 2)左半部分和右半部分递归相同        a)获得左半部分的中间部分,使其成为根部的孩子           在步骤1中创建        b)获得右半部分的中间位置并使其成为正确的孩子           在步骤1中创建的root。
时间复杂度:O(nLogn)其中n是链表中的节点数 虽然如果你在BST中以与双链表中出现的顺序相同的顺序插入节点,它可以在O(n)中求解。

答案 2 :(得分:0)

我希望这段代码对您有所帮助。用双向链表的头调用DLL2BT方法,该方法返回创建的树的根节点。

class box
{
    int data;
    box left=null,right=null;
    box(int a)
    {
        data=a;
    }
}

public static box DLL2BT(box head)// head = linked list head
{       
    if(head!=null)
    {
        box node=null;
        try 
        {
            node = findMid(head);
            node.left.right=null;
            node.left=DLL2BT(head);
            node.right.left=null;
            node.right=DLL2BT(node.right);
        }
        catch( Exception e){ }
        return node;
    }
    return null;
}

public static box findMid(box head)
{
    box slow=head,fast=head.right;
    try
    {
        while(fast!=null)
        {
            slow=slow.right;
            fast=fast.right.right;
        }
    }
    catch(Exception e){ }
    return slow;
}