Darts 题解
附原题:
题目描述
考虑一个扔飞镖的游戏。板子由十个环组成,半径分别为20, 40, 60, 80, 100, 120, 140, 160, 180和200(单位:mm),均以原点为中心。每次投掷的得分取决于飞镖所击中的位置。如果包含飞镖的最小环(可以在圆上)的半径是20 * (11 - p),则得分是p。不在最外环以内的点不得分。你的任务是计算n次投掷之后的得分。
输入
第一行一个正整数T,表示有T组数据。
每组数据第一行一个正整数n,表示有n次投掷,1 <= n <= 10^6。
接下来n行,每行两个整数x和y,表示一次投掷击中的位置为(x, y),-200 <= x, y <= 200。
输出
对于每组数据输出一行,即n次投掷得分的总和。
样例输入
1
5
32 -39
71 89
-60 80
0 0
196 89
样例输出
29
首先来看一看这一题,可以说是一道模拟题了,但是先给大家灌输一下勾股定理,在来做一下这一道题目。勾股定理
其实,就是a²+b²=c²了,首先写下一个最基础的步骤:获得这个点到圆心的距离。
double gs(int a,int b){
a=abs(a); b=abs(b);
double x,y;
x=a*a; y=b*b;
return sqrt(x+y);
}
但是,有以下几点需要注意:
1.记住,输入的可能是负数,所以abs不可少
2.记住,注意sqrt是浮点数
3.记住,不要写太长的表达式,自己看都不方便
4.记住,类型以及局部变量和全局变量的改变
要知道,模拟的精髓是寄存器优化和细节
接下来是关键部分 gc(得到这个距离的得分)
这个是我的代码 (简单好理解的O1算法)
int gc(double s){
if(200<s) return 0;
if(180<s&&s<=200) return 1;
if(160<s&&s<=180) return 2;
if(140<s&&s<=160) return 3;
if(120<s&&s<=140) return 4;
if(100<s&&s<=120) return 5;
if(80<s&&s<=100) return 6;
if(60<s&&s<=80) return 7;
if(40<s&&s<=60) return 8;
if(20<s&&s<=40) return 9;
if(s<=20) return 10;
}
还是要注意这个double
最后注意多组测试数组,要把ans清零。
其他就没有什么了,但是细节细节细节(重要的事情说三遍)
最后,献上AC代码:
#include<cstdio>
#include<cmath>
using namespace std;
int T;
int a,b,sum,n;
double gs(int a,int b){
a=abs(a); b=abs(b);
double x,y;
x=a*a; y=b*b;
return sqrt(x+y);
}
int gc(double s){
if(200<s) return 0;
if(180<s&&s<=200) return 1;
if(160<s&&s<=180) return 2;
if(140<s&&s<=160) return 3;
if(120<s&&s<=140) return 4;
if(100<s&&s<=120) return 5;
if(80<s&&s<=100) return 6;
if(60<s&&s<=80) return 7;
if(40<s&&s<=60) return 8;
if(20<s&&s<=40) return 9;
if(s<=20) return 10;
}
int main(){
scanf("%d",&T);
while(T--){
sum=0;
scanf("%d",&n);
for(int i=1;i<=n;i++){
scanf("%d%d",&a,&b);
double k=gs(a,b);
sum+=gc(k);
}
printf("%d\n",sum);
}
return 0;
}