博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
分治法之循环赛日程表
阅读量:5278 次
发布时间:2019-06-14

本文共 2647 字,大约阅读时间需要 8 分钟。

问题描写叙述:
            设有n(n = 2^k)位选手參加网球循环赛,循环赛共进行n-1天,每位选手要与
        其它n-1位选手比赛一场,且每位选手每天必须比赛一场,不能轮空。试按此要求
        为比赛安排日程。
    编程思想:
            如果n位选手被顺序编号为1,2,3,...,n,比赛的日程表是一个n行n-1列的表格,
        i行j列的表格内容是第i号选手在第j天的比赛对手。
            依据分而治之的原则,可从当中一半选手(2^(n-1位)的比赛日程,导出全体n位
        选手的日程,终于细分到仅仅有两位选手的比赛日程出发。
            可如果仅仅有8位选手參赛,若1至4号选手之间的比赛日程填在日程表的左上角
        (4行3列),5至8号选手之间的比赛日程填在日程表的左下角(4行3列);那么左下角的
        内容可由左上角的相应项加上数字4得到。至此,剩余的右上角(4行4列)是为编号小的
        1至4号选手与编号大的5至8号选手之间的比赛日程安排。比如,在第4天,让1至4号选
        手分别与5至8号选手比赛,以后各天,依次由前一天的日程安排,让5至8号选手“循环
        轮转”就可以。
        最后,比赛日程表的右下角的比赛日程表可由,右上角的相应项减去数字
        4得到。
    编程图例:
        
    ===================================================================
    |*| 选手    1天        2天        3天        4天        5天        6天        7天    |*|
    ===================================================================
    |*|    1号    |    2    |    3    |    4    ||    5    |    6    |    7    |    8    |*|
    |*|    2号    |    1    |    4    |    3    ||    6    |    7    |    8    |    7    |*|
    |*|    3号    |    4    |    1    |    2    ||    7    |    8    |    5    |    6    |*|
    |*|    4号    |    3    |    2    |    1    ||    8    |    5    |    6    |    5    |*|
    ========[左上角]========================[右上角]===================
    |*|    5号    |    6    |    7    |    8    ||    1    |    4    |    3    |    2    |*|
    |*|    6号    |    5    |    8    |    7    ||    2    |    1    |    4    |    3    |*|
    |*|    7号    |    8    |    5    |    6    ||    3    |    2    |    1    |    4    |*|
    |*|    8号    |    7    |    6    |    5    ||    4    |    3    |    2    |    1    |*|

    ========[左下角]========================[右下角]===================

#define    MAXN    64//日程表数组int    calendar[MAXN + 1][MAXN];void    Round_Robin_Calendar(){    int i,j,m,number,p,q;    printf("输入选手个数:(注意:2^k) ");    scanf("%d",&number);    //预置两位选手的比赛日程表://第i位选手第j天与第calendar[i][j]位选手比赛    calendar[1][1] = 2;        //第1位选手第1天与第2位选手比赛    calendar[2][1] = 1;        //第2位选手第1天与第1位选手比赛    m = 1;    p = 1;    while(m < number)    {        m ++;        //p = p + p;        p += p;        q = 2 * p;    //为2^m位选手安排比赛日程        //填充日程表的左下角        for(i = p + 1;i <= q;i++)            for(j = 1;j<= p - 1;j++)                calendar[i][j] = calendar[i - p][j] + p;    //左下角的内容 = 左上角的相应项加上数字4[]        //填充日程表的右上角        //填充日程表的右上角的第1列        calendar[1][p] = p + 1;                for(i = 2;i <= p;i++)            calendar[i][p] = calendar[i - 1][p] + 1;        //填充日程表的右上角的其它列,參照前一列填充当前列[循环轮转算法]        for(j = p + 1;j < q;j++)        {            for(i = 1;i < p;i++)                calendar[i][j] = calendar[i + 1][j - 1];            calendar[p][j] = calendar[1][j - 1];        }        //填充日程表的右下角        for(j = p;j < q;j++)            for(i = 1;i <= p;i++)                calendar[calendar[i][j]][j] = i;    //关键语句        for(i = 1;i <= q;i++)        {            for(j = 1;j < q;j++)                printf("%4d",calendar[i][j]);            printf(" ");        }        printf(" ");    }}//:====================“循环赛日程安排”问题的分而治之解决算法====================int main(int argc, char* argv[]){    Round_Robin_Calendar();    printf(" 应用程序执行结束! ");    return 0;}

转载于:https://www.cnblogs.com/blfshiye/p/4369001.html

你可能感兴趣的文章
多线程的通信方法
查看>>
Emgucv(一)Aforge切换摄像头并调用摄像头属性
查看>>
AutoCAD® Civil 3D API需求意愿调查
查看>>
Python的学习(二十一)----Python的静态变量
查看>>
Python中文件的读写操作的几种方法
查看>>
nltk
查看>>
argularJS学习笔记-增删改
查看>>
spring声明式事务 同一类内方法调用事务失效
查看>>
JUnit - 测试框架
查看>>
MySQL-数据类型及选择
查看>>
简单的注册表单
查看>>
caffe c++
查看>>
概率图模型课本笔记(五)
查看>>
数据库MySQL/mariadb知识点——存储过程及存储引擎
查看>>
决策树
查看>>
动态规划走楼梯问题
查看>>
mvc模型绑定问题
查看>>
评价现在的输入法
查看>>
美国行照片集之十二:一日两季
查看>>
素数回文(高效判断素数法)
查看>>