您的位置:首页 > 其它

[POJ][3285][Point of view in Flatland][模拟退火]

2011-03-09 11:44 330 查看
/*
题目:Point of view in Flatland
题目来源:POJ 3285
题目难度:中等偏难
题目内容或思路:
模拟退火
这题的难点在找到合适的评估函数
做题日期:2011.3.9
*/
#include <cstdio>
#include <cstdlib>
#include <climits>
#include <iostream>
#include <algorithm>
#include <cstring>
#include <string>
#include <queue>
#include <map>
#include <vector>
#include <bitset>
#include <cmath>
#include <set>
#include <utility>
#include <ctime>
#define sqr(x) ((x)*(x))
using namespace std;

const int N = 30, nt = 20, step = 30;
const double inf = 1e100;
const double eps = 1e-3;
const double pi = acos(-1.0);
double delta;

struct cpoint{
double x, y, r;
}cp
, test
;

int dcmp(double x) {
if (x < -eps) return -1; else return x > eps;
}

double dis(cpoint a, cpoint b) {
return sqrt(sqr(a.x - b.x) + sqr(a.y - b.y));
}

void calc(cpoint &p) {
double t[3], ave = 0;
int id = 0;
for (int i = 0; i < 3; ++i) {
t[i] = dis(p, cp[i]) / cp[i].r;
ave += t[i];
}
ave /= 3;
p.r = 0;
for (int i = 0; i < 3; ++i) {
p.r += sqr(t[i] - ave);
}
}

void updata(int id) {
cpoint t;
double angle = rand();
angle -= int(angle / pi / 2) * pi * 2;
t.x = test[id].x + delta * cos(angle);
t.y = test[id].y + delta * sin(angle);
calc(t);
if (t.r < test[id].r)
test[id] = t;
}

bool solve() {
double t = 0, maxx, minx, maxy, miny;
maxx = maxy = -inf;
minx = miny = inf;
for (int i = 0; i < 3; ++i) {
scanf("%lf%lf%lf", &cp[i].x, &cp[i].y, &cp[i].r);
t += cp[i].r;
maxx = max(maxx, cp[i].x);
minx = min(minx, cp[i].x);
maxy = max(maxy, cp[i].y);
miny = min(miny, cp[i].y);
}
if (dcmp(t) == 0) return false;
for (int i = 0; i < nt; ++i) {
test[i].x = minx + (rand() % (int)(maxx * 10 - minx * 10 + 1)) / 10.0;
test[i].y = miny + (rand() % (int)(maxy * 10 - miny * 10 + 1)) / 10.0;
calc(test[i]);
}
delta = max(maxx - minx, maxy - miny);
for (; delta > 1e-6; delta *= 0.9) {
for (int i = 0; i < nt; ++i)
for (int j = 0; j < step; ++j)
updata(i);
}
int res = -1;
for (int i = 0; i < nt; ++i) {
if (dcmp(test[i].r) == 0) {
double u = dis(test[i], cp[0]);
double v = dis(test[res], cp[0]);
if (res == -1 || dcmp(u - v) < 0)
res = i;
}
}
if (res == -1) puts("No solution");
else {
if (dcmp(test[res].x) == 0) test[res].x = 0;
if (dcmp(test[res].y) == 0) test[res].y = 0;
printf("%.2lf %.2lf\n", test[res].x, test[res].y);
}
return true;
}

int main() {
#ifndef ONLINE_JUDGE
freopen("D:\\in.txt", "r", stdin);
#endif
while (solve());
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: