问题描述:

a和b为指针,则a异或b的运算结果仍为原指针类型,且

异或(a异或b)=(a异或a)异或b=b;

异或b)异或b=a异或(a异或b)=a;

即可利用一个指针域来实现双向链表L。链表L中的每个结点只含两个域:data域和LRPtr域,其中LRPtr域存放该节点的左邻与右邻结点指针(不存在是为null)的异或。若设指针L.Left指向链表中的最左结点,L.Right指向链表中的最右结点,则可实现从左向右或从右向左遍历此双向链表的操作。试写一算法按任一方向依次输出链表中的各元素的值。

 

问题分析:感觉有点回到高中时期,哪个时候,没做过的题,第一次看到都看不懂题目要问的意思,不知道它要我干什么,这是很槽糕的,通常在这样的情况下,也只有先看下答案,然后慢慢再理解一下题目的意思,这样弄懂了以后,下次碰到这样的题也就有了思路,现在又何尝不是这样呢?要弄懂是要花功夫的,过去的大学,你是怎么上的,你怎么能没有这些努力,好吧,回到正题,再想想,看书上已经给了一些提示了:

异或指针双向链表类型和指针异或函数定义为:

Typedef struct XorNode{
Char data;
Struct XorNode LRPtr;
}XorNode,*XorPointer;
 
Typedef struct {//无头结点的异或指针双向链表
XorPointer  Left, Right;//分别指向链表的左端和右端
} XorLinkedList;
 
XorPointer XorP(XorPointer  p,XorPointer  q);//指针异或函数XorP返回指针p和q的异或的值
Status TraversingLinkList(XorLinkedList &L,char d)
{
   XorPointer p,left,right;
   If(d==’l’||d==’L’)
   {
      P=L.left;
      Left=null;
      While(p!=null)
      {
         VisitingData(p->data);
          Left=p;
          P=XorP(left,p->LRPtr);
       }
   }
  Else
     If(d==’R’||d==’r’)
      {
         P=L.right;
         Right=null;
         While(p!=null)
         {
           VisitingData(p->data);
           Right=p;
           P=XorP(p->LRPtr, Right);
         }
      }
}

接着采用上述的存储结构,写出在第i个结点之前插入一个结点的算法,和删除第i个结点的算法。

,改装下

 

先定位:

返回的应该是地址,用指针保存,再这里函数返回的是指针类型的该怎样表示了,

暂且按我的理解来吧

Char *  GetElemP_Dul(XorLinkedList &L,int i)
{
  Char *p;
  P=L->next;j=1;
  While(p&&j<i)
  {
   P=p->next;
   ++j;
  }
 If(!p||j>i)  return error;
Return p;
}

插入的算法:

Status ListInsert_Dul(XorLinkedList &L,int i,char d)
{
 If(!(p=GetElemP_Dul(L,i)))
 Return error;
 If(!(s=(XorLinkedList)malloc(sizeof(XorNode)) ))  return error;
 S->data=d;
 S->prior=p->prior; p->prior->next=s;
 S->next=p;p->prior=s;
 Return ok;
}

删除的算法:

Status ListDelete_Dul(XorLinkedList &L,int i)
{
  If(!(p=GetElemP_Dul(L,i)))
   Return error;
  p->prior->next=p->next;
  P->next->prior=p->prior;
  Free(p);
  Return ok;
}


作者:wj704