首页 > 编程语言 >栈和队列的应用 ——球钟算法

栈和队列的应用 ——球钟算法

时间:2024-12-07 15:29:44浏览次数:5  
标签:qu hour 指示器 min 队列 st 算法 球钟 个球

栈和队列的应用 ——球钟算法

1.球钟背景
球钟是一个利用球的移动来记录时间的简单装置
它有三个可以容纳若干个球的指示器:分钟指示器,五分钟指示器,小时指示器
若分钟指示器中有两个球,五分钟指示器有六个球,小时指示器有五个球,那就代表时间是5:32
2. 工作原理
每过一分钟球钟就会从球队列的队首取出一个球放入分钟指示器,分钟指示器最多可容纳4个球。
当放入第五个球时,在分钟指示器的4个球就会照他们被放入时的相反顺序出栈并加入球队列的队尾。
而第五个球就会进入五分钟指示器。按此类推,五分钟指示器最多可放11个球,小时指示器最多可放11个球。
当小时指示器放入第12个球时,原来的11个球按照他们被放入时的相反顺序加入球队列的队尾,然后第12个球也回到队尾。这时,三个指示器均为空,回到初始状态,从而形成一个循环。
因此,该球钟表示的时间范围是从00:00到11:59。(12小时制)
3. 问题:
假设有1-27个升序排列的球钟在球队列中,球钟的三个指示器初态均为空。求经过多长时间,球队列的排序再次回到1-27的升序顺序?
4. 代码实现
使用顺序栈和顺序队列实现,整体流程如下
在这里插入图片描述

#include<stdio.h>
#include<stdlib.h>
#include "../test8-stack/sqstack.h"
#include "../test10_squeue/queue.h"
//球钟算法:三个栈,一个队列,12小时制,27个球,求什么时候球的顺序排列再为1~27
//包含其他头文件,注意要改下前面定义相同的变量,如MAXSIZE,struct 
#define NR_BALL 27 //定义27个球
static int check(queue *qu)
{
    //循环队列,i为第一个值指向head的下一个数据(head不放数据)
    int i=(qu->head+1)%MAXSIZE;
    while (i!=qu->tail)
    {
        //若队列为1~27的顺序,则每个数小于后一个数
        if(qu->data[i]>qu->data[(i+1)%MAXSIZE])
          return 0;
        i=(i+1)%MAXSIZE;
    }
    return 1;
}
int main()
{
    queue *qu;//存放球
    int t,time=0,value=0,hour;//t存放出队的球,time存放时间
    sqstack *st_min,*st_fivemin,*st_hour;//三个时间栈
    qu=qu_create();
    if(qu==NULL) return -1;
    st_min=st_create();
    if(st_min==NULL) return -1;
    st_fivemin=st_create();
    if(st_fivemin==NULL) return -1;
    st_hour=st_create();
    if(st_hour==NULL) return -1;
    //球入队
    for(int i=1;i<=NR_BALL;i++)
      qu_enqueue(qu,&i);
    while (1)
    {
        //球出队
        qu_dequeue(qu,&t);
        time++;//时间自增
        //1min栈球数不到4,直接入栈 top从0开始入栈 0,1,2,3(最多放四个1min的球)
        if(st_min->top!=3)
        {
            st_push(st_min,&t);
        }
        else
        {
            //1min的球栈满了,要全部出栈清空
            while (!st_isempty(st_min))
            {
                st_pop(st_min,&value);
                //出栈后的球重新入在原来队列的后面
                qu_enqueue(qu,&value);
            }
            //1min的球栈清空后,如果5min的栈未满,出队的球要入5min的球栈,否则5min的球栈要出栈进入1hou栈
            if(st_fivemin->top!=10)
              st_push(st_fivemin,&t);//5min球栈满为11个球,top从0开始,满表示10
            else
            {
                //5min球栈满,要出栈入队
                while (!st_isempty(st_fivemin))
                {
                    st_pop(st_fivemin,&value);
                    qu_enqueue(qu,&value);
                }
                //如1hour栈,11个球表示栈满(12小时制)
                if(st_hour->top!=10)
                   st_push(st_hour,&t);
                else
                {
                    //1hour球栈满,出栈,球入队
                    while (!st_isempty(st_hour))
                    {
                        st_pop(st_hour,&value);
                        qu_enqueue(qu,&value);
                    }
                    //此时栈全部清空,最后一个球也进入原来的对列中,这时才可能会有球的重新排序为1~27的情况
                    qu_enqueue(qu,&t);
                    check(qu);//检测队列情况
                    //队列为所求,退出循环
                    if(check(qu))
                     break;
                }
                
            } 
        }
    }
    printf("The order of the balls is:\n");
    qu_travel(qu);
    hour=time/60;//计算时间
    time=time%60;//计算分钟
    printf("time:%d hour %d min after success!\n",hour,time);
    qu_destroy(qu);
    st_destroy(st_min);
    st_destroy(st_fivemin);
    st_destroy(st_hour);
    return 0;
}
//gcc.exe .\bowlTime.c ..\test8-stack\sqstack.c ..\test10_squeue\queue.c -o main.exe

