荼蘼== 发表于 2022-5-23 01:16:42

c语言解决从一开始的报数问题

有N个人围成一圈,顺序排号。

从第一个人开始报数,凡是报数中的尾数为3,或能被3整除,就退出圈子。

问最后留下的是原来第几号的人,最后报数报到多少?

比如:N=3,3个人,从第1号开始,从1开始报数

报数:1   2   3            4   5   6             7

编号:1   2   3(退出)1   2   1(退出)   2(只剩最后一个人)

最后报数最高是7,剩下的人编号是2



编写代码,要求:

1)用数组保存游戏参加人列表(最多不超过N)

      int LOOP;

2)数组取值为1或0,其中1代表参加报数,0代表被淘汰(1 TRUE / 0 FALSE)

3)键盘输入参加人数(人数<N)

4)编写函数处理游戏逻辑,输入指针(数组名)和参加人数(实际参加人数),输出报数最高值和最终胜利人编号

          int loops(int* p, int nums, int* top, int* id);

      p为输入指针,nums为输入人数,top为返回的最高值,id为返回的最终剩下的人编号

5)打印输出最高值和胜利者编号



其中:

1)函数内用 指针++操作遍历参加人

2)函数内用 指针赋值 操作完成从队尾到对头的循环

jhq999 发表于 2022-5-23 07:13:16

pnum Numoff(pnum head,int *n)
{
        pnum p=head->next,q=p;
        int i=1;
        while (p->next!=p)
        {
                if(i%3==0)
                {
                        q->next=p->next;
                        if (p==head->next)
                        {

                                head->next=q->next;
                       
                        }
                }
                q=p;
                p=p->next;
                i++;
        }
        *n=i;
        return head->next;
}
int main(void)
{
        int i=0,n=0;
        scanf("%d",&n);
        pnum num=(pnum)malloc(sizeof(NUMBER)*(n+1));
        for (i = 0; i < n; i++)
        {
                num.id=i;
                num.next=&num;
        }
        num.id=i,num.next=&num;
        Numoff(num,&n);
        printf("%d %d",n,num.next->id);
        return 0;
}

wp231957 发表于 2022-5-23 07:44:09

jhq999 发表于 2022-5-23 07:13


人家让用数组做,链表肯定好做些,数组的删除啊还是首尾链接啊都不咋好弄

jhq999 发表于 2022-5-23 09:06:22

本帖最后由 jhq999 于 2022-5-23 09:25 编辑

wp231957 发表于 2022-5-23 07:44
人家让用数组做,链表肯定好做些,数组的删除啊还是首尾链接啊都不咋好弄
最笨的扫描,

int loops(int* p, int nums, int* top, int* id)
{
        int i = 0,j=1,flag=nums;
        while (flag-1)
        {
                for (i = 0; i < nums; i++)
                {
                        if (p)
                        {
                                if (j%3==0)
                                {
                                        p=0;
                                        flag--;
                                        if (1==flag)break;
                                }
                                j++;
                        }
                }
                //if (1==flag)break;
        }
        for (i = 0; 0==p; i++);
        *id=1==nums?1:i+1;
        *top=1==nums?1:j+1;
        return i;
}
int main(void)
{
        int i=0,n=0,top=0,id=-1;
        scanf("%d",&n);
        int* num=(int*)malloc(sizeof(int)*n);
        for (i = 1; i <n; i++)
        {
                num=1;
               
        }
       
        loops(num,n,&top,&id);
        printf("%d %d",top ,id);
        return 0;
}
int loops(int* p, int nums, int* top, int* id)
{
        int i = 0,j=1,flag=nums;
        while (flag-1)
        {
                for (i = 0; i < nums&&(flag-1); i++)
                {
                        if (p)
                        {
                                if (j%3==0)
                                {
                                        p=0;
                                        flag--;
                                        //if (1==flag)break;
                                }
                                j++;
                        }
                }
                //if (1==flag)break;
        }
        for (i = 0; 0==p; i++);
        *id=i+1;
        *top=j;
        return i;
}

wp231957 发表于 2022-5-23 10:30:29

jhq999 发表于 2022-5-23 09:06
最笨的扫描,

我没用指针,也算笨笨的思想吧
int        printf (const char *__restrict, ...);
#define max 15

int main()
{
    int s={1,2,3,4,5,6,7,8,9,10,11,12,13,14,15};
    int num=1;
    int sum=0;
    int r=0;
    int n=0;
    while(1)
    {
      for(int x=0;x<max;x++)
      {
            if(num%3==0 && s)
            {
                s=0;
                num++;
            }
            if(num%3!=0 && s)
            {
                sum++;
                r=s;    //一旦sum==1这个rn就是我们要的结果
                n=num;
            }
            if(s) num++;
      }
      if (sum==1)
      {
            printf("结果剩下 :%4d 数数数到 %d\n",r,n);
            break;
      }
      sum=0;
    }
    return 0;
}

傻眼貓咪 发表于 2022-5-23 11:39:46

本帖最后由 傻眼貓咪 于 2022-5-23 11:41 编辑

完全以题目要求为条件的代码:#include <stdio.h>
#define N 20 // 设最高人数

// 编写函数处理游戏逻辑,输入指针(数组名)和参加人数(实际参加人数)
int loops(int* p, int nums, int* top, int* id) {
        if (nums < 1) return 0;
        *top = 0;
       
        // 函数内用 指针++操作遍历参加人
        // 函数内用 指针赋值 操作完成从队尾到对头的循环
        for (int *q = p, out = 0; out < nums - 1; ++q) {
                if (q == p + nums) {
                        q = p;
                }
                if (*q) {
                        (*top)++;
                        if ((*top) % 10 == 3 || !((*top) % 3)) {
                                (*q) = 0;
                                out++;
                        }
                }
        }
        for (int *q = p, i = 1; q < p + nums; ++q, ++i) {
                if (*q) {
                        (*id) = i;
                        (*top)++;
                }
        }
        return 1;
}

int main(void) {
        int
                n,
                LOOP = { 0 }, // 用数组保存游戏参加人列表(最多不超过N)
                top, id; // top为返回的最高值,id为返回的最终剩下的人编号
       
        // 键盘输入参加人数(人数<N)
        scanf("%d", &n);
       
        // 数组取值为 1 或 0,其中 1 代表参加报数,0 代表被淘汰(1 TRUE / 0 FALSE)
        for (int i = 0; i < n; ++i) LOOP = 1;
       
        loops(LOOP, n, &top, &id);
       
        // 输出报数最高值和最终胜利人编号
        printf("最高值: %d\n", top);
        printf("胜利者编号: %d", id);
        return 0;
}

荼蘼== 发表于 2022-5-23 15:39:01

傻眼貓咪 发表于 2022-5-23 11:39
完全以题目要求为条件的代码:

感谢大佬

荼蘼== 发表于 2022-5-23 15:39:41

jhq999 发表于 2022-5-23 07:13


谢谢谢谢
页: [1]
查看完整版本: c语言解决从一开始的报数问题