• 【BZOJ 1005】【HNOI 2008】明明的烦恼


    http://www.lydsy.com/JudgeOnline/problem.php?id=1005
    答案是$$frac{(n-2)!}{(n-2-sum)!×prod_{i=1}{cnt}(d[i]-1)!}×(n-cnt){n-2-sum}$$

    [sum=sum_{i=1}^{cnt}(d[i]-1) ]

    用到了prufer编码,参考http://www.cnblogs.com/zhj5chengfeng/p/3278557.html
    注意要写高精度!

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    using namespace std;
    
    typedef long long ll;
    const int N = 1003;
    
    bool notp[N];
    int cnt = 0, n, d[N], num = 0, prime[N], sum = 0, tot[N];
    
    void shai() {
    	for (int i = 2; i <= n; ++i) {
    		if (!notp[i]) prime[++num] = i;
    		for (int j = 1; j <= num && i * prime[j] <= n; ++j) {
    			notp[i * prime[j]] = true;
    			if (i % prime[j] == 0)
    				break;
    		}
    	}
    }
    
    void add(int x, int flag) {
    	for (int i = 1; i <= num && x != 1; ++i)
    		if (x % prime[i] == 0)
    			while (x % prime[i] == 0) {
    				tot[i] += flag;	
    				x /= prime[i];
    			}
    }
    
    ll ipow(int x, int b) {
    	ll w = x, r = 1;
    	while (b) {
    		if (b & 1) r *= w;
    		w = w * w;
    		b >>= 1;
    	}
    	return r;
    }
    
    struct Big {
    	int a[10003], len;
    	Big() {memset(a, 0, sizeof(a)); len = 0;}
    	Big operator * (const int &b) const {
    		Big C;
    		for (int i = 1; i <= len; ++i) {
    			C.a[i] += a[i] * b;
    			C.a[i + 1] += C.a[i] / 10;
    			C.a[i] %= 10;
    		}
    		C.len = len;
    		while (C.a[C.len + 1] != 0) {
    			++C.len;
    			C.a[C.len + 1] = C.a[C.len] / 10;
    			C.a[C.len] %= 10;
    		}
    		return C;
    	}
    };
    
    int main() {
    	scanf("%d", &n);
    	int dd;
    	for (int i = 1; i <= n; ++i) {
    		scanf("%d", &dd);
    		if (dd != -1)
    			d[++cnt] = dd, sum += dd - 1;
    	}
    	shai();
    	
    	if (n == 1) {
    		puts(dd > 0 ? "0" : "1");
    		return 0;
    	}
    	
    	if (sum > n - 2) {
    		puts("0");
    		return 0;
    	}
    	
    	int down = n - 2 - sum;
    	for (int i = n - 2; i > down; --i) add(i, 1);
    	for (int i = 1; i <= cnt; ++i)
    		for (int j = d[i] - 1; j > 1; --j)
    			add(j, -1);
    	add(n - cnt, down);
    	
    	Big ans; ans.len = 1; ans.a[1] = 1;
    	for (int i = 1; i <= num; ++i)
    		for (int j = tot[i]; j >= 1; --j)
    			ans = ans * prime[i];
    	for (int i = ans.len; i >= 1; --i)
    		putchar('0' + ans.a[i]);
    	puts("");
    	return 0;
    }
    
  • 相关阅读:
    CF1137C Museums Tour(tarjan+DP)
    Educational Codeforces Round 65 (Rated for Div. 2)
    Codeforces Round #559(Div.1)
    委托
    类库
    is 和 as 运算符
    面向对象 接口
    抽象类
    面向对象 多态
    访问修饰符 程序集 静态方法
  • 原文地址:https://www.cnblogs.com/abclzr/p/6194542.html
Copyright © 2020-2023  润新知