前几天园子里有人发表关于8皇后的算法.只有代码,没有能运行的DEMO多枯燥.于是我这两天抽时间写了个N皇后的屏保程序.程序启动后会从4皇后到14皇后显示其所有排列,每隔0.5秒自动切换一次.按下空格键会停止自动切换,按-=键可以手动切换排列.算法是对网上找的程序做了点修改,先申请一块8M的内存区域,将N皇后中所有合适的位置保存到该内存中,代码如下:
1 static Ybyte g_listQueen[YD_MAX_STACKS_NUM] = {0}; 2 3 bool check_pos_valid(Ybyte loop, Ybyte value) 4 { 5 Ybyte index; 6 Ybyte data; 7 8 for(index = 0; index < loop; index ++) 9 { 10 data = g_listQueen[index]; 11 12 if(value == data) 13 return false; 14 15 if((index + data) == (loop + value)) 16 return false; 17 18 if((index - data) == (loop - value)) 19 return false; 20 } 21 22 return true; 23 } 24 25 void CNQueenEntitySP::CalculateQueen(Yuint index) 26 { 27 Ybyte loop; 28 29 for(loop = 0; loop < m_stacks; loop++) 30 { 31 if(check_pos_valid(index, loop)) 32 { 33 g_listQueen[index] = loop; 34 35 if(m_stacks - 1 == index) 36 { 37 //assert((m_resultsCount + 1)*m_stacks < YD_BUFFER_SIZE); 38 memcpy(m_resultBuffer + m_resultsCount*m_stacks, g_listQueen, m_stacks); 39 m_resultsCount++; 40 g_listQueen[index] = 0; 41 return; 42 } 43 44 CalculateQueen(index + 1); 45 g_listQueen[index] = 0; 46 } 47 } 48 }
算法使用的是递归,让人感觉有些费解,我也是看好好久才搞明白.其实N皇后问题可以写成一个N重循环,而为了解决N的不确定性,所以采用了递归算法.因此使用递归和使用N重循环其算法的复杂度是一样的.其算法运算量随着N数目的增加会爆增.生成14皇后的数据非常耗时,请耐心等待.再说递归,这样的代码多少都让人头疼,而实际应用中,我很少使用递归.印象中只有遍历文件夹时才用过,很早之前还写过一个无限递归的BUG导致堆栈爆掉,忘了是做什么应用了.再有就是上学时学算法,老师教的是所有的递归算法都可以改成循环,而考试的一个题目就是将某个递归算法改循环.其实反过来说,所有的循环也可以改成递归,我学过一个神一样的语言prolog,它里面貌似没有循环,所有的循环逻辑都是用递归实现的.写它的代码有种要疯的感觉.
对于8皇后算法,最早接触是上大学时开过一门课叫面向对象的程序设计,教材中有个DEMO是8皇后.后来这课的课程设计,大部分同学交的就是这个8皇后算法.我的也是,而且还是拷贝别人的.对这门课我目前也只有这点印象,因为当时我这课基本没怎么上,也根本不懂什么是面向对象.谁让这课的学分不高,考研不考呢.毕业后这本书也不见了,我现在很疑惑的是:8皇后问题和面向对象有什么关系呢?希望哪天能找到这书教材,看看这书写过什么.
"NQueenSP.scr"全屏可执行程序
"NQueen.exe"窗口可执行程序
鼠标左键右键拖动,调节视角.
鼠标滚轮,调节摄像机的远近.
X,恢复为默认视角并停止视角旋转.
空格,P,暂停与恢复.
ESC,退出.
R N皇后重新开始.
[ 减少皇后数.最小为4
] 增加皇后数.最多为14
- 上一个排列
= 下一个排列
下载地址:
http://files.cnblogs.com/WhyEngine/NQueenSP.zip
屏保设置方式
XP:
将目录下的所有文件拷贝到WINDOWS系统目录下如"C:WINDOWSsystem32"
WIN7,WIN8:
将目录下的所有文件拷贝到"C:WINDOWSSysWOW64"或"C:WINDOWSSysWOW32"目录下
在设置屏保的对话框中,选择"NQueenSP"