Online JudgeProblem SetAuthorsOnline ContestsUser
Web Board
Home Page
F.A.Qs
Statistical Charts
Problems
Submit Problem
Online Status
Prob.ID:
Register
Update your info
Authors ranklist
Current Contest
Past Contests
Scheduled Contests
Award Contest
User ID:
Password:
  Register

折半状压 O(n*2^n)

Posted by kg20006 at 2017-03-18 19:54:04 on Problem 2531
#include <stdio.h>
#include <algorithm>
#include <string.h>
#define ok(x,i) (((x)>>(i))&1)
using namespace std;
int C[25][25];
int lf[20][1<<10], rt[20][1<<10];
int main() {
	int n;
	while(scanf("%d", &n) != EOF) {
		memset(lf, 0, sizeof(lf));
		memset(rt, 0, sizeof(rt));
		int tot = 0;
		for(int i = 0; i < n; ++i) {
			for(int j = 0; j < n; ++j) {
				scanf("%d", C[i]+j);
			}
		}
		int up = 1<<n, left = n/2, right = n-n/2;
		int leftup = 1<<left, rightup = 1<<right;
		for(int i = 0; i < leftup; ++i) {
			for(int j = 0; j < n; ++j) {
				if(ok(i, j)) continue;
				for(int k = 0; k < left; ++k) {
					if(ok(i, k)) {
						lf[j][i] += C[j][k];
					}
				}
			}
		}
		for(int i = 0; i < rightup; ++i) {
			for(int j = 0; j < n; ++j) {
				if(ok(i<<left, j)) continue;
				for(int k = 0; k < right; ++k) {
					if(ok(i, k)) {
						rt[j][i] += C[j][k+left];
					}
				}
			}
		}
		int ans = -1;
		for(int i = 0; i < up; ++i) {
			int tmp = 0;
			for(int j = 0; j < n; ++j) {
				if(ok(i, j)) continue;
				tmp += lf[j][i&(leftup-1)] + rt[j][i>>left];
			}
			ans = max(ans, tmp);
		}
		printf("%d\n", ans);
	}
}

Followed by:

Post your reply here:
User ID:
Password:
Title:

Content:

Home Page   Go Back  To top


All Rights Reserved 2003-2013 Ying Fuchen,Xu Pengcheng,Xie Di
Any problem, Please Contact Administrator