0001-算法笔记分治法实现棋盘覆盖问题

本文深入探讨了使用分治法解决L型骨牌填充问题的算法实现,通过递归的方式实现了除特殊方格外的所有方格填充,并提供了完整的C语言代码示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  今天上课老师讲了分治法,下课后自己把程序碼了一遍,还是存在一个疑问--为什么每个方格都会填充到,在下面将会解决并叙述。

        首先贴上程序:

#include <stdio.h>
#include <stdlib.h>
#include <memory.h>
int tile = 0;
int Board[100][100];

/*

    tr:棋盘左上角方格的行号

    tc:棋盘左上角方格的列号

    dr:特殊方格所在行号

    dt:特殊方格所在列号

*/
void chessBoard(int tr, int tc, int dr, int dc, int size);


int main()
{
    int size,r,c,row,col;
    memset(Board,0,sizeof(Board));
    scanf("%d",&size);
    scanf("%d%d",&row,&col);
    chessBoard(0,0,row,col,size);


    for (r = 0; r < size; r++)
    {
        for (c = 0; c < size; c++)
        {
            printf("%2d ",Board[r][c]);
        }
        printf("\n");
    }


    return 0;
}


void chessBoard(int tr, int tc, int dr, int dc, int size)
{
    int s,t;
    if (1 == size) return;


    s = size/2;               //分割棋盘 
    t = ++ tile;              //L型骨牌号

    //覆盖左上角子棋盘
    if (dr < tr + s && dc < tc +s)
    {
        //特殊方格在此棋盘中

chessBoard(tr,tc,dr,dc,s);
    }
    else
    {//此棋盘中无特殊方格

        //用t号L型骨牌覆盖右下角
        Board[tr+s-1][tc+s-1] = t;
       //覆盖其余方格

        chessBoard(tr,tc,tr+s-1,tc+s-1,s);
    }
    //覆盖右上角子棋盘
    if (dr < tr + s && dc >= tc + s )
    {

//特殊方格在此棋盘中
        chessBoard(tr,tc+s,dr,dc,s);
    }
    else
    {//此棋盘中无特殊方格

//用t号L型骨牌覆盖在左下角
        Board[tr+s-1][tc+s] = t;

        //覆盖其余方格
        chessBoard(tr,tc+s,tr+s-1,tc+s,s);
    }

 //覆盖左下角子棋盘
    if (dr >= tr + s && dc < tc + s)
    {
       //特殊方格在此棋盘中

 chessBoard(tr+s,tc,dr,dc,s);
    } 
    else
    {//此棋盘中无特殊方格

//用t号L型骨牌覆盖在左下角
        Board[tr+s][tc+s-1] = t;

 //覆盖其余方格
        chessBoard(tr+s,tc,tr+s,tc+s-1,s);
    }


    if (dr >= tr + s && dc >= tc + s)
    {
        chessBoard(tr+s,tc+s,dr,dc,s);
    } 
    else
    {
        Board[tr+s][tc+s] = t;
        chessBoard(tr+s,tc+s,tr+s,tc+s,s);
    }


}

实现结果如图示:



通过代码调试,我们可以看到,每次的填值都是将方格里的值填入,而不是只填特殊格的值。书中的这段代码在每次覆盖还有循环递归中也设计的很巧妙!和大家一起分享学习


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

精神抖擞王大鹏

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

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

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

打赏作者

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

抵扣说明:

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

余额充值