双链表_解决约瑟夫问题

#include<iostream>
using namespace std;

typedef int Node;

typedef struct DblNode
{
 Node data;
 DblNode *lLink,*rLink;

}DblNode;

class Dblist
{
 DblNode *first;
public:
//==========构造函数==================
 Dblist();
// ~Dblist();
//==========返回双链表长度============
 int Length() const;
//==========判断双链表空否============
 bool IsEmpty(){return first->rLink==first;}
//==========取附加头节点地址==========
 DblNode *getHead()const {return first;}
//==========设置附加头节点地址=========
 void setHead(DblNode *ptr){first=ptr;}
//==========在链表中沿后继方向寻找等于给定值X的节点
 DblNode *Search(const Node &x);
//==========在链表中定位序号为i(≥0)的节点,d=0按前驱方向,d≠0按后继方向
 DblNode *Locate(int i,int d);
//==========在第i个节点后插入一个包含有值x的新节点,d=0按前驱方向,d≠0按后继方向
 bool Insert(int i,const Node &x,int d);
//==========删除第i个节点,x返回其值,d=0按前驱方向,d≠0按后继方向
 bool Remove(int i,Node &x,int d);
//=========删除节点并返回其值=================
 int Remove(DblNode *x);
//=======返回所有结点的值====================
 void GetElement();
//=======返回下一结点====================
 DblNode *Next(DblNode* node){node=node->rLink; return node;}
 
};
//==========类的实现部分=================
Dblist::Dblist()
{
 first=new DblNode;
 if(first==NULL){cerr<<"存储分配出错!"<<endl;exit(1);}
 first->rLink=first->lLink=first;
}
/*Dblist::~Dblist()
{

}
*/
//==========返回双链表长度============
int Dblist::Length() const
{
 DblNode *current=first->rLink; int count=0;
 while(current!=first){current=current->rLink;count++;}
 return count;
}
//==========在链表中沿后继方向寻找等于给定值X的节点
DblNode * Dblist::Search(const Node &x)
{
 DblNode *current=first->rLink;
 while(current!=first && current->data !=x)
  current=current->rLink;
 if(current!=first)return current;
 else return NULL;
}
//==========在链表中定位序号为i(≥0)的节点,d=0按前驱方向,d≠0按后继方向
DblNode * Dblist::Locate(int i,int d)
{
 if(first->rLink==first || i==0)return first;
 DblNode *current;
 if(d==0) current=first->lLink;
 else current=first->rLink;
 for(int j=1;j<i;j++)
 {
  if(current==first)break;
  else if(d==0)current=current->lLink;
  else current=current->rLink; 
 }
 if(current !=first)return current;
 else return NULL;
}
//==========在第i个节点后插入一个包含有值x的新节点,d=0按前驱方向,d≠0按后继方向
bool Dblist::Insert(int i,const Node &x,int d)
{
 DblNode *current=Locate(i,d);
 if(current==NULL)return false;
 DblNode *newNode=new DblNode;
 newNode->data=x;
 newNode->lLink=NULL;
 newNode->rLink=NULL;
 if(newNode==NULL){cerr<<"存储分配失败!"<<endl;exit(1);}
 if(d==0)
 {
  newNode->lLink=current->lLink;
  current->lLink=newNode;
  newNode->lLink->rLink=newNode;
  newNode->rLink=current;
 }else
 {
  newNode->rLink=current->rLink;
  current->rLink=newNode;
  newNode->rLink->lLink=newNode;
  newNode->lLink=current;
 }
 return true;
}
//==========删除第i个节点,x返回其值,d=0按前驱方向,d≠0按后继方向
bool Dblist::Remove(int i,Node &x,int d)
{
 DblNode *current=Locate(i,d);
 if(current==NULL)return false;
 current->rLink->lLink=current->lLink;
 current->lLink->rLink=current->rLink;
 x=current->data;delete current;
 return true;
}
//==========删除节点x返回其值===============
int Dblist::Remove(DblNode *x)
{
 DblNode *p=x->rLink;
 p->rLink->lLink=p->lLink;
 p->lLink->rLink=p->rLink;
 int data=p->data;
 delete p;
 return data;
}
//=======返回所有结点==================
void Dblist::GetElement()

 DblNode *current=first->rLink;
 while(current->rLink!=first->rLink)
 {
  cout<<" "<<current->data ;
  current=current->rLink ;
 }
}
void main()
{
 Dblist mylink;
 cout<<"利用双向循环链表求解约瑟夫(Josephus)问题:"<<endl;
 int i,j,k,n,m,d;
 cout<<"输入人数 n:";cin>>n;
 cout<<"输入第次数 m:";cin>>m;
 cout<<"d=0按前驱方向,d≠0按后继方向:";cin>>d;

 for(i=0;i<n;i++)
 {
  mylink.Insert(i,i+1,d);
 }

 cout<<"员工编号依次为:";
 DblNode *node=mylink.Locate(1,d);
 mylink.GetElement();
 cout<<"删除次序依次为:\n";
 for(i=1;i<n;i++)
 {
  for(int j=0;j<m;j++)
  {
   node=mylink.Next(node);
   if(node==mylink.Locate(0,d)) node=mylink.Next(node);
  }
  if(node==mylink.Locate(0,d)->lLink) node=mylink.Next(node);
  cout<<"删除第"<<mylink.Remove(node)<<"人\n";
  
 }
 cout<<"最后剩下的是:编号为"<<mylink.Locate(1,d)->data<<"的员工。\n";  
}

posted on 2008-10-26 08:12  ....11  阅读(910)  评论(0编辑  收藏  举报

导航