Equalizing by Division (easy version)&&(hard version)

题目链接:http://codeforces.com/contest/1213/problem/D1

大致题意:

给出一个数组arr,可以将数组里的数进行向下取整的除2操作,求最少的操作数使得数组中有k个数相同

#include <bits/stdc++.h>
const int maxn=1e5+10;
using namespace std;
int a[maxn];
int num[maxn];
int sum[maxn];
int main()
{
    ios::sync_with_stdio(0);
    int n,m;
    int ans=maxn;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
        cin>>a[i];
    sort(a+1,a+n+1);
    for(int i=1;i<=n;i++){
        int temp=0;
        int x=a[i];
        while(x){
            num[x]++;
            sum[x]+=temp;
            if(num[x]==m)
                ans=min(ans,sum[x]);
            temp++;
            x/=2;
        }
    }
    cout<<ans<<endl;
    return 0;
}

另附困难版本代码,n,k范围变大

#include <stdio.h>
#include <algorithm>
#include <string.h>
#include <vector>
#include <numeric>
#include <math.h>
typedef long long ll;
using namespace std;
const int N = 2e5+11;

int n,k;
vector<int>a[N];

int main(){
	scanf("%d%d",&n,&k);
	for(int i = 1;i <= n;i++){
		int x,k = 0;
		scanf("%d",&x);
		while(x){
			a[x].push_back(k);
			x /= 2;
			k++;
		}
	}
	int ans = 1e9;
	for(int i = 1;i <= 200*1000;i++){
		if(a[i].size() >= k){
			sort(a[i].begin(),a[i].end());
			ans = min(ans,accumulate(a[i].begin(),a[i].begin()+k,0));
		}
	}
	printf("%d\n",ans);
	return 0;
}

 

posted @ 2019-09-11 12:02  Shmilky  阅读(82)  评论(0编辑  收藏  举报