// Slower C++ solution:
#include<cstdio>

#include<cstring>

#include<algorithm>

#include<cmath>

#include<queue>

using namespace std;



const int MAXN=1005;



int n;

double d[MAXN][MAXN],s[MAXN],t[MAXN],ans=1e18;

bool in[MAXN];

queue<int> q;

pair<int,int> st,ed;

struct node{

    double x,y,r;

}a[MAXN];



double dis(double x1,double y1,double x2,double y2){

    return sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));

}



void work(){

    memset(in,0,sizeof in);

    for(int i=1;i<=n;i++)

        q.push(i),in[i]=1;

    while(!q.empty()){

        int u=q.front(); q.pop(); in[u]=0;

        for(int v=1;v<=n;v++){

            if(u==v||s[u]+d[u][v]>=s[v]) continue;

            s[v]=d[u][v]+s[u];

            if(!in[v]){

                in[v]=1;

                q.push(v);

            }

        }

    }

    memset(in,0,sizeof in);

    for(int i=1;i<=n;i++)

        q.push(i),in[i]=1;

    while(!q.empty()){

        int u=q.front(); q.pop(); in[u]=0;

        for(int v=1;v<=n;v++){

            if(u==v||t[u]+d[u][v]>=t[v]) continue;

            t[v]=d[u][v]+t[u];

            if(!in[v]){

                in[v]=1;

                q.push(v);

            }

        }

    }

    for(int i=1;i<=n;i++) ans=min(ans,s[i]+t[i]);

}



int main(){

    scanf("%d%d%d%d",&st.first,&st.second,&ed.first,&ed.second);

    scanf("%d",&n);

    for(int i=1;i<=n;i++)

        scanf("%lf%lf%lf",&a[i].x,&a[i].y,&a[i].r);

    ans=dis(st.first,st.second,ed.first,ed.second);

    for(int i=1;i<=n;i++) s[i]=max(0.0,dis(st.first,st.second,a[i].x,a[i].y)-a[i].r);

    for(int i=1;i<=n;i++) t[i]=max(0.0,dis(ed.first,ed.second,a[i].x,a[i].y)-a[i].r);

    for(int i=1;i<=n;i++)

        for(int j=1;j<=n;j++){

            if(i==j) continue;

            d[i][j]=max(0.0,dis(a[i].x,a[i].y,a[j].x,a[j].y)-a[i].r-a[j].r);

        }

    work();

    printf("%.10lf",ans);

}


// Faster C++ solution for the same problem (measured speedup: 4.274783124574799x):
#include <cstdio>

#include <cstring>

#include <cmath>

#include <algorithm>

const int MAXN = 1005;

const double eps = 1e-12;





int xs, ys, xt, yt, n;

struct node

{

	int x, y, z;

}p[MAXN];

double f[MAXN][MAXN], dis[MAXN];



double dist(int x, int y, int u, int v)

{

	return sqrt(1.0 * (1ll * (x-u) * (x-u) + 1ll * (y-v) * (y-v)));

}



double calc(int i, int j)

{

	double d = dist(p[i].x, p[i].y, p[j].x, p[j].y);

	if(p[i].z + p[j].z - d < eps) return d - p[i].z - p[j].z;

	return 0;

}



bool vis[MAXN];



int main ()

{

	scanf("%d%d%d%d", &xs, &ys, &xt, &yt);

	scanf("%d", &n); n++;

	for(int i = 1; i < n; i++)

		scanf("%d%d%d", &p[i].x, &p[i].y, &p[i].z);

	p[0].x = xs, p[0].y = ys, p[0].z = 0;

	p[n].x = xt, p[n].y = yt, p[n].z = 0;

	for(int i = 0; i <= n; i++)

		for(int j = i; j <= n; j++)

			f[i][j] = f[j][i] = calc(i, j);

	memset(dis, 127, sizeof dis); dis[0] = 0;

	for(int i = 1; i <= n; i++)

	{

		int k = -1;

		for(int j = 0; j <= n; j++)

			if(!vis[j] && (k == -1 || dis[j] - dis[k] < eps))

				k = j;

		if(k < 0) break;

		vis[k] = 1;

		for(int j = 0; j <= n; j++)

			if(!vis[j] && dis[k] + f[k][j] - dis[j] < eps)

				dis[j] = dis[k] + f[k][j];

	}

	printf("%.10lf\n", dis[n]);

}