Exemplo n.º 1
0
static FlatGeoPoint
SegmentNearestPoint(const SearchPointVector& spv,
                      const SearchPointVector::const_iterator i1,
                      const FlatGeoPoint &p3)
{
  if (i1+1 == spv.end()) {
    return NearestPoint(i1->get_flatLocation(),
                         spv.begin()->get_flatLocation(),
                         p3);
  } else {
    return NearestPoint(i1->get_flatLocation(),
                         (i1+1)->get_flatLocation(),
                         p3);
  }
}
Exemplo n.º 2
0
Point CCurve::NearestPoint(const CCurve& c, double *d)const
{
	double best_dist = 0.0;
	Point best_point = Point(0, 0);
	bool best_point_valid = false;
	Point prev_p = Point(0, 0);
	bool prev_p_valid = false;
	bool first_span = true;
	for(std::list<CVertex>::const_iterator It = c.m_vertices.begin(); It != c.m_vertices.end(); It++)
	{
		const CVertex& vertex = *It;
		if(prev_p_valid)
		{
			double dist;
			Point near_point = NearestPoint(Span(prev_p, vertex, first_span), &dist);
			first_span = false;
			if(!best_point_valid || dist < best_dist)
			{
				best_dist = dist;
				best_point = near_point;
				best_point_valid = true;
			}
		}
		prev_p = vertex.m_p;
		prev_p_valid = true;
	}
	if(d)*d = best_dist;
	return best_point;
}
Exemplo n.º 3
0
Point Span::NearestPoint(const Span& p, double *d)const
{
	double best_dist;
	Point best_point = this->NearestPointToSpan(p, best_dist);

	// try the other way round too
	double best_dist2;
	Point best_point2 = p.NearestPointToSpan(*this, best_dist2);
	if(best_dist2 < best_dist)
	{
		best_point = NearestPoint(best_point2);
		best_dist = best_dist2;
	}

	if(d)*d = best_dist;
	return best_point;
}
Exemplo n.º 4
0
		bool Line::hit(const Line& ls) const {
			auto fn = [](float f){return f;};
			Vec3x2 res = NearestPoint(*this, ls, fn, fn);
			return res.first.distance(res.second) <= Point::NEAR_THRESHOLD;
		}
Exemplo n.º 5
0
		bool Line::hit(const Vec3& p) const {
			Vec3 cp = NearestPoint(*this, p, [](float f){return f;});
			return p.distance(cp) <= Point::NEAR_THRESHOLD;
		}
Exemplo n.º 6
0
		Vec3 Line::nearest(const Vec3& p) const {
			return NearestPoint(*this, p, [](float f){ return f; });
		}
Exemplo n.º 7
0
		Vec3x2 Line::nearestPoint(const Line& s) const {
			auto fn = [](float f) { return f; };
			return NearestPoint(*this, s, fn, fn);
		}
Exemplo n.º 8
0
bool Span::On(const Point& p, double* t)const
{
	if(p != NearestPoint(p))return false;
	if(t)*t = Parameter(p);
	return true;
}
 std::vector<City> solve(const std::vector<Point>& points) override {
     std::set<City> outTourCities;
     for (size_t i = 0; i < points.size(); i++) {
         outTourCities.insert(i);
     }
     
     std::vector<Edge> edges;
     std::vector<City> startingTour = this->startingTour(points);
     for (Index i = 0; i < startingTour.size(); i++) {
         edges.push_back(Edge(startingTour[i], startingTour[(i+1)%startingTour.size()]));
         outTourCities.erase(startingTour[i]);
     }
     
     std::vector<Record> outTour;
     for (City c : outTourCities) {
         City c_in = *NearestPoint(points, startingTour.begin(), startingTour.end(), points[c]);
         outTour.push_back(Record(c, c_in, points[c].Distance(points[c_in])));
     }
     
     size_t i = startingTour.size();
     while (i < points.size()) {
         auto it = max_element(outTour.begin(), outTour.end());
         Record r = *it;
         outTour.erase(it);
    
         typedef std::vector<Edge>::iterator EdgeIt; 
         
         EdgeIt es[2];
         bool b = 0;
         for (auto e_it = edges.begin(); e_it != edges.end(); e_it++) {
             if (e_it->hasCity(r.nearestInTourCity)) { 
                 es[b] = e_it;
                 b = !b;
             }
         }
         assert(b==0);
         EdgeIt removingEdge = min(es[0], es[1], [&](const EdgeIt& e_0, const EdgeIt& e_1) {
             auto &ps = points;
             return -ps[e_0->at(0)].Distance(ps[e_0->at(1)]) 
                    +ps[e_0->otherCity(r.nearestInTourCity)].Distance(ps[r.outTourCity]) <  
             
                    -ps[e_1->at(0)].Distance(ps[e_1->at(1)]) 
                    +ps[e_1->otherCity(r.nearestInTourCity)].Distance(ps[r.outTourCity]);
         });
         
         City c = removingEdge->otherCity(r.nearestInTourCity);
         edges.erase(removingEdge);
         
         edges.push_back(Edge(c, r.outTourCity));
         edges.push_back(Edge(r.nearestInTourCity, r.outTourCity));
         
         for (Record& out_r : outTour) {
             double d = points[r.outTourCity].Distance(points[out_r.outTourCity]);
             if (out_r.distance > d) {
                 out_r.nearestInTourCity = r.outTourCity;
                 out_r.distance = d;
             }
         }
         
         i++;
     }
     
     return edgesToTour(edges);
 }