实验一:第五题循环链表的应用(约瑟夫回环问题)

n个数据元素构成一个环,从环中任意位置开始计数,计到m将该元素从表中取出,重复上述过程,直至表中只剩下一个元素。

提示:用一个无头结点的循环单链表来实现n个元素的存储。

参考代码:

#include<stdio.h>  //声明
#include<malloc.h>
#define ERROR 0
#define OK 1    //宏定义 oK 相当于 1
typedef  int ElemType; //定义表元素的类型
typedef struct LNode   //线性表的单链表存储
{
    ElemType data;       //数据元素data
    struct LNode *next;   //指向下一个节点的指针next
} LNode,*LinkList;      //定义单链表别名 Linklist

LinkList Creat(int t)   //创建长度为 t 的单向循环链表
{
    int n;    //整型变量
    LinkList p1,p2,head; 
    p1=(LinkList)malloc(sizeof(LNode));  //分配一个内存,大小是LNode的大小,
    p2=(LinkList)malloc(sizeof(LNode));  //并将这个内存地址转化为Link型,然后将赋给 p1,p2
    head = NULL;   //链表为空
    n = 1;   //从1开始
    while(n<=t)  // n<=t 循环
    {
        p1->data = n;  // n 赋值给p1所指向的数据元素data
        if(n==1)    //若 n 等于 1
            head = p1;  //p1 赋值给head
        else        //不等
            p2->next = p1;  //p1 赋值给p2所指向的next
        p2 = p1;  //p1 赋值给p2
        if(n!=t)  // 若 n 不等于 t
            p1 = (LinkList)malloc(sizeof(LNode)); //为p1重新分配一个是LNode大小的内存
        n++;  //自增
    }
    p2->next = head;   //将最后一个节点p2的指针指向头节点 head
    return head;    //返回头节点

}
LinkList Start(LinkList L,int k)  //start函数,用于找链表中第 K 个节点的位置
{
    int i;
    i=1;
    while(i!=k)
    {
        L=L->next;  //L 指向下一个节点赋值给 L 
        i++;        //自增,i+1
    }
    return L;  //返回该节点的指针

}
LinkList Delete(int n,int m,LinkList L)  //Delete函数用于删除每个 m 节点
{
    int i,j,k;
    LinkList p;
    p=L;
    k=0;
    while(n>1)
    {
        j=0;
        for(i=1+k; i<=n; i++)
        {
            if((i+1)%m==0)  //i+1对 m 取余
            {
                printf("%d ",p->next->data);  // 输出p的下一个的节点.
                p->next=p->next->next;   // 把 p的下一个的下一个赋给p的下一个.
                i++;
                j++;

            }
            p=p->next;  // p 的下一个指针赋值给 p
            k=i%m;      // i 对 m 取余赋值给 K
        }
        n=n-j;
    }
    printf("%d\n",p->data);  //输出被删除的节点数据
    return p;   //返回最后一个节点的指针
}
int main()
{
    int m,n,k;
    scanf("%d%d%d",&n,&m,&k); //从输入读入n,m,K三个整数
    LinkList L,cur;
    L=Creat(n);     //调用Creat 函数创建一个长度为 n 的单向循环链表
    cur=Start(L,k); //调用 Start 函数找到第 K 个节点的位置,赋值给 cur 传给Delete函数
    Delete(n,m,cur); //调用 Delete函数,进行链表节点的删除操作
    return 0;  //程序退出
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

努力的敲码工

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值