《编程之美》读书笔记:中国象棋将帅问题

找出将和帅所有可能的局面,要求用一个字节的变量来存储数据。

我最初分析这道题,想可以枚举将的位置,那么一共有9个,再写出帅的位置就行,由于将帅不能照面,所以此时帅只有6个位置。答案必定有9*6=54个。只是判断照面的地方会比较麻烦。

由于只有一个字节的变量限制和以前做题经验,使我一度想歪以为要用二进制的位来表示将的位置。但是这样的话,一个字节只有8位,而将可有9个位置,显然不行。

当然,不应这样做,也没有必要这样。

后来想到另一种思路,可以把将和帅的位置同时压缩到一个十进制数字N里面,这样N=a*9+b,a和b分别是将和帅的位置编号。

位置如图:

这样取N从0到80,即取遍了a和b所有可能的位置(包括照面的情况)。所以问题就变成了去掉照面的情况。

看图,什么时候a和b照面呢?明显是a和b位于同一列的时候,这样只需要判断a/3是否等于b/3即可。

#include<iostream>
#include<cstdio>
using namespace std;
int main()
{
    for(int i=0; i<81; ++i)
    {
        if(i/9/3!=i%9/3)
        {
            cout<<i/9<<" "<<i%9<<endl;
        }
    }
    return 0;
}

《编程之美》读书笔记:中国象棋将帅问题,布布扣,bubuko.com

时间: 2024-12-24 12:08:13

《编程之美》读书笔记:中国象棋将帅问题的相关文章

《编程之美》之中国象棋将帅问题

一个将,一个帅,在各自的活动的9个格子里,但是两个人不能面对面,站在同一条直线上 下面两种简单的解法 #include <stdio.h> int main() { unsigned char i = 81; while (i--) { if (i / 9 % 3 == i % 9 % 3) continue; printf("a:%d,b:%d\n", i / 9, i % 9); } struct { unsigned char a:4; unsigned char b

编程之美——1.2中国象棋将帅问题

#include<iostream> using namespace std; //设置一些计算的宏 typedef char bytes; #define BYTES_LENGTH 255//一个字节的数据大小 #define BYTES_HALF_LENGTH 4//半个字节的位数 //#define RHALF (BYTES_LENGTH>>BYTES_HALF_LENGTH)//右半边为00001111 #define RHALF 15 //#define LHALF (B

《编程之美-读书笔记》-1 中国象棋将帅问题

时间:2014.05.27 地点:基地 ---------------------------------------------------------------------------------------- 一.指针和引用的区别 1.指针可以为空,引用不可以不空. 引用是一个对象的别用,定义一个引用时必须初始化,而声名指针时可以不指向任何对象,故使用指针时也常要做空的判断,而引用无需,因为引用总是绑定着一个对象. 2.指针可以改变指向,而引用不可以重新绑定新对象.(指针变异思迁,引用从

编程之美读书笔记1.2——中国象棋将帅问题

http://blog.csdn.net/pipisorry/article/details/36380669 问题:下过中国象棋的朋友都知道,双方的"将"和"帅"相隔遥远,并且它们不能照面.在象棋残局中,许多高手能利用这一规则走出精妙的杀招.假设棋盘上只有"将"和"帅"二子(如图1-3所示)(为了下面叙述方便,我们约定用A表示"将",B表示"帅"): A.B二子被限制在己方3×3的格子

编程之美读书笔记1.8 - 小飞的电梯调度算法

http://blog.csdn.net/pipisorry/article/details/36688019 问题: 亚洲微软研究院所在的希格玛大厦一共有6部电梯.在高峰时间,每层都有人上下,电梯每层都停.实习生小飞常常会被每层都停的电梯弄的很不耐烦,于是他提出了这样一个办法: 由于楼层并不算太高,那么在繁忙的上下班时间,每次电梯从一层往上走时,我们只允许电梯停在其中的某一层.所有乘客从一楼上电梯,到达某层后,电梯停下来,所有乘客再从这里爬楼梯到自己的目的层.在一楼的时候,每个乘客选择自己的目

编程之美读书笔记2.15 - 子数组之和的最大值(二维)

http://blog.csdn.net/pipisorry/article/details/39083073 问题: 求二维数组(矩阵)的子矩阵之和的最大值. 亦可见:http://poj.org/problem?id=1050 解法1:(解释见注释) 每个子矩阵由列长.行长和左上角的元素位置决定.如果我们指定左上角的元素位置 (i,j) 和列长 c,那么可以求所有这些子矩阵中和最大的.然后,变化列长 c,可以求以 (i,j) 为左上角的最大和子矩阵.最所有左上角位置再求最大和子矩阵,问题就解

编程之美读书笔记1.1——让CPU占用率曲线听你的指挥

http://blog.csdn.net/pipisorry/article/details/36189155 <strong><span style="font-size:48px;color:#ff0000;">问题:</span></strong>写一个程序,让用户来决定Windows任务管理器(Task Manager)的CPU占用率. 假设机器是多CPU,上面的程序会出现什么结果?怎样在多个CPU时显示相同的状态?比如.在双核的

编程之美读书笔记2.14 - 子数组之和的最大值

http://blog.csdn.net/pipisorry/article/details/39083281 问题: 1. 一个由N个整数元素的一维数组,求其所有子数组中元素和的最大值. 2. 如果数组首尾相邻,也就是允许子数组A[i],...,A[n-1],A[0],...,A[j]存在,求其所有子数组总元素和的最大值. 解法1: /* O(n^2) 遍历算法 */ static int maxSubarraySum1(int *a,int a_len){ int max_sum = INT

编程之美1.2 | 中国象棋将帅问题

后面两种写法很巧妙.一种利用位域,一种利用取余. 这里如果不用unsigned char来做位域的话,大小就为4. unsigned char才符合题目要求. 1 void chess1() { 2 struct { 3 unsigned char a:4; 4 unsigned char b:4; 5 } i; 6 cout << "sizeof(i): " << sizeof(i) << endl; 7 for (i.a = 1; i.a <

编程之美读书笔记之---”不要被阶乘吓到“

问题一:给定一个整数N,那么N的阶乘末尾有多少个0呢?例如N = 10, N! = 362800,N! 的末尾有两个0. 问题二:求N! 的二进制表示中,最低位1的位置. 问题一的解法一: 最简单的方法就是把N! 算出来,就可以知道末尾有多少个0了. 问题一的解法二: 我们这样想,末尾的0可以从哪里得到呢,10的倍数,例如像10,20,100....这样的,可以贡献0,还有就是2 * 5这样也可以得到一个0,不过我们可以发现,10其实也是从5得来的, 10 = 2 * 5, 20 = 4 * 5