2018"百度之星"程序设计大赛 - 初赛

/* * @Author: Achan * @Date: 2019-08-16 22:00:16 * @Last Modified by: Achan * @Last Modified time: 2019-08-17 00:04:24 */
#include
using namespace std;
int main(void)
{
    int T;
    cin >> T;
    int cas = 1;
    while(T--)
    {
    	int n,m,k;
    	cin >> n >> m >> k;
    	std::vector<int> v(n);
    	for (int i = 0; i < n; ++i)
    	{
    		string s;
    		cin >> s;
    		for (int j = 0; j < m; ++j)
    		{
    			v[i] |= ( (s[j]=='A')<<j );
    		}
    	}
    	int ans = 0;
    	for (int i = (1<<m) - 1; i; i--) //对于m位的每一种状态集合,这里的集合不能为全0
    	{
    		/* code */
    		std::vector<int> num(1<<m,0); 
    		for (int j = 0; j < n; ++j)  //统计某种相同答案的人数
    		{
    			/* code */
    			num[v[j] & i]++;  //在当前集合下统计故用 & 
    			//cout << (v[j]^i) << endl;
    		}
    		int tot = 0;
    		for (int j = 0; j < (1<<m); ++j) //遍历每一种答案(这里必须包括全0,全0和非全0的任意两两组合皆满足条件),统计两两不同总对数
    		{
    			/* code */
    			
    			tot += num[j] * (n - num[j]); //组合数的基础
    			
    		}
    		//cout << tot << endl; 
    		if( (tot>>1) >= k ) ans++;
    	}
     	cout << "Case #" << cas++ << ": " << ans << endl;
    }
    
#ifdef LOCAL
    Debug("My Time: %.3lfms\n", (double)clock() / CLOCKS_PER_SEC);
#endif 
    return 0;
}

你可能感兴趣的:(思维)