题目:
分析:
题目给出了一段序列,要我们还原出原序列。由于原序列是在1n范围内,并且是由1n组成的,所以我们可以先给出一个1n的递增序列List,然后按照一定的规则重新排列,就能得到原序列。而这个排序规则就是根据逆序列来的。一个数a的逆序数表示的是在原序列中,a后面的数中比a小的数的个数。那么反过来,如果给出一个逆序数b,我们只要在List中从小到大数b个数,那么下一个数就是b对应的原来的数。要注意每找一个原来的数后,就要把这个数删除。按照这个思路,可以用数组实现,也可以用链表来做,这里采用的是链表。如果用链表,那么这道题就相当于是:创建一个长度为n的链表,链表的数据依次为从1n,然后根据逆序列,对每一个逆序数b,指针从头开始往右移动b次,输出下一个结点的数据,并删除该节点。这样就可以了。
代码:
#include<iostream>
#include<stdlib.h>
using namespace std;
struct Numlist
{
int data;
Numlist *next;
};
int main()
{
int i,j,n,a[500],out[500];
Numlist *p,*newp,*p1,*head;
head=(Numlist*)malloc(sizeof(Numlist));
head->next=NULL;
p=head;
cin>>n;
for(i=0;i<n;i++)
cin>>a[i];
for(i=0;i<n;i++) //创建一个长度为n的链表,数据依次为1~n
{
newp=(Numlist*)malloc(sizeof(Numlist));
newp->data=i+1;
p->next=newp;
newp->next=NULL;
p=p->next;
}
for(i=0;i<n;i++)
{
p=head;
for(j=0;j<a[i];j++) //指针后移逆序数次
p=p->next;
p1=p->next;
out[i]=p1->data; //记录下一个结点的数据
p->next=p1->next; //删除该节点
delete p1;
}
for(i=0;i<n;i++)
cout<<out[i]<<" ";
return 0;
}