PTA开军舰前の体能训练

书接上回,四年级学生选出了有资格开军舰的一年级学生后,自然要对他们进行体能训练了hhhhhhhh

训练是在一片无限大的操场上进行的,操场是一片长与宽无限大的正方形,而操场又可以分成若干个长度为单位长度的正方形。这些正方形上都标有序号,标号方式如下图示:

而一年级学生且按照如下的规则移动:

  • 如果第i秒在标号为x的格子处,则第i+1秒在标号为i+1的格子处。

  • 第一秒的时候一年级的学生在标号为1的格子处。

经过很久很久以后,四年级学生已经找不到这些学生的方位了。现在请聪明的你来帮他们查询一下吧。

他们想知道:经过t秒后,一年级学生在何处和已经知道一年级学生在第r行和第c列时,距离开始已经过了多少秒了。

输入格式:

输入文件的第一行将给出一个数t(1≤t≤105),为聪明的你要处理的查询数。

输入文件的第二行开始直到第t+1行将按如下格式读入查询:

  • 1 x y:表示查询的学生此时位于第x行第y列(1≤x,y≤108)

  • 2 t:表示查询的学生此时恰好在第t秒时(1≤t≤1016)

    输出格式:

针对输入文件,你的输出应该有t行。其中第i(1≤i≤t)为针对第i条查询的回答。即:

如果你的查询为1 x y,则你应该回答当一年级学生在第x行第y列时的时刻,输出一个数t即可。

如果你的查询为2 t,则你应该回答在t秒时一年级学生应该在第几行第几列。应输出两个数x y,代表在第x行第y列。

样例1

样例输入

5
1 1 1
1 1 2
1 1 3
1 2 1
1 2 2

样例输出

1
2
9
4
3

样例2

样例输入

5
2 1
2 2
2 3
2 4
2 5

样例输出

1 1
1 2
2 2
2 1
3 1

 没什么可以说的,就是一个模拟题。加油!多打题,有思路就能很快过了。

AC代码:

#include<bits/stdc++.h>
using namespace std;

long long t,k,n,m,x,y,z,sum;

int main(){
	cin >> t;
	while(t--){
		cin >> n;
		if(n==1){
			sum=0;
			cin >> x >> y;
			if(x>y){
				if(x%2==1){
					sum=(x-1)*(x-1);
					sum+=y; 
				}else{
					sum=x*x;
					sum=sum-y+1;
				}
			}else{
				if(y%2==1){
					sum=y*y;
					sum=sum-x+1;
				}else{
					sum=(y-1)*(y-1);
					sum+=x;
				}
			}
			cout << sum << endl;
		}else{
			cin >> z;
			long long i=sqrt(z);
			if(z==i*i){
				if(z%2==1){
					y=i;x=1;
				}else{
					x=i;y=1;
				}
			}else{
				i=i+1;
				if(i%2==1){
					if(z<=i*i-i+1){
						x=i;
						y=z-(i-1)*(i-1);
					}else{
						y=i;
						x=i*i-z+1;
					}
				}else{
					if(z<=i*i-i+1){
						y=i;
						x=z-(i-1)*(i-1);
					}else{
						x=i;
						y=i*i-z+1;
					}
				}
			}
			cout << x << " " << y << endl;
		}
	} 
	return 0;
}

更新的AC代码: 

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
#define endl "\n"

void solve(){
	ll n;
	cin >> n;
	for(ll i = 0 ; i < n ; i ++){
		ll x,y,z;
		cin >> z;
		if(z == 1){
			cin >> x >> y;
			ll mx=max(x,y),mn=min(x,y);
			if(y == mx && y%2 == 1)cout << y*y-x+1 << endl;
			else if(y == mx && y%2 == 0)cout << (y-1)*(y-1)+x << endl;
			else if(x == mx && x%2 == 1)cout << (x-1)*(x-1)+y << endl;
			else if(x == mx && x%2 == 0)cout << x*x-y+1 << endl;
		}else{
			cin >> z;
			ll x = sqrt(z),y=z-x*x;
			if(y == 0){
				x%2 == 1 ? cout << "1 " << x << endl : cout << x << " 1" << endl;
			}else if(z == x*x+1){
				x++;
				x%2 == 0 ? cout << y << " " << x << endl : cout << x << " " << y << endl;
			}else if(y > x){
				y=(x+1)*(x+1)-x*x-y+1;
				x++;
				x%2 == 0 ? cout << x << " " << y << endl : cout << y << " " << x << endl;
			}else{
				x++;
				x%2 == 0 ? cout << y << " " << x << endl : cout << x << " " << y << endl;
			}
		}
	}
	return;
}

int main(){
	ll t=1;//cin >> t;
	while(t --)solve();
	return 0;
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值