题目链接: A Leapfrog in the Array
题意:给出1~n的n个数,从小到大每隔一个位置放一个数。现在从大到小把数往前移动,每次把最右边的数移动最靠右边的空格处直到n个数都在前n个位置。
题解:从数据的大小就可以看出这题一定是推公式的题,那么假设现在一个数刚刚移动到了x位置,那么这个数之前一定有x/2个数没有移动过,所有这个数后面就有n-x/2个数(这里包括x本身)。所以x在移动之前的位置就是x+(n-x/2)。所以一直将所要求的x 按 x = x+(n-x/2)这个公式一直向上求直到x为奇数为止就是最初的位置。
1 #include<bits/stdc++.h> 2 using namespace std; 3 const int MAX_N = 2e5+9; 4 const int INF = 1e9+9; 5 int N,M,T,S; 6 long long n,q; 7 int main(){ 8 while(cin>>n>>q){ 9 long long t = 2*n-1; 10 long long p = 1; 11 while(t > p){ 12 t -= p; 13 p *= 2; 14 } 15 //cout<<"!!!!!"<<endl; 16 for(int i=0;i<q;i++){ 17 long long x; 18 scanf("%lld",&x); 19 if((x+1)%2 == 0){ 20 cout<<(x+1)/2<<endl; 21 } 22 else{ 23 while(!(x&1)){ 24 x += n - x/2; 25 } 26 cout<<x/2+1<<endl; 27 } 28 } 29 } 30 return 0; 31 }