1、这题和杨辉三角很像,可以找规律:每一个数字都是它上方数字加上右上方数字再模2。
(1)2的n次方可以用二进制数左移的方式;
(2)register声明的变量会被放到CPU的寄存器里,不用从内存取,用时更短;
(3)C++中的a^b为按位异或,异或根据计算位是否相同决定结果位,如果相同结果位为0,否则为1。
2、赦免的函数是对称的,f(i,j)=f(j,i),可考虑用位运算,发现 i|j=111(7),得出以下判断式:
f(i,j)=((i|j)!=((1<<n)-1)?0:1)。
3、本题基本思路是分治,代码可以通过递归来实现(好写但用时长),每次递归将左上方的正方形清零,并再次递归剩余的三个正方形,当正方形的边长为2时结束递归。
4、找规律,然后打表。
(1)C 库函数 double pow(double x, double y) 返回 x 的 y 次幂;
5、核心思想(方法):求下一个方阵的情况,逐行逐行的将当前方阵情况插入下方(在下面复制两次),最后再补0。
(1)头文件 #include < string > 里有一个本题特别重要的函数—— insert() 函数
(2)copy下洛谷 @渊源 大佬有趣的AC算法(转侵删)
a[0]="01"; //第一行情况
a[1]="11"; //第二行情况
for(long I=2;I<=n;I++){ //现在是第几个方阵(即求输入I的输出结果)(**分治思想**)
for(long i=A[I-1];i<A[I];i++){ //新增行的行号(是第几行)
a[i].insert(a[i].length(),a[i-A[I-1]]); //在新一行尾部插入
a[i].insert(a[i].length(),a[i-A[I-1]]); //**插入两次**
}
for(long i=0;i<A[I-1];i++) //在头几行最前面插入A[I-1]个0(应该不需要解释了吧)
for(long j=0;j<A[I-1];j++) //字符串**存储时不带空格,输出才带空格**
a[i].insert(0,"0");
}
原博客:题解 P5461 【赦免战俘】
6、找规律:
首先n要先变成2^n。
不难发现,对于第一行的最后一个(即(1,n)),为1。
从第二行开始,对于每一个数可以用它上一个的数+右上的一个数,然后再%2。
因为求出来之后这个数字就不会改变,而且只涉及到上一行,所以可以直接用一维数组来模拟(上一个数就是自身,右上的数就是后一个)。
(1)用位运算可以加快速度(强调第二遍);
(2)ios::sync_with_stdio(false); 加快cin cout输入输出;
(2020/5/27 22:28 明天继续做大自然的搬运工,看题解真的能收获良多~)