Josephus约瑟夫环问题循环链表实现

来源:互联网 发布:tvbj2港台网络电视直播 编辑:程序博客网 时间:2024/05/17 21:41

问题描述
已知n个人(以编号1,2,3…n分别表示)围坐在一张圆桌周围。从编号1开始报数,数到k的那个人出列;他的下一个人又从1开始报数,数到k的那个人又出列;依此规律重复下去,直到圆桌周围的人全部出列。
例如n=10,k=3时,输出的出列顺序是3,6,9,2,7,1,8,5,10,4。

程序代码
CLinkList.h

#include<iostream>using namespace std;#define MAXSIZE 100template<class T>struct Node{    T data;     //数据域    struct Node<T> *next;       //指针域,在这里<T>可省略};template<class T>class CLinkList{    public:        CLinkList(){rear = new Node<T>; rear->next = rear;} //无参构造函数        CLinkList(T a[],int n); //有参构造函数,使用含有n个元素的数组a初始化链表//      ~CLinkList();      //析构函数        void PrintList();   //按次序遍历链表中的各个数据元素        void Delete(int i);     //删除链表中第i个元素,并将该元素返回        void Josephus(int i);    private:        Node<T> *rear;      //尾指针        Node<T> *front;     //头指针        Node<T> *p;        int length;};template<class T>CLinkList<T>::CLinkList(T a[],int n){    front = new Node<T>;    Node<T> *r = front;    front->data = a[0];     //此构造函数中头结点也有数据,所以在出环的时候可以不用考虑头结点    length = n;    for(int i=1; i<n; i++)    {        Node<T> *s = new Node<T>;        s->data = a[i];        r->next = s;        r = s;    }    rear = r;    rear->next = front;}/*由于在josephus()函数中,已将所有元素删除,所以此处不需要析构函数template<class T>CLinkList<T>::~CLinkList(){    Node<T> *q = front;    while(q)    {        front = q;        q = q->next;        delete front;    }}*/template<class T>void CLinkList<T>::PrintList(){           Node<T> *x = front;         for(int i=0; i<length; i++)    {        cout<<" "<<x->data<<" ";        x = x->next;    }    cout<<endl;}template<class T>void CLinkList<T>::Delete(int i){    if(i == 0)   //如果出环间隔为0    {        Node<T> *q = p;        p = q->next;         cout<<q->data<<" ";        delete q;        length--;    }    else    //如果出环间隔不为0    {        for(int x=0; x<i-2; x++)    //计算出环位置        {               p=p->next;        }        Node<T> *q = p->next;        p->next = q->next;         p = p->next;        cout<<q->data<<" ";        delete q;        length--;    }}template<class T>void CLinkList<T>::Josephus(int i){    p = front;    while(length != 0)    {        Delete(i);    }}

Josephus.cpp

#include"CLinkList.h"int main(){    int n,k,a[MAXSIZE];    cout<<"请输入总数n:"<<endl;    cin>>n;    cout<<"请输入出环间隔k:"<<endl;    cin>>k;    for(int i=0; i<n; i++)    {        a[i]=i+1;    }    CLinkList<int> josephus(a,n);//  josephus.PrintList();    josephus.Josephus(k);    return 0;}

输出结果
请输入总数n:
20
请输入出环间隔k:
3
3 6 9 12 15 18 1 5 10 14 19 4 11 17 7 16 8 2 13 20
请按 ENTER 或其它命令继续

0 0
原创粉丝点击