★实验任务
有 n 个人参加舞蹈课,每个人以他的舞蹈技能 ai 为特点。舞蹈课开始前,他们从左到右排成一行。当队伍中至少含有一名男生和一名女生时,下面的过程会重复进行:站在相邻位置的男女生且舞蹈技能差异最小的开始跳舞。如果有很多对,最靠左边的开始跳舞。跳舞完以后就离开。舞蹈技能的差异为| ai-aj| 。你的任务是找到每一对,并找出是按什么顺序开始跳舞。
★数据输入
输入的第 1 行是一个正整数 n(1 <= n <= 2 * 10^5) ,表示人的个数。第 2 行包含 n 个字符” B” 或” G” ,分别代表男生和女生,之间没有用空格隔开。第 3 行包含 n 个整数 ai (1 ≤ ai ≤ 10^7), 表示每个人的舞蹈技能。按从左到右的顺序排列。
★数据输出输出 k 对。接下去输出 k 行,每行包含 2 个整数,表示组成一对的男女生的序号。按从左到右从 1 到 n 开始排序。当一对舞者离开时不用重新排序。打印每一对时按递增打印。按跳舞的顺序打印。
输入示例 输出示例
4 2
BGBG 3 4
4 2 4 3 1 2
<span style="color:#000000;"> #include<iostream>
using namespace std;
struct DanceClass
{
long int ability;
bool sex,sign;
DanceClass ()
{
sign=1;
};
};
struct delta
{
long int dt,from,to;
};
void buildheap(delta*dl,long int n)
{
long int dec,son;
bool ok;
for(dec=n/2+1;dec>=1;dec--)
{
dl[0]=dl[dec];
son=2*dec;
ok=1;
while(son<=n&&ok)
{
if(son<n&&(dl[son].dt>dl[son+1].dt||
dl[son].dt==dl[son+1].dt&&dl[son].from>dl[son+1].from))son++;
if(dl[0].dt>dl[son].dt||dl[0].dt==dl[son].dt&&dl[0].from>dl[son].from)
{
dl[son/2]=dl[son];
son*=2;
}
else
ok=0;
}
dl[son/2]=dl[0];
}
}
void improve(delta*dl,long int sail)
{
long int father,son;
bool ok=1;
son=2;
father=1;
while(son<sail-1&&ok)
{
if(son<=sail-1&&(dl[son].dt>dl[son+1].dt||
dl[son].dt==dl[son+1].dt&&dl[son].from>dl[son+1].from))son++;
if(dl[sail].dt>dl[son].dt||dl[sail].dt==dl[son].dt&&dl[sail].from>dl[son].from)
{
dl[father]=dl[son];
father=son;
son*=2;
}
else
ok=0;
}
dl[father]=dl[sail];
}
long int rebuildheap(delta*dl,DanceClass*DC,long int sail,long int n)
{
long int ff,tt;
ff=dl[1].from;
tt=dl[1].to;
DC[ff].sign=0;
DC[tt].sign=0;
while(ff>=0&&DC[ff].sign==0)
ff--;
while(tt<=n&&DC[tt].sign==0)
tt++;
if(ff>=0&&tt<=n&&DC[ff].sign&&DC[tt].sign&&DC[ff].sex!=DC[tt].sex)
{
sail++;
dl[sail].from=ff;
dl[sail].to=tt;
dl[sail].dt=DC[ff].ability-DC[tt].ability;
if(dl[sail].dt<0)dl[sail].dt=-dl[sail].dt;
}
improve(dl,sail);
sail--;
while(DC[dl[1].from].sign==0||DC[dl[1].to].sign==0)
{
improve(dl,sail);
sail--;
}
return sail;
}
int main()
{
long int n,add,inc,total;
char c;
DanceClass*DC;
delta*dl;
scanf("%d",&n);
DC=new DanceClass [n];
dl=new delta[n];
c=getchar();
for(add=0,total=0;add<n;add++)
{
c=getchar();
if(c=='B')
{
DC[add].sex=1;
total++;
}
else
DC[add].sex=0;
}
c=getchar();
for(add=0,inc=1;add<n;add++)
{
scanf("%d",&DC[add].ability);
if(add>0&&DC[add-1].sex!=DC[add].sex)
{
dl[inc].dt=DC[add-1].ability-DC[add].ability;
dl[inc].from=add-1;
dl[inc].to=add;
if(dl[inc].dt<0)dl[inc].dt=-dl[inc].dt;
inc++;
}
}
buildheap(dl,inc-1);
if(total+total>n)
total=n-total;
printf("%d\n",total);
inc--;
n--;
while(total>0)
{
total--;
printf("%d %d\n",dl[1].from+1,dl[1].to+1);
if(total)
inc=rebuildheap(dl,DC,inc,n);
}
return 0;
} </span>