Polycarp is a music editor at the radio station. He received a playlist for tomorrow, that can be represented as a sequence a1, a2, ..., an, where ai is a band, which performs the i-th song. Polycarp likes bands with the numbers from 1 to m, but he doesn't really like others.
We define as bj the number of songs the group j is going to perform tomorrow. Polycarp wants to change the playlist in such a way that the minimum among the numbers b1, b2, ..., bm will be as large as possible.
Find this maximum possible value of the minimum among the bj (1 ≤ j ≤ m), and the minimum number of changes in the playlist Polycarp needs to make to achieve it. One change in the playlist is a replacement of the performer of the i-th song with any other group.
The first line of the input contains two integers n and m (1 ≤ m ≤ n ≤ 2000).
The second line contains n integers a1, a2, ..., an (1 ≤ ai ≤ 109), where ai is the performer of the i-th song.
In the first line print two integers: the maximum possible value of the minimum among the bj (1 ≤ j ≤ m), where bj is the number of songs in the changed playlist performed by the j-th band, and the minimum number of changes in the playlist Polycarp needs to make.
In the second line print the changed playlist.
If there are multiple answers, print any of them.
4 2 1 2 3 2
2 1 1 2 1 2
7 3 1 3 2 2 2 2 1
2 1 1 3 3 2 2 2 1
4 4 1000000000 100 7 1000000000
1 4 1 2 3 4
In the first sample, after Polycarp's changes the first band performs two songs (b1 = 2), and the second band also performs two songs (b2 = 2). Thus, the minimum of these values equals to 2. It is impossible to achieve a higher minimum value by any changes in the playlist.
In the second sample, after Polycarp's changes the first band performs two songs (b1 = 2), the second band performs three songs (b2 = 3), and the third band also performs two songs (b3 = 2). Thus, the best minimum value is 2.
Source
Codeforces Round #375 (Div. 2)
My Solution
贪心+排序
刚开始的时候理解题意错了,以为最小值尽可能大,最大值尽可能小,
但其实是中间贪心的过程中把最大值的 cnt[m-1].b的乐队变成最小值的乐队 cnt[0].b,直到 cnt[0].cnt 达到 n / m 就是最大的那个最小值了,而bj 的最大值不用再压缩了。
即
val[i].b 表示乐队编号, val[i].cnt 表示该乐队当前表演songs的数量
while(最小值 < int(n / m)){
如果 大于m的 v[j] 还有则把这个v[j] 变成 当前最小值的乐队 val[0].b;
否则把当前最大值的乐队变成 当前最小值的乐队 val[0].b;
cnt++;
重新排序
}
复杂度 O(n^2)
#include <iostream> #include <cstdio> #include <algorithm> #include <map> #include <cstring> using namespace std; typedef long long LL; const int maxn = 2e3 + 8; struct p{ int b, cnt = 0; }val[maxn]; inline bool cmp(const p& a, const p& b) { return a.cnt < b.cnt; } int v[maxn]; map<int, int> sz; //priority_queue<ii, vector<ii>, greater<ii> > pq; int main() { #ifdef LOCAL freopen("c.txt", "r", stdin); //freopen("c.out", "w", stdout); int T = 6; while(T--){ #endif // LOCAL ios::sync_with_stdio(false); cin.tie(0); int n, m, cnt = 0, k = 0; cin >> n >> m; for(int i = 0; i < n; i++){ cin >> v[i]; sz[v[i]]++; if(v[i] > m) k++; } for(int i = 1; i <= m; i++){ val[i-1].cnt = sz[i]; val[i-1].b = i; } sort(val, val + m, cmp); //cout << val[0].cnt << " " << val[m-1].cnt << endl; while(val[0].cnt < (n / m)){ //m <= m ¹Ê val[0].cnt > 0 //cout << "H"<<endl; if(k == 0){ val[0].cnt++; val[m-1].cnt--; cnt++; for(int i = 0; i < n; i++){ if(v[i] == val[m-1].b){ v[i] = val[0].b; break; } } } else{ k--; val[0].cnt++; cnt++; for(int i = 0; i < n; i++){ if(v[i] > m){ v[i] = val[0].b; break; } } } sort(val, val + m, cmp); } cout << val[0].cnt << " " << cnt << endl; for(int i = 0; i < n; i++){ if(i != 0) cout << " " << v[i]; else cout << v[i]; } #ifdef LOCAL sz.clear(); memset(val, 0, sizeof val); cout << endl; } #endif // LOCAL return 0; }
Thank you!
------from ProLights