【BZOJ1013】球形空间产生器sphere 高斯消元

第一次见到行末有空格要错的题。。

我真的是以为这题是计算几何才去做的。。

设圆心的n个坐标为x1——xn,不难推广出n维向量的点乘,并注意到球上任意两点的向量与球心和两点中点的向量垂直,固定第一个点列出n个方程求解即可

#include<cstdlib>
#include<cstdio>
#include<iostream>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<vector>
#include<queue>
using namespace std;
int n;
struct P
{
	double a[15];
}A[15],t;
double g[15][15];
void Init()
{
	scanf("%d",&n);
	for(int i=1;i<=n+1;i++)
	{
		for(int j=1;j<=n;j++)
		{
			scanf("%lf",&A[i].a[j]);
		}
	}
	for(int i=2;i<=n+1;i++)
	{
		for(int j=1;j<=n;j++)t.a[j]=(A[1].a[j]+A[i].a[j])/2.0;
		for(int j=1;j<=n;j++)
		{
			g[i-1][j]=A[i].a[j]-A[1].a[j];
			g[i-1][n+1]+=t.a[j]*(A[i].a[j]-A[1].a[j]);
		}
	}
	return ;
}
double fabs(double x)
{
	return x<0 ? -x : x;
}
void Debug()
{
	for(int i=1;i<=n;i++)
	{
		for(int j=1;j<=n+1;j++)
		{
			printf("%.3lf ",g[i][j]);
		}
		printf("\n");
	}
}
void Gauss()
{
	int ni=1,nj=1,k;
	double f;
	
	while(ni<=n && nj<=n )
	{
		k=ni;
		for(int j=ni+1;j<=n;j++)
		{
			if(fabs(g[j][nj])>fabs(g[k][nj]))k=j;
		}
		for(int i=1;i<=n+1;i++)swap(g[k][i],g[ni][i]);
		if(g[ni][nj]!=0)
		{
			for(int i=1;i<=n;i++)if(i!=ni && g[i][nj])
			{
				f=g[i][nj]/g[ni][nj];
				for(int j=1;j<=n+1;j++)g[i][j]-=f*g[ni][j];
			}
			ni++;
		}
		nj++;
	//	Debug();
	}
	for(int i=1;i<=n;i++)
	{
		if(i<n)printf("%.3lf ",g[i][n+1]/g[i][i]);
		else printf("%.3lf",g[i][n+1]/g[i][i]);
	}
	return ;
}
int main()
{
	freopen("in.txt","r",stdin);
	Init();
	Gauss();
	return 0;
}

你可能感兴趣的:(高斯消元)