Pagini recente » Cod sursa (job #971748) | Cod sursa (job #1275075) | Cod sursa (job #1483120) | Cod sursa (job #912618) | Cod sursa (job #2320972)
// Guster Andreea 15.01.2019
#include <iostream>
#include <fstream>
#include <vector>
#include <algorithm>
#include <cmath>
#define x first
#define y second
using namespace std;
typedef pair<int, int> Point;
bool cmpY(Point p1, Point p2) {
return p1.y > p2.y;
}
double distance(Point p1, Point p2) {
return sqrt((p1.x - p2.x) * (p1.x -p2.x) + (p1.y - p2.y) * (p1.y - p2.y));
}
double minimum( vector<Point> &array) {
double MIN = 0x3f3f3f3f;// DBL_MAX;
for (unsigned int i = 0; i < array.size() - 1; i++)
for (unsigned int j = i + 1; j < array.size(); j++)
if (distance(array[i], array[j]) < MIN)
MIN = distance(array[i], array[j]);
return MIN;
}
double dividePlane(vector<Point> &Y, vector<Point> &X, int left, int right) { //X[left...right]
double dist;
if (right - left + 1 < 4) {
dist = minimum(X);
}
else {
int counter = 0;
int middle = (right + left) / 2;
vector<Point> Yleft, Yright;
Yleft.resize(middle - left + 1);
Yright.resize(right - middle + 1);
for (int i = left; i <= middle; i++) {
Yleft[counter++] = X[i];
}
counter = 0;
for (int i = middle + 1; i <= right; i++) {
Yright[counter++] = X[i];
}
double distLeft = dividePlane(Yleft, X, left, middle); //X[left ...middle]
double distRight = dividePlane(Yright, X, middle + 1, right); //X[middle+1 ....right]
dist = min(distLeft, distRight);
vector<Point> MiddleStrip; //fasia facuta prin trasarea derptei verticale M de dimensiune 2*dist, pe aceasta fasie pot exista maxim 8 pct
for (unsigned i = 0; i < X.size(); i++) { //vectorul MiddleStrip este vectorul care contine punctele din interiorul fasiei
if ( abs(X[i].x - X[middle].x) < dist) {
MiddleStrip.push_back(X[i]);
}
}
double MIN = 0x3f3f3f3f;//DBL_MAX;
for (unsigned i = 0; i < MiddleStrip.size() - 1; i++) { //vad care punct este cel mai aproape de liniva verticala middle
for (unsigned j = i + 1; j < MiddleStrip.size(); j++) // && (MiddleStrip[j].y - MiddleStrip[i].y < MIN)
if (distance(MiddleStrip[i], MiddleStrip[j]) < MIN)
MIN = distance(MiddleStrip[i], MiddleStrip[j]);
}
dist = min(dist, MIN);
}
return dist;
}
int main() {
ifstream fin("cmap.in");
ofstream fout("cmap.out");
int sizePoints;
vector<Point> Points;
vector<Point> PointsX, PointsY;
fin >> sizePoints;
Points.resize(sizePoints);
PointsX.resize(sizePoints);
PointsY.resize(sizePoints);
//cout << "Cate puncte sunt in plan: " << sizePoints << "\n";
for (int i = 0; i < sizePoints; i++) {
fin >> Points[i].x >> Points[i].y;
PointsX[i] = PointsY[i] = Points[i];
}
fin.close();
/*
cout << "Afiseaza punctele din plan:\n";
for (int i = 0; i < sizePoints; i++) {
cout << Points[i].x << " " << Points[i].y << "\n";
}
*/
sort(PointsX.begin(), PointsX.end()); //ordonez crescator dupa abscisa
sort(PointsY.begin(), PointsY.end(), cmpY); //ordonex descrescator dup ordonata
/**
cout << "Punctele ordonate dupa abscisa:\n";
for (auto point : PointsX)
cout << point.x << " " << point.y << "\n";
cout << "\nPunctele ordonate dupa ordonata:\n";
for (auto point : PointsY)
cout << point.x << " " << point.y << "\n";
cout << "\nCea mai mica distanta intre 2 puncte este: " << dividePlane(PointsY, PointsX, 0, Points.size() - 1) << "\n";*/
fout << dividePlane(PointsY, PointsX, 0, Points.size() - 1);
fout.close();
//system("pause");
return 0;
}