题目链接
题意:给出n个点,记为数组a,然后要你构造出m个点,记为数组b,要求这m+n个元素互不相同,同时对于b数组的每个元素,满足每个点到最近的a数组里的某个元素距离最近,求最近的距离的和,同时构造出b数组。
思路:很显然,根据贪心思想,我们的b数组最好的就是在每个a元素的两端,比如a数组是1 3 6,那么构造b数组的时候就考虑,1的两端0,-1,3的两端2,4,6的两端5,7,以此类推,这个过程其实就是bfs的过程。
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn=2e5+1;
int n,m;
ll sum=0,a[maxn];
map<ll,ll>vis;
queue<ll>q;
vector<ll>ans;
void bfs()
{
while(m>0)
{
int top=q.front();
q.pop();
if(vis[top-1]==0) {
vis[top-1]=vis[top]+1,sum+=vis[top];
q.push(top-1);m--;
ans.push_back(top-1);
}
if(m==0) break;
if(vis[top+1]==0)
{
vis[top+1]=vis[top]+1,sum+=vis[top];
q.push(top+1);m--;
ans.push_back(top+1);
}
}
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=1;i<=n;++i) scanf("%lld",&a[i]),vis[a[i]]=1;
for(int i=1;i<=n;++i) if(!vis[a[i]-1]||!vis[a[i]+1]) q.push(a[i]);
bfs();
printf("%lld\n",sum);
for(int i=0;i<ans.size();++i) printf("%lld ",ans[i]);
}