QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#853785#9735. Japanese Bandsucup-team191#WA 38ms76036kbC++232.6kb2025-01-11 19:15:092025-01-11 19:15:10

Judging History

你现在查看的是最新测评结果

  • [2025-01-18 23:34:05]
  • hack成功,自动添加数据
  • (/hack/1459)
  • [2025-01-11 19:15:10]
  • 评测
  • 测评结果:WA
  • 用时:38ms
  • 内存:76036kb
  • [2025-01-11 19:15:09]
  • 提交

answer

#include <bits/stdc++.h>

using namespace std;

const int N = 21;
const int MSK = (1 << 20);
const int MOD = 1e9 + 7;

inline int add(int A, int B) {
	if(A + B >= MOD) return A + B - MOD;
	return A + B;
}

inline int sub(int A, int B) {
	if(A - B < 0) return A - B + MOD;
	return A - B;
}

inline int mul(int A, int B) {
	return A * 1ll * B % MOD;
}

inline int pot(int A, int B) {
	int ret = 1;
	for(; B ; B >>= 1) {
		if(B & 1) ret = mul(ret, A);
		A = mul(A, A);
	}
	return ret;
}

int sus[N], n_1, n_2, m, k;
int dp[N][MSK], svi[MSK];

int ch[2][N], ob_ch[N][N];

void solve() {
	memset(sus, 0, sizeof(sus));
	scanf("%d%d%d%d", &n_1, &n_2, &m, &k); n_1--, n_2--;
	ch[0][0] = ch[1][0] = 1;
	for(int t = 1;t <= m;t++) {
		ch[0][t] = mul(ch[0][t - 1], mul(n_1 - t + 1, pot(t, MOD - 2)));
		ch[1][t] = mul(ch[1][t - 1], mul(n_2 - t + 1, pot(t, MOD - 2)));
	}
	
	int moraju = 0, vani = 0;
	for(int i = 0;i < k;i++) {
		int a, b; scanf("%d%d", &a, &b);
		a--, b--;
		vani |= (1 << a) | (1 << b);
		if(a == b) moraju |= 1 << a;
		else  {
			sus[a] |= (1 << b);
			sus[b] |= (1 << a);
		}
	}
	int Z = vani ^ moraju;

	vani = m - __builtin_popcount(vani);
	moraju = __builtin_popcount(moraju);

	int ind = 0;
	for(int msk = Z; msk; msk = (msk - 1) & Z) {
		svi[ind++] = msk;
	}
	dp[0][0] = 1;
	for(int i = ind - 1;i >= 0;i--) {
		int x = __lg(svi[i]);		
		int ss = (sus[x] & svi[i]) | (1 << x);
		int cnt = __builtin_popcount(svi[i]);
		int cnt2 = __builtin_popcount(ss) - 1;
		for(int j = 1;j <= cnt;j++)
			dp[j][svi[i]] = dp[j - 1][svi[i] ^ (1 << x)];
		for(int j = cnt2;j <= cnt;j++)
			dp[j][svi[i]] += dp[j - cnt2][svi[i] ^ ss];
	}
	int ans = 0;
	svi[ind] = 0;
	for(int i = 0;i <= ind;i++) {
		bool dobar = true;
		for(int j = 0;j < m;j++) {
			if((1 << j) & svi[i]) continue;
			if(!((1 << j) & Z)) continue;
			if(sus[j] & (Z ^ svi[i])) dobar = false;
		}
		if(!dobar) continue;
		int L = 0, R = 0;
		int vel = __builtin_popcount(svi[i]);
		for(int j = 0;j <= vel;j++) {
			for(int dod = 0;dod <= vani;dod++) {
				if(j + dod + (m - vani - vel) > 0)
					R = add(R, mul(ob_ch[vani][dod], mul(dp[j][svi[i]], ch[1][j + dod + (m - vani - vel) - 1])));
			}
		}
		for(int dod = 0;dod <= vani;dod++)
			if(vel + dod + moraju > 0)
				L = add(L, mul(ob_ch[vani][dod], ch[0][vel + dod + moraju - 1]));
		ans = add(ans, mul(L, R));
	}
	printf("%d\n", ans);
}

int main() {
	for(int i = 0;i < N;i++) ob_ch[i][i] = ob_ch[i][0] = 1;
	for(int n = 1;n < N;n++)
		for(int k = 1;k < n;k++)
			ob_ch[n][k] = add(ob_ch[n - 1][k - 1], ob_ch[n - 1][k]);
	int T; scanf("%d", &T);
	for(;T--;) solve();
	return 0;
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 1ms
memory: 12196kb

input:

3
2 3 3 3
2 3
1 1
2 3
2 2 2 1
1 1
1 1 10 2
1 2
1 3

output:

6
4
0

result:

ok 3 lines

Test #2:

score: -100
Wrong Answer
time: 38ms
memory: 76036kb

input:

500
481199252 336470888 8 58
4 7
7 6
4 7
2 6
2 6
2 7
8 3
8 7
8 1
2 6
2 6
1 2
1 5
3 1
6 4
2 4
4 7
2 6
2 3
7 1
4 4
5 1
2 7
6 7
8 1
8 7
5 6
4 2
4 2
8 5
5 4
6 8
5 6
3 8
1 7
1 6
7 1
5 6
6 3
1 1
2 7
3 3
1 5
5 5
8 7
3 4
6 3
8 8
7 4
1 6
2 1
8 7
4 5
2 7
3 5
2 6
4 5
4 3
2 6 2 2
2 1
1 1
500330171 987581927 10 ...

output:

724920553
12
579901092
899472719
317242474
1
843830107
658545278
1
269113412
451420947
1
0
609678007
406362572
578055068
3858776
147729622
739211824
601906839
0
487514263
436874930
182398261
16
414442277
563522120
515100860
1
639478118
830566917
889861497
126
86879785
1
55391062
356707395
1
1
437071...

result:

wrong answer 2nd lines differ - expected: '11', found: '12'