前两天没怎么做,卡在这道题上了,很是郁闷,觉得连这些基础的题都做不了。
后来觉得看看别人的做法,在网上看到了这位同学的博客:http://blog.sina.com.cn/s/blog_606e17490100f4n8.html
代码的思路比较清晰,比较容易看懂。
但是其中有一个问题我想了很长时间,就是为什么深度将16次作为上限。
后来在别人的帮助下终于想通了:
一共就16个格子 按17次的话 肯定有一个两次
一个格子在变换过程中按两次 相当于没按 没有意义
所以将16作为上限值。
==========================================华丽的分割============================================
2013-6-7
自己很久没有写算法的题目了。没有思路。参考了别人的总结。上面的代码简洁明了。
bsp的递归实现写的很棒,想起来数据结构老师曾经说过一句话: 要大胆地写递归。
这个题目,我联想到了人工智能中的产生式系统。
产生式系统的组成我还记得。
1)综合数据库
2)产生式规则集
3)控制策略
想来,大体框架就是:
DATA <---- 初始状态描述
until DATA 满足终止条件 , do;
begin
在规则集合中,选一条可用于DATA的规则R
DATA <----- R应用到DATA的结果
end
其中如何选取规则,就是控制策略的工作了。
根据上面的代码, 修改后AC:
Source Code Problem: 1753 User: huntinux Memory: 132K Time: 47MS Language: C Result: Accepted Source Code #include <stdio.h> // 代表16条翻转规则。翻转用亦或操作实现。 unsigned short int flips[16]={0xc800,0xe400,0x7200,0x3100,0x8c80,0x4e40,0x2720,0x1310,0x08c8,0x04e4,0x0272,0x0131,0x008c,0x004e,0x0027,0x0013}; int min = 16 + 1; void bsp(unsigned short int number, int index, int flip) { if(number == 0x0000 || number == 0xffff){ min = (min > flip ? flip : min); // 记录最小的层数 return ; } if(index >= 16) return; bsp(number, index + 1, flip); // 同层 bsp(number ^ flips[index], index + 1, flip + 1); //下一层 , 体现了宽度优先搜索 } void get_number(unsigned short int *number) { int i; char ch; for(i = 0; i < 16; i++){ scanf("%c", &ch); if('b' == ch) *number += (1 << (15 - i)); else if('\n' == ch) i--; // 去掉多余的回车的影响 } } int main() { unsigned short int number = 0; get_number(&number); bsp(number, 0, 0); if(min <= 16) printf("%d\n", min); else printf("Impossible\n"); return 0; }