大题题意:给你一个数组m和c,要将m数组划分成若干个子数组,c[i]表示每个子数组中最多有c[i]个大于等于 i 的。问最小能划分成几组并输出每个组。
开一个sum数组保存后缀和,sum[i]表示大于等于 i 的数有多少个,然后针对每个 i ,需要分sum[i]/c[i](上取整)个组,确定好分多少组直接分就好了
代码:
#include <bits/stdc++.h>
#define ll long long
using namespace std;
ll m[200005],c[200005];
ll sum[200005],book[200005];
vector<ll>d[200005];
int main()
{
ll n,k;
scanf("%lld %lld",&n,&k);
for(int i=1;i<=n;i++)
{
scanf("%lld",&m[i]);book[m[i]]++;}
for(int i=1;i<=k;i++)
{
scanf("%lld",&c[i]);}
sort(m+1,m+1+n);
for(int i=200001;i>=1;i--)
{
if(book[i]>0)
{
sum[i]=sum[i+1]+book[i];}
else
{
sum[i]=sum[i+1];}
}
ll maxx=-1,op;
for(int i=1;i<=k;i++)
{
if(c[i]>=sum[i])
{
op=1;
maxx=max(op,maxx);
}
else
{
if(sum[i]%c[i]==0)
{
op=sum[i]/c[i];
maxx=max(maxx,op);
}
if(sum[i]%c[i]!=0)
{
op=sum[i]/c[i]+1;
maxx=max(maxx,op);
}
}
}
printf("%lld\n",maxx);
int e=1;
for(int i=n;i>=1;i--)
{
d[e].push_back(m[i]);
e++;
if(e==maxx+1)
{
e=1;}
}
for(int i=1;i<=maxx;i++)
{
printf("%lld ",d[i].size());
for(int j=0;j<d[i].size();j++)
{
printf("%lld ",d[i][j]);}
printf("\n");
}
return 0;
}