【题目描述】
给定平面上 n 个圆,这些圆之间只有包含和分离两种关系(不存在相切的情况)。
定义两个圆之间的距离是从圆 A 到圆 B 经过的圆弧的最小个数,但是不包括圆 A 和圆 B
的圆弧。两个圆之间的路径不一定只是走直线,还可以存在绕弯的情况。
对于上述情况,从绿色圆到橙色圆的距离是 0,而从红色圆到橙色圆的距离是 1。
给出 q 个询问,每个询问的格式形如 u, v,对于每个询问,都需要回答第 u 个圆到第 v 个圆之间的最短距离。
【输入格式】
第一行一个整数n,表示圆的个数。
接下来n行,每行三个整数xi,yi,ri表示第 i 个圆的圆心与半径。
第 n + 2 行一个整数 q 表示询问的个数。
接下来 q 行,每行两个整数 u, v,表示需要求第 u 个圆到第 v 个圆的最短距离。
【输出格式】
对于每个询问,输出一行一个整数表示答案。
【样例 1 输入】
5
9 -7 4
0 -6 4
-6 10 1
9 8 2
-1 9 8
2
5 3
2 3
【样例 1 输出】
0
1
CODE<代码>
#include <bits/stdc++.h>
#define for1(i,n) for(i=1;i<=(n);i++)
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
const int N=100005;
int n,q,dep[N],f[N][20],cs[N],cp,b[N],si[N],t[N];
struct nd{
int x,y,r,id;
bool operator<(const nd &n1)const{
return y-r<n1.y-n1.r;
}
bool p(nd &n1){
return r+y<n1.y-n1.r;
}
bool dr(nd &n1){
ll dy=(ll)y-n1.y+n1.r,dx=x-n1.x;
return dx>=0||(ull)((ll)dx*dx)+(ull)(dy*dy)<(ll)r*r;
}
bool d(nd &n1){
ll dy=(ll)y-n1.y+n1.r,dx=x-n1.x;
return (ull)((ll)dx*dx)+