标签:qu,hour,指示器,min,队列,st,算法,球钟,个球
From: https://blog.csdn.net/m0_55967108/article/details/144307800

相关文章

  • [学习笔记 #8] Manacher 算法
    目录[学习笔记#8]Manacher算法[学习笔记#8]Manacher算法至今都不会exKMP/dk/dk/dk[]里的是我还不确定的。Manacher是对序列上每个点求它作为[回文中心]的最长回文子串长度/端点的算法,时间复杂度是\(O(|S|)\)。具体地,从左往右加入每个点,记录当前字符串的回......
  • 【C++算法】31.前缀和_连续数组
    文章目录题目链接:题目描述:解法C++算法代码:图解题目链接:525.连续数组题目描述:解法前缀和思想:如果把0变成-1,那么就是在区间内找一个最长的子数组,使得子数组中所有元素的和为0前面做过一个前缀和为k的子数组,这里就是转化为和为0。前缀和+哈希表哈希表里......
  • 【C++算法】32.前缀和_矩阵区域和
    文章目录题目链接:题目描述:解法C++算法代码:题目链接:1314.矩阵区域和题目描述:解法防止有人看不明白题目,先解释一下题目二维前缀和思想:使用前缀和矩阵ret=[x1,y1]~[x2,y2]=D=(A+B+C+D)-(A+B)-(A+C)+A=dp[x2,y2]-dp[x1-1,y2]-dp[x2,y1-1]+dp[x......
  • 基于机器学习算法的糖尿病风险预测可视化分析
    背景:根据世界卫生组织的数据,全球糖尿病发病率逐年上升。在中国,糖尿病的发病率也呈上升趋势,对人们的生活质量造成严重影响。机器学习算法在糖尿病风险预测方面具有巨大潜力。目的:通过机器学习算法分析糖尿病患者的特征,预测糖尿病风险,并进行可视化分析。内容:数据收集:收集......
  • 深入解析图神经网络:Graph Transformer的算法基础与工程实践
    GraphTransformer是一种将Transformer架构应用于图结构数据的特殊神经网络模型。该模型通过融合图神经网络(GNNs)的基本原理与Transformer的自注意力机制,实现了对图中节点间关系信息的处理与长程依赖关系的有效捕获。GraphTransformer的技术优势在处理图结构数据任务时,Graph......
  • 补码一位算法(booth算法)
    方法初始化将被乘数A放在寄存器A中。将乘数B放在寄存器B中,并在最低位添加一个额外的位Q(-1)=0。结果寄存器P初始化为0,长度为2n位。迭代过程(重复n次)对于i从0到n-1:检查乘数B的最后两位(Bi和Q(-1)):如果BiQ(-1)=01,则P=P+A,然后右移一位(ARShift)。如果B......
  • 每日一道算法题之最大人工岛
    importjava.util.HashMap;importjava.util.HashSet;classSolution{publicintlargestIsland(int[][]grid){//思路:遇到1,渲染,cnt++.然后统计每个岛屿的大小。//遍历。遇到0,看上下左右分别是哪些独立的岛屿。加起来。intans=0;......
  • 基于WOA鲸鱼优化的购售电收益与风险评估算法matlab仿真
    1.课题概述      基于WOA鲸鱼优化的购售电收益与风险评估算法.WOA优化算法是一种基于鲸鱼捕食过程的仿生优化算法,其包括鲸鱼行走觅食、鲸鱼包围以及鲸鱼螺旋捕食三个步骤。在WOA优化算法中,将售电公司的购售电收益风险计算公式作为WOA优化算法的目标函数,然后通过WOA的迭代......
  • 【机器学习】从入门到实战:深入解析 K 最近邻(KNN)算法在手写数字分类中的应用
    从入门到实战:深入解析K最近邻(KNN)算法在手写数字分类中的应用K最近邻(K-NearestNeighbors,KNN)算法基本原理特点总结实战基于KNN对手写数字进行分类超参数调节模型训练与测试性能评估与混淆矩阵绘制完整代码训练代码测试代码不同度量方法比较总结K最近邻(K-Nearest......
  • 基于Huffman编码的GPS定位数据无损压缩算法
    目录一、引言二、霍夫曼编码三、经典Huffman编码四、适应性Huffman编码五、GPS定位数据压缩提示:文末附定位数据压缩工具和源码一、引言        车载监控系统中,车载终端需要获取GPS信号(经度、纬度、速度、方向等)实时上传至监控中心,监控中心按通信协议将收......