0
点赞
收藏
分享

微信扫一扫

n皇后问题,自然数拆分

minute_5 2022-01-09 阅读 145

- [P1219 [USACO1.5]八皇后 Checker Challenge](https://www.luogu.com.cn/problem/P1219)

我在这里想介绍一下如何用dfs解n皇后。

图片来自于:biibii懒猫老师

实现代码如下:

#include<stdio.h>
int place[15];//0表示没放,非0表示放了,并且表示放在第几列,下标表示行数
int flag[15],d1[30],d2[30];//d1为上对角线,d2为下对角线,0表示未被占据,非0表示已占据
int n,count,top;
void dfs(int row)
{
    if(row>n)//边界情况要>n,不是等于n
    {
        count++;
        if(count<=3)
        {
            for(int i=1;i<=n;i++)
            {
                printf("%d ",place[i]);
            }
            printf("\n");
        }
        return;
    }
    for(int i=1;i<=n;i++)//1至n列,尝试第row个皇后在第row行的不同可能
    {
        if(!flag[i]&&!d1[row-i+n]&&!d2[row+i])
        {
            place[row]=i;
            flag[i]=1;
            d1[row-i+n]=1;
            d2[row+i]=1;
            dfs(row+1);
            //回溯后取消标记
            flag[i]=0;
            d1[row-i+n]=0;
            d2[row+i]=0;
        }
    }
}
int main()
{
    scanf("%d",&n);
    dfs(1);
    printf("%d",count);
    return 0;
}

- [P2404 自然数的拆分问题](https://www.luogu.com.cn/problem/P2404)

这题我同样用dfs解。

所以代码如下:

#include<stdio.h>
int a[10];//存加数
void dfs(int number,int x)//number为第几个加数位置,x为剩下的数
{
   if(x==0&&number>2)
   {
       for(int i=1;i<number-1;i++)//特别注意此时是i<number-1,不是i<number
       printf("%d+",a[i]);
       printf("%d\n",a[number-1]);
       return;
   }
   for(int i=1;i<=x;i++)//处理节点情况,判断每个位置每个加数的可能性
   {
       if(i>=a[number-1])//此时a[0]=1发挥作用
       {
           a[number]=i;
           x-=i;
           dfs(number+1,x);
           //回溯
           a[number]=0;
           x+=i;
       }
   }
   return;
}
int main()
{
   int n=0;
   scanf("%d",&n);
   a[0]=1;
   dfs(1,n);
    return 0;
}
举报

相关推荐

0 条评论