zoukankan      html  css  js  c++  java
  • ural 1932 The Secret of Identifier 容斥

    主题链接:点击打开链接

    stl+容斥

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <vector>
    #include <iostream>
    #include <set>
    using namespace std;
    #define N 65540
    #define ll __int64
    ll n;
    ll a[N][4], mul[4]={1,16,256,4096};
    ll h[N];
    vector<ll>G[N];
    set<ll>myset;
    set<ll>::iterator p;
    ll find1(ll x){ //设除了x位。其它3位同样
    	myset.clear();
    	for(ll i = 0; i < n; i++){
    		ll now = 0;
    		for(ll j = 0; j < 4; j++)if(j!=x)
    		now += a[i][j];
    		G[now].push_back(i);
    		myset.insert(now);
    	}
    	ll ans = 0;
    	for(p = myset.begin(); p!=myset.end(); p++) {
    		ll siz = G[*p].size();
    		ans += (siz*(siz-1))>>1;
    		G[*p].clear();
    	}
    	return ans;
    }
    
    ll find2(ll x,ll y){
    	myset.clear();
    	for(ll i = 0; i < n; i++) {
    		ll now = 0;
    		for(ll j = 0; j < 4; j++)if(j!=x&&j!=y)
    			now += a[i][j];
    		G[now].push_back(i);
    		myset.insert(now);
    	}
    	ll ans = 0;
    	for(p = myset.begin(); p!=myset.end(); p++) {
    		ll siz = G[*p].size();
    		ans += (siz*(siz-1))>>1;
    		G[*p].clear();
    	}
    	return ans;
    }
    ll find3(ll x){
    	myset.clear();
    	for(ll i = 0; i < n; i++){
    		ll now = 0;
    		now += a[i][x];
    		G[now].push_back(i);
    		myset.insert(now);
    	}
    	ll ans = 0;
    	for(p = myset.begin(); p!=myset.end(); p++) {
    		ll siz = G[*p].size();
    		ans += (siz*(siz-1))>>1;
    		G[*p].clear();
    	}
    	return ans;
    }
    int main(){
    	ll i,j;
    	for(ll i = 0; i < N; i++)G[i].clear();
    	while(cin>>n) {
    		for(i=0;i<n;i++)
    		{
    			char s[10]; scanf("%s",s);
    			for(j=0;j<4;j++) {
    				a[i][j] = ('0'<=s[j]&&s[j]<='9')?s[j]-'0':s[j]-'a'+10;
    				a[i][j] *= mul[j];
    			}
    		}
    		ll ans[5] = {0};
    		ans[1] = find1(0) + find1(1) + find1(2) + find1(3);
    		ans[2] = find2(0,1) + find2(0,2) + find2(0,3) + find2(1,2) + find2(1,3) + find2(2,3) - ans[1]*3;
    		ans[3] = find3(0) + find3(1) + find3(2) + find3(3) - ans[1]*3 - ans[2]*2;
    		ll all = (ll) ((n*(n-1))/2);
    		ans[4] = all - ans[1] - ans[2] - ans[3];
    		cout<<ans[1]<<" "<<ans[2]<<" "<<ans[3]<<" "<<ans[4]<<endl;
    
    	}
    	return 0;
    }
    /*
    4
    abcd
    abca
    abce
    abcf
    10
    0000
    1111
    2222
    3333
    4444
    5555
    6666
    7777
    8888
    9999
    
    */


    版权声明:本文博主原创文章,博客,未经同意不得转载。

  • 相关阅读:
    697-数组的度
    1013-将数组分成和相等的三个部分
    linux命令基础
    Fiddler安卓抓包设置
    HTTPS协议
    HTTP协议
    TCP和UDP的区别
    TCP三次握手以及四次挥手
    OSI七层网络模型,数据传输过程解析
    jmeter常用命令(非GUI模式命令)
  • 原文地址:https://www.cnblogs.com/bhlsheji/p/4809903.html
Copyright © 2011-2022 走看看