75分,太菜,不会优化了,吐了。
几点优化。
1.先搜索容易确定的位置
2.从中心往周围搜
3.枚举数字的时候倒序枚举
4.如果没有枚举到的数字都是最优情况的话也不能比当前ans大就剪枝
5.位运算
#include <cstdio> #include <iostream> #include <algorithm> #define max(x, y) ((x) > (y) ? (x) : (y)) #define tu(i, j) (((i) - 1) / 3 * 3 + ((j) - 1) / 3 + 1) int ans = -1, cnt; int hang[10], lie[10], jiu[10], shu[10], a[10][10], num[10][10], point[11]; struct node { int pt, x, y, z; node(int pt = 0, int x = 0, int y = 0, int z = 0) : pt(pt), x(x), y(y), z(z) {} }p[101]; inline int read() { int x = 0, f = 1; char ch = getchar(); for(; !isdigit(ch); ch = getchar()) if(ch == '-') f = -1; for(; isdigit(ch); ch = getchar()) x = (x << 1) + (x << 3) + ch - '0'; return x * f; } inline bool cmp(node x, node y) { return x.z > y.z || (x.z == y.z && x.pt > y.pt); } inline int pd(int x, int y) { if(x == 1 || x == 9 || y == 1 || y == 9) return 6; if(x == 2 || x == 8 || y == 2 || y == 8) return 7; if(x == 3 || x == 7 || y == 3 || y == 7) return 8; if(x == 4 || x == 6 || y == 4 || y == 6) return 9; return 10; } inline bool check(int sum) { int i, j, k, top; k = 10; top = point[k]; for(i = 9; i >= 1; i--) for(j = 1; j <= 9 - shu[i]; j++) if(top) top--, sum += i * k; else { while(!top && k > 6) k--, top = point[k]; top--; sum += i * k; } return sum > ans; } inline void dfs(int x, int y, int k, int sum) { if(k > cnt) { ans = max(ans, sum); return; } for(int i = 9; i >= 1; i--) if(!(hang[x] & (1 << i - 1)) && !(lie[y] & (1 << i - 1)) && !(jiu[tu(x, y)] & (1 << i - 1))) { shu[i]++; point[pd(x, y)]--; lie[y] |= 1 << i - 1; hang[x] |= 1 << i - 1; jiu[tu(x, y)] |= 1 << i - 1; if(check(sum + p[k].pt * i)) dfs(p[k + 1].x, p[k + 1].y, k + 1, sum + p[k].pt * i); jiu[tu(x, y)] ^= 1 << i - 1; hang[x] ^= 1 << i - 1; lie[y] ^= 1 << i - 1; point[pd(x, y)]++; shu[i]--; } } int main() { int i, j, k, l, x, sum = 0; point[6] = 32; point[7] = 24; point[8] = 16; point[9] = 8; point[10] = 1; for(i = 1; i <= 9; i++) for(j = 1; j <= 9; j++) { shu[a[i][j] = read()]++; sum += a[i][j] * pd(i, j); if(a[i][j]) { point[pd(i, j)]--; lie[j] |= 1 << a[i][j] - 1; hang[i] |= 1 << a[i][j] - 1; jiu[tu(i, j)] |= 1 << a[i][j] - 1; } } for(i = 1; i <= 9; i++) for(j = 1; j <= 9; j++) { for(k = 1; k <= 9; k++) if(a[i][k] && k != j) num[i][j]++; for(k = 1; k <= 9; k++) if(a[k][j] && k != i) num[i][j]++; for(k = 1; k <= 9; k++) for(l = 1; l <= 9; l++) if(tu(i, j) == tu(k, l) && a[k][l] && !(i == k && j == l)) num[i][j]++; } for(i = 1; i <= 9; i++) for(j = 1; j <= 9; j++) if(!a[i][j]) p[++cnt] = node(pd(i, j), i, j, num[i][j]); std::sort(p + 1, p + cnt + 1, cmp); dfs(p[1].x, p[1].y, 1, sum); printf("%d ", ans); return 0; }