一看题目 经典的8皇后问题 不过是皇后数量可变而已 不用想 回溯法。 需要个生成每次可选择序列的函数, 在存储可选择的序列时按照先大后小的顺序排的。这样每次找最小和去掉最小都很方便,只要有个记录数量的变量 每次减1就好了。  写完后,居然悲剧了。 在皇后数量达到13时, 在自己电脑上跑 内存溢出了 在评分系统上超时了。需要优化。

#include <stdio.h>
//k计算第几层从0开始 x已经摆好的位置 S存放产生的位置 l存放产生的数量 N一共有多少位置可以选择
int calculate(int k, int * x, int *S, int * l, int N)
{
int i, j;
int flag;
*l = ;
for(i = N; i >= ; i--) //大数在前面
{
flag = ;
for(j = ; j <= k - ; j++)
{
if(i == x[j] || i - x[j] == k - j || x[j] - i == k - j )
{
flag = ;
}
}
if(flag == )
{
S[*l] = i;
(*l)++;
}
}
return ;
} int BackTrack(int N, int (*ans)[], int * anum)
{
*anum = ;
int i, j, k;
int x[];
int S[][] = {};
int l[] = {};
for(i = N - ; i >= ; i--) //大数放前面
{
S[][i] = N - i;
}
l[] = N;
k = ;
do{
while(l[k] != )
{
x[k] = S[k][l[k] - ]; //取最小的
l[k]--;
if(k < N - )
{
k++;
calculate(k, x, S[k], &l[k], N);
}
else
{
for(i = ; i < N; i++)
{
ans[*anum][i] = x[i];
}
(*anum)++;
}
}
k--;
}while(k != -);
return ;
} int main()
{
FILE *in, *out;
in = fopen("checker.in", "r");
out = fopen("checker.out", "w"); int N;
int ans[][];
int anum;
fscanf(in, "%d", &N);
BackTrack(N, ans, &anum); int i, j;
for(i = ; i <= ; i++)
{
for(j = ; j < N - ; j++)
{
fprintf(out, "%d ", ans[i][j]);
}
fprintf(out, "%d\n", ans[i][N - ]);
}
fprintf(out, "%d\n", anum);
return ;
}

-------------------------------------

优化了一下计算新一层可能产生的数的算法 把calculate中嵌套的两个循环分开了(通过少量内存的代价)通过了测试 很开心啊~

#include <stdio.h>
#include <stdlib.h>
//k计算第几层从0开始 x已经摆好的位置 S存放产生的位置 l存放产生的数量 N一共有多少位置可以选择
int calculate(int k, int * x, int *S, int * l, int N)
{
int i, j;
int flag;
*l = ;
int cannot[] = {}; //分开两个循环的关键 用变量记录下不可用的数字
for(j = ; j <= k - ; j++)
{
cannot[x[j] - ] = ; //不能同一列
if(x[j] + k - j - <= N - ) //不能对角线 不能越界
{
cannot[x[j] + k - j - ] = ;
}
if(x[j] - k + j - >= )
{
cannot[x[j] - k + j - ] = ;
}
}
for(i = N; i >= ; i--) //大数在前面
{
if(cannot[i - ] == )
{
S[*l] = i;
(*l)++;
}
}
return ;
} int BackTrack(int N, int **ans, int * anum)
{
*anum = ;
int i, j, k;
int x[];
int S[][] = {};
int l[] = {};
for(i = N - ; i >= ; i--) //大数放前面
{
S[][i] = N - i;
}
l[] = N;
k = ;
do{
while(l[k] != )
{
x[k] = S[k][l[k] - ]; //取最小的
l[k]--;
if(k < N - )
{
k++;
calculate(k, x, S[k], &l[k], N);
}
else
{
for(i = ; i < N; i++)
{
ans[*anum][i] = x[i];
}
(*anum)++;
}
}
k--;
}while(k != -);
return ;
} int main()
{
FILE *in, *out;
in = fopen("checker.in", "r");
out = fopen("checker.out", "w"); int N;
int ** ans;
int i, j;
ans = (int **)malloc( * sizeof(int *)); //大内存要自己分配
for(i = ; i < ; i++)
{
ans[i] = (int *)malloc( * sizeof(int));
}
int anum;
fscanf(in, "%d", &N);
BackTrack(N, ans, &anum); for(i = ; i <= ; i++)
{
for(j = ; j < N - ; j++)
{
fprintf(out, "%d ", ans[i][j]);
}
fprintf(out, "%d\n", ans[i][N - ]);
}
fprintf(out, "%d\n", anum);
return ;
}

