| ||||||||||
| Online Judge | Problem Set | Authors | Online Contests | User | ||||||
|---|---|---|---|---|---|---|---|---|---|---|
| Web Board Home Page F.A.Qs Statistical Charts | Current Contest Past Contests Scheduled Contests Award Contest | |||||||||
请大牛看一下,我几百组数据都过了,为什么还是wa?#include<stdio.h>
#include<iostream>
#include<algorithm>
using namespace std;
#define N 1030
int len,k,a[N],lct[N][N],sum[N][N],in[9]= {1,1,2,6,24,120,720,5040,40320};
int tree[4*N];
void builde(int l,int r,int v)
{
int m=(l+r)>>1;
tree[v]=0;
if(l==r)return ;
builde(l,m,v<<1);
builde(m+1,r,v<<1|1);
}
int updata(int l,int r,int v,int id)
{
int m=(l+r)>>1;
tree[v]++;
if(l==r)return 0;
if(id<=m) return updata(l,m,v<<1,id)+tree[v<<1|1];
else return updata(m+1,r,v<<1|1,id);
}
int cmp(int a,int b)
{
return a<b;
}
int cmp1(int a,int b)
{
return a>b;
}
void xchg(int &a,int &b)
{
int t;
t=a;
a=b;
b=t;
}
int find(int i)//找出比a[i]大的数中最小的位置
{
int l;
for(l=i+1; l<len; l++)
if(a[i]<a[l]) return l;
}
void print(int l,int r)//输出l~r的数
{
for(; l<=r; l++)
if(l!=0) printf(" %d",a[l]);
else printf("%d",a[l]);
}
void setlct()//以数值从小到大的序列为目标,计算出每个sum,lct对应的大小
{
for(len=1024; len>=1; len--)
{
sum[len][len-1]=0; sum[len][len]=0;
for(int j=len-2; j>=0; j--)
{
lct[len][j]=len-j-1;//j后有len-j-1个数比a[j]大
sum[len][j]=sum[len][j+1];//位置j排列种数,越靠左的sum越大
if(len-j<=9)
sum[len][j]+=lct[len][j]*in[len-j-1];
}
}
}
int two(int l,int r,int ln)//找到sum[ln]中比k值大的数中最小的位置
{
for(; r>=l; r--)
if(sum[ln][r]>=k)
return r;
}
void ssss(int l,int ln)
{
if(l>=len) return ;
int i;
i=two(l,len-1,ln);
k-=sum[ln][i+1];//printf("k=%d ",k);
print(l,i-1);
l=i;
int m=k/in[len-i-1],j,flog=0;
if(k%in[len-i-1]) {m++,flog=1;}
sort(a+i+1,a+len,cmp);
j=find(i);
if(j>i)xchg(a[i],a[j+m-1]);
print(l,i);
l=i+1;
k-=(m-flog)*in[len-i-1];
if(k==0)
{
sort(a+l,a+len,cmp1);
print(l,len-1);
l=len;
return;
}
else
{
k--;
sort(a+l,a+len,cmp);
if(k==0)
{
print(l,len-1);
l=len;
return ;
}
}
while(sum[len][l]<k)k-=sum[len][l];
if(k>0) ssss(l,len);
}
int main()
{
int t,l,i,r,max,v;
//位置i的组合数=后方比位置i的值大的个数*(len-i)!
setlct();
scanf("%d",&t);
while(t--)
{
scanf("%d%d",&len,&k);
sum[0][len]=0;
r=len-1; max=0;
for( i=0; i<len; i++)
{
scanf("%d",&a[i]);lct[0][i]=0;
if(max<a[i])max=a[i];
}
if(len==1||k==0)
{
print(0,len-1);printf("\n");
continue;
}
builde(1,max,1);
for( i=len-1; i>=0; i--)
{
lct[0][i]=updata(1,max,1,a[i]);
sum[0][i]=sum[0][i+1];
if(len-i<=9) sum[0][i]+=lct[0][i]*in[len-i-1];
if(lct[0][i]&&len-r<9) r=i;
}
l=0;
v=0;
if(sum[v][l]>=k&&k>0)
{
ssss(l,v);
}
else while(k>0)
{
k-=sum[v][l];
if(len-r>=9)
{
print(l,r);
l=r+1;
r=len;
}
sort(a+l,a+len,cmp);
k--;
if(k==0)
{
print(l,len-1);
l=len;
break;
}
else
{
v=len;
if(sum[v][l]>=k)
{
ssss(l,len);
break;
}
}
}
printf("\n");
}
return 0;
}
Followed by: Post your reply here: |
All Rights Reserved 2003-2013 Ying Fuchen,Xu Pengcheng,Xie Di
Any problem, Please Contact Administrator