《编程之美》笔记(一)

  1.2 中国象棋将帅问题。

  中国象棋中,“将”和“帅”都有九个位置可以选择放置,找出所有将和帅不再一列的放置方法,要求只能使用一个字节存储变量。

  这道题的难点在于只能使用一个字节存储变量。第一种思路是用一个字节的高四位和底四位分别保存将和帅的位置,一种方法是使用位操作,略显麻烦,另外一种方法就是使用位域(bit-field),操作比较简单;第二种思路就是利用二维矩阵与一维的对应关系,通过 /C 和 %C 操作得到元素的行号和列号(C为二维矩阵的列数),如下图。

  0 1 2
0 0 1 2
1 3 4 5
2 6 7 8

  因为以前只是知道位域这个概念,没有用过,就写一下代码熟悉一下吧。

 1 #include <stdio.h>
 2 
 3 struct
 4 {
 5     unsigned char a:4;
 6     unsigned char b:4;
 7 } i;
 8 
 9 int main()
10 {
11     for (i.a = 1; i.a <= 9; i.a++)
12         for (i.b = 1; i.b <= 9; i.b++)
13             if (i.a%3 != i.b%3)
14                 printf("A = %d, B = %d
", i.a, i.b);
15     return 0;
16 }
bit-field

   4.3 买票找零

  有2n个人在排队买门票,门票50一张,其中有n个人手持50的钞票,n个人手持100元的钞票。开始时售票处没有零钱,问这2n个人有多少中排队方式,使得售票处到最后都可以找到零钱。

  关于卡特兰数(Catalan)的问题。h(0)=1, h(1)= 1, 当n>=2时,h(n) = h(0)*h(n-1) + h(1)*h(n-2) + ... + h(n-1)*h(0), h(n) = C(2n, n)/(n+1)。

  与卡特兰数相关的问题有:

  • 矩阵链乘的括号化方案数。
  • 多边形的三角剖分方案数。
  • n个节点构成不同二叉树个数。
  • 圆上n条直线不相交方案数。
  • 从(0, 0)到(n, n)不越过连线的走法数。

  3.6 判断两个链表是否相交

  因为单链表的特点,实际是就是判断两个链表是否有公共节点问题,判断最后一个节点就好了。《剑指Offer》第37题介绍了求两个链表第一个公共节点的方法。

  3.7 队列中最大值操作问题

  在正常队列基础上增加取最大值操作。其实就是《剑指Offer》第7题:用两个栈实现队列和第21题:包含min函数的栈的结合。可是这道题还是没能做出来...

  2.9 斐波那契数列

  正常的解法就是递推,不过公式+二分的解法在处理大数据的时候还是挺好的,将时间复杂度优化到了O(log2n)。

  2.10 寻找数组中的最大值和最小值

  这个题的优化就是分成两个一组,这样只需一次比较就得出的该组的最大值和最小值,将比较次数较少了n/2次。

原文地址:https://www.cnblogs.com/xiaobaibuhei/p/3345707.html