【USACO】checker的更多相关文章

  1. POJ 1986 Distance Queries / UESTC 256 Distance Queries / CJOJ 1129 【USACO】距离咨询(最近公共祖先)

    POJ 1986 Distance Queries / UESTC 256 Distance Queries / CJOJ 1129 [USACO]距离咨询(最近公共祖先) Description F ...

  2. 1642: 【USACO】Payback(还债)

    1642: [USACO]Payback(还债) 时间限制: 1 Sec 内存限制: 64 MB 提交: 190 解决: 95 [提交] [状态] [讨论版] [命题人:外部导入] 题目描述 &quo ...

  3. 1519: 【USACO】超级书架

    1519: [USACO]超级书架 时间限制: 1 Sec 内存限制: 64 MB 提交: 1735 解决: 891 [提交] [状态] [讨论版] [命题人:外部导入] 题目描述 Farmer Jo ...

  4. Java实现【USACO】1.1.2 贪婪的礼物送礼者 Greedy Gift Givers

    [USACO]1.1.2 贪婪的礼物送礼者 Greedy Gift Givers 题目描述 对于一群要互送礼物的朋友,你要确定每个人送出的礼物比收到的多多少(and vice versa for th ...

  5. 【CPLUSOJ】【USACO】【差分约束】排队(layout)

    [题目描述] Robin喜欢将他的奶牛们排成一队.假设他有N头奶牛,编号为1至N.这些奶牛按照编号大小排列,并且由于它们都很想早点吃饭,于是就很可能出现多头奶牛挤在同一位置的情况(也就是说,如果我们认 ...

  6. 【USACO】Dining

    [题目链接] [JZXX]点击打开链接 [caioj]点击打开链接 [算法] 拆点+网络流 [代码] #include<bits/stdc++.h> using namespace std ...

  7. 【USACO】Optimal Milking

    题目链接 :        [POJ]点击打开链接        [caioj]点击打开链接 算法 : 1:跑一遍弗洛伊德,求出点与点之间的最短路径 2:二分答案,二分”最大值最小“ 3.1:建边,将 ...

  8. 【USACO】 Balanced Photo

    [题目链接] 点击打开链接 [算法] 树状数组 [代码] #include<bits/stdc++.h> using namespace std; int i,N,ans,l1,l2; ] ...

  9. 【USACO】 Balanced Lineup

    [题目链接] 点击打开链接 [算法] 这是一道经典的最值查询(RMQ)问题. 我们首先想到线段树.但有没有更快的方法呢?对于这类问题,我们可以用ST表(稀疏表)算法求解. 稀疏表算法.其实也是一种动态 ...

随机推荐

  1. 洛谷P2279 [HNOI2003]消防局的设立

    题目描述 2020年,人类在火星上建立了一个庞大的基地群,总共有n个基地.起初为了节约材料,人类只修建了n-1条道路来连接这些基地,并且每两个基地都能够通过道路到达,所以所有的基地形成了一个巨大的树状 ...

  2. 全排列(java版)

    适用于不同数字的全排列,其实也适用于有重复数字的全排列,只不过的出来的结果有重复,需手动删减掉重复的组合. package testFullPermutation; import java.util. ...

  3. i++和++i

    这个问题总是讨论,有时又被弄晕了,特来复习一下 ; ; cout<<s<<endl; cout<<5,而i+++4返回4,其实这样的i++先运算,再加,++i先加再 ...

  4. hdu 1201 18岁生日

    #include <stdio.h> int r(int y) { return (y%4==0&&y%100!=0)||(y%400==0); } int f(int y ...

  5. C语言之参数传递

    学了四年的计算机,一直让自己比较苦恼的问题是C语言的参数传递问题,之所以说是苦恼,是因为在某年的一个学期,不幸接触到数据结构,光一个链表就把自己弄得死去活来的,而且自已一直就楞以为在操作的过程中,传递 ...

  6. (7)UI(基础对象)

    1.地图控件:   地图控件可支持导入Tiled地图编辑器导出的tmx格式文件,地图是制作游戏关卡地形图的控件,对于即时战略类型游戏的制作,为了使玩家流畅的切换游戏画面,经常会使用超过屏幕尺寸的地图. ...

  7. Third scrum meeting - 2015/10/28

    在一天的工作中明显发现到,无法和网站开发团队进行交流会严重导致我们的进程拖延,所以我们在现有的情况下也把大家的goal初步完成了,我们也对代码规范进行了详细的讨论,以及UI的设计完成,所以整个团队都真 ...

  8. basic use of sidekiq

    参考页面 https://github.com/mperham/sidekiq https://github.com/mperham/sidekiq/wiki/Getting-Started 强烈推荐 ...

  9. Procrustes Analysis普氏分析法

    选取N幅同类目标物体的二维图像,并用上一篇博文的方法标注轮廓点,这样就得到训练样本集: 由于图像中目标物体的形状和位置存在较大偏差,因此所得到的数据并不具有仿射不变性,需要对其进行归一化处理.这里采用 ...

  10. Nmap备忘单:从探索到漏洞利用(Part3)

    众所周知NMAP是经常用来进行端口发现.端口识别.除此之外我们还可以通过NMAP的NSE脚本做很多事情,比如邮件指纹识别,检索WHOIS记录,使用UDP服务等. 发现地理位置 Gorjan Petro ...