在O(1)时间内删去链表节点。

来源:互联网 发布:ps淘宝详情页字体大小 编辑:程序博客网 时间:2024/06/06 01:01

 

60.在O(1)时间内删除链表结点。 题目:给定链表的头指针和一个结点指针,在O(1)时间删除该结点。链表结点的定义如下: struct ListNode { int m_nKey; ListNode* m_pNext; }; 函数的声明如下: void DeleteNode(ListNode* pListHead, ListNode* pToBeDeleted); 分析:这是一道广为流传的Google 面试题,能有效考察我们的编程基本功,还能考察我们 的反应速度, 更重要的是,还能考察我们对时间复杂度的理解。

思路一 :

从表头开始搜索,直到搜索到这个节点为止,但是这个的时间复杂度为 O(n)

 

typedef struct LinkNode
{
 struct LinkNode *next;
 int data;
}node;


void print_1(node *head)
{
 node *p;
 p = head->next;
    while(p != NULL)
 {
  printf("%2d",p->data);
  p = p->next;
 }
}
node *del(node *head ,node *p)
{
 node *s,*s1;
 s = head->next;
 while((p->data != s->data) &&(s != NULL))
 {
  s1 = s;
  s = s->next;
 }
 if(s == head->next)
 {
  head->next = s->next;
  delete p;
  p = NULL;
 }
 else if(s != NULL)
 {
  s1->next = s->next;
  delete p;
  p = NULL;
 }
 else
 {
  printf("mei you ci zhi");
  delete p;
  p = NULL;
 }
 return head;
}

void main()
{
    node *head,*p0 ,*p1,*p2,*head1 ;
 head = (node*)malloc(sizeof(node));
 p0 = (node*)malloc(sizeof(node));
 p1 = (node*)malloc(sizeof(node));
 p2 = (node*)malloc(sizeof(node));
 node *p3 = (node*)malloc(sizeof(node));
 head->next = p0;
 p0->next = p1;
 p1->next = p2;
 p2->next= p3;
 p3->next = NULL;
 p0->data = 0;
 p1->data = 1;
 p2->data = 2; 
 p3->data = 3;

 head1 = del(head , p2);
 print_1(head1);
}

 

 

思路二 :

首先我们要明确这个要删除的节点一定存在链表中,这个节点可以在链表头,中间,表尾三种情况。

对于在表尾 需要进行搜索到表尾,这个的时间复杂度为n, 

对于中间结点,需要知道它的前一个节点,需要搜索到它的前一个节点,时间复杂度为 小于n的,即O(1)

总的来说,时间复杂度为 O(1).

代码如下:

typedef struct LinkNode
{
 struct LinkNode *next;
 int data;
}node;


void print_1(node *head)
{
 node *p;
 p = head->next;
    while(p != NULL)
 {
  printf("%2d",p->data);
  p = p->next;
 }
}

node *del(node *head ,node *p)
{
 if(( head == NULL ) || ( p == NULL ))
 {
  return NULL;
 }

 if(p == head->next)
 {
  head->next = p->next;
  
 // delete p;
 // p = NULL;
 }

 else if(p->next != NULL) //中间结点
 {
        node *s;
  s = head->next;
  while( s->next != p )
  {
   s = s->next;
  }
  s->next = p->next;
 // delete p;
 // p = NULL;
 }

 if(p->next == NULL)
 {
  node *s;
  s = head->next;
  while(s->next != p)
  {
   s = s->next;
  }
  s->next = NULL; //把最后的节点职位空 
 }
 delete p;
 p = NULL;
 return head;
 
}
void main()
{
    node *head,*p0 ,*p1,*p2,*head1 ;
 head = (node*)malloc(sizeof(node));
 p0 = (node*)malloc(sizeof(node));
 p1 = (node*)malloc(sizeof(node));
 p2 = (node*)malloc(sizeof(node));
 node *p3 = (node*)malloc(sizeof(node));

 head->next = p0;
 p0->next = p1;
 p1->next = p2;
 p2->next= p3;
 p3->next = NULL;

 p0->data = 0;
 p1->data = 1;
 p2->data = 2; 
 p3->data = 3;

 head1 = del(head , p2);
 print_1(head1);
}

 

 思路三:知道了要删除的节点,我们删除这个节点的下一个节点,首先要记住这个节点的值,然后把这个节点的值给本该删除却没有删除的值。

前提是这个节点有下一个节点,如果是最后一个节点那么就应该采用遍历的方法遍历到最后要删除的节点。

时间复杂度为O(1)

直接定位到要删除的节点。

 

#include <iostream>using namespace std;typedef struct LinkNode{int data;struct LinkNode *next;}node;node *deletenode(node *head,node *delenode){   node *p ,*s;int tmp;if(delenode->next==NULL){p = head;{while(p->next){   s = p;   p = p->next;}cout<<"删除:"<<s->data<<endl;s->next=NULL;}}else{     p = delenode;       tmp = p->next->data;   cout<<"删除数据:"<<p->data<<endl;   p->next = p->next->next;   p->data = tmp;  }return head;}void main(){node *head,*p0,*p1,*p2,*p3;head = new node();p0 = new node();p1 = new node();p2 = new node();p3 = new node();p3->next= NULL;head->next=p0;p0->next=p1;p1->next= p2;p2->next=p3;p0->data = 1;p1->data = 2;p2->data = 3;p3->data =4;head = deletenode(head,p1); }


 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

原创粉丝点击