Esempio n. 1
0
void nearest(struct kd_node_t *root, struct kd_node_t *nd, int i, int dim,
        struct kd_node_t **best, double *best_dist)
{
    double d, dx, dx2;
 
    if (!root) return;
    d = dist(root, nd, dim);
    dx = root->x[i] - nd->x[i];
    dx2 = dx * dx;
 
    visited ++;
 
    if (!*best || d < *best_dist) {
        *best_dist = d;
        *best = root;
    }
 
    /* if chance of exact match is high */
    if (!*best_dist) return;
 
    if (++i >= dim) i = 0;
 
    nearest(dx > 0 ? root->left : root->right, nd, i, dim, best, best_dist);
    if(dx2 >= *best_dist) return;
    nearest(dx > 0 ? root->right : root->left, nd, i, dim, best, best_dist);
}
Esempio n. 2
0
int FluoDBase::nearest( double E, int s, int e )
// 2 分探索をやった後、最後の詰めが自信ないので最終候補全員比較
{
  if ( ( e - s ) < 2 ) {
    int ss = s - 1;
    int ee = e + 1;
    if ( ss < 0 ) ss = 0;
    if ( ee >= fluos.count() )
      ee = fluos.count() - 1;
    int minp = ss;
    for ( int i = ss; i <= ee; i++ ) {
      if ( fabs( fluos[i].val - E ) < fabs( fluos[minp].val - E ) ) {
	minp = i;
      }
    }
    return minp;
  }

  int np = ( s + e ) / 2.;
  if ( fluos[np].val < E ) {
    return nearest( E, np, e );
  } else {
    return nearest( E, s, np );
  }
}
Esempio n. 3
0
/**
 * recursively finds the nearest node and the distance to the nearest 
 * node in the kd tree
 */
void kdtree::nearest(struct kd_node_t *& root, struct kd_node_t *& nd, int i,
		struct kd_node_t *&best, double &best_dist)
{
	double d, dx, dx2;
 
	if (!root) return;
	d = dist(root, nd);
	dx = root->x[i] - nd->x[i];
	dx2 = dx * dx;

	if (!best || d < best_dist) 
	{
		best_dist = d;
		best = root;
	}
 
	/* if chance of exact match is high */
	if (!best_dist) return;
 
	if (++i >= (int)_dim) i = 0;
 
	nearest(dx > 0 ? root->left : root->right, nd, i, best, best_dist);
	if (dx2 >= best_dist) return;
	nearest(dx > 0 ? root->right : root->left, nd, i, best, best_dist);
}
void nearest(kd_tree* This){
	if (!This||mht_dist(p,This)>=ans) return;
	mini(ans,mht_dist(p,This->x));
	fd=This->split;
	bool gotoright=This->x.p[fd]<p.p[fd];
	nearest(This->c[gotoright]);
	nearest(This->c[!gotoright]);
}
Esempio n. 5
0
 static A0& compute(A0& yi, const A1& inputs, char, boost::mpl::long_<3> const &)
 {
   const child0 & x   =  boost::proto::child_c<0>(inputs);
   const child1 & y   =  boost::proto::child_c<1>(inputs);
   const child2 & xi  =  boost::proto::child_c<2>(inputs);
   yi = nearest(x, y, xi);  return yi;
 }
Esempio n. 6
0
/**
 * wraps the nearest function to work with the defined root node
 */
void kdtree::nearest(struct kd_node_t * node, struct kd_node_t *& best, double & dist )
{
    if ( _root ) 
    {
        nearest (_root , node, 0, best, dist);
    }
}
bool Foam::sampledTriSurfaceMesh::update()
{
    if (!needsUpdate_)
    {
        return false;
    }


    // Find the cells the triangles of the surface are in.
    // Does approximation by looking at the face centres only
    const pointField& fc = surface_.faceCentres();

    meshSearch meshSearcher(mesh(), false);

    const indexedOctree<treeDataPoint>& cellCentreTree =
        meshSearcher.cellCentreTree();


    // Global numbering for cells - only used to uniquely identify local cells.
    globalIndex globalCells(mesh().nCells());
    List<nearInfo> nearest(fc.size());
    forAll(nearest, i)
    {
        nearest[i].first() = GREAT;
        nearest[i].second() = labelMax;
    }
Esempio n. 8
0
void Foam::patchProbes::findElements(const fvMesh& mesh)
{
    (void)mesh.tetBasePtIs();

    const polyBoundaryMesh& bm = mesh.boundaryMesh();

    label patchi = bm.findPatchID(patchName_);

    if (patchi == -1)
    {
        FatalErrorInFunction
            << " Unknown patch name "
            << patchName_ << endl
            << exit(FatalError);
    }

     // All the info for nearest. Construct to miss
    List<mappedPatchBase::nearInfo> nearest(this->size());

    const polyPatch& pp = bm[patchi];

    if (pp.size() > 0)
    {
        labelList bndFaces(pp.size());
        forAll(bndFaces, i)
        {
            bndFaces[i] =  pp.start() + i;
        }
Esempio n. 9
0
labelList triSurfaceSearch::calcNearestTri
(
    const pointField& samples,
    const vector& span
) const
{
    labelList nearest(samples.size());

    const scalar nearestDistSqr = 0.25*magSqr(span);

    pointIndexHit hitInfo;

    forAll(samples, sampleI)
    {
        hitInfo = tree().findNearest(samples[sampleI], nearestDistSqr);

        if (hitInfo.hit())
        {
            nearest[sampleI] = hitInfo.index();
        }
        else
        {
            nearest[sampleI] = -1;
        }
    }
Esempio n. 10
0
    /**
     * Grow the tree in the direction of @state
     *
     * @return the new tree Node (may be nullptr if we hit Obstacles)
     * @param target The point to extend the tree to
     * @param source The Node to connect from.  If source == nullptr, then
     *             the closest tree point is used
     */
    virtual Node<T>* extend(const T& target, Node<T>* source = nullptr) {
        //  if we weren't given a source point, try to find a close node
        if (!source) {
            source = nearest(target, nullptr);
            if (!source) {
                return nullptr;
            }
        }

        //  Get a state that's in the direction of @target from @source.
        //  This should take a step in that direction, but not go all the
        //  way unless the they're really close together.
        T intermediateState;
        if (_isASCEnabled) {
            intermediateState = _stateSpace->intermediateState(
                source->state(), target, stepSize(), maxStepSize());
        } else {
            intermediateState = _stateSpace->intermediateState(
                source->state(), target, stepSize());
        }

        //  Make sure there's actually a direct path from @source to
        //  @intermediateState.  If not, abort
        if (!_stateSpace->transitionValid(source->state(), intermediateState)) {
            return nullptr;
        }

        // Add a node to the tree for this state
        Node<T>* n = new Node<T>(intermediateState, source);
        _nodes.push_back(n);
        return n;
    }
Esempio n. 11
0
void IHSFinder::processEHH(const EHH& ehh, std::size_t line)
{
    double freqs = 0.0;
    double iHS = 0.0;
    freqs = nearest(m_binFactor, ehh.num/(double)m_snpLength);
    if (freqs > 0 && ehh.iHH_a > 0)
    {
        iHS = log(ehh.iHH_d/ehh.iHH_a);
        if (iHS == -std::numeric_limits<double>::infinity() || iHS == std::numeric_limits<double>::infinity())
        {
            ++m_nanResults;
            return;
        }
    } else {
        iHS = NAN;
        return;
    }
    
    if (ehh.num + ehh.numNot != m_snpLength)
        return;
    
    if (freqs > 0 && ehh.iHH_a > 0)
    {
        m_freqmutex.lock();
        
        m_unStandIHSByFreq[freqs].push_back(iHS);
        m_freqmutex.unlock();
    }
    
    m_mutex.lock();
    m_freqsByLine[line] = freqs;
    m_unStandIHSByLine[line] = iHS;
    m_mutex.unlock();
}
Esempio n. 12
0
QVector<Fluo> FluoDBase::nears( double E, double range, double dE )
// 指定エネルギー E の前後 range の範囲に入る元素リスト作成。
// 最初は E に近いもの順にしてたけど、今はエネルギーの小さいもの順
{
  if ( E < 0 ) {
    QVector<Fluo> rv;
    return rv;
  }
  QVector<Fluo> nFluos;

  int p = nearest( E, 0, fluos.count() - 1 );
  int u = p;
  int d = p - 1;

  while ( ( u < fluos.count() )&&( fabs( fluos[u].val - E ) < range ) ) {
    nFluos << fluos[u];
    u++;
  }
  while ( ( d >= 0 )&&( fabs( fluos[d].val - E ) < range ) ) {
    nFluos << fluos[d];
    d--;
  }
  qSort( nFluos.begin(), nFluos.end() );

  nFluos = removeTooNears( nFluos, dE );  // ソート済み

  return nFluos;
}
Esempio n. 13
0
STCalEnum::InterpolationType CalibrationManager::stringToInterpolationEnum(const string &s)
{
  String itype(s);
  itype.upcase();
  const Char *c = itype.c_str();
  String::size_type len = itype.size();
  Regex nearest("^NEAREST(NEIGHBOR)?$");
  Regex linear("^LINEAR$");
  Regex spline("^(C(UBIC)?)?SPLINE$");
  Regex poly("^POLY(NOMIAL)?$");
  if (nearest.match(c, len) != String::npos) {
    return STCalEnum::NearestInterpolation;
  }
  else if (linear.match(c, len) != String::npos) {
    return STCalEnum::LinearInterpolation;
  }
  else if (spline.match(c, len) != String::npos) {
    return STCalEnum::CubicSplineInterpolation;
  }
  else if (poly.match(c, len) != String::npos) {
    return STCalEnum::PolynomialInterpolation;
  }

  os_.origin(LogOrigin("CalibrationManager","stringToInterpolationEnum",WHERE));
  os_ << LogIO::WARN << "Interpolation type " << s << " is not available. Use default interpolation method." << LogIO::POST;
  return STCalEnum::DefaultInterpolation;
}
Esempio n. 14
0
RGBColor RayCast::traceRay(const Ray& a_ray) const
{
    Intersection inter(m_pWorld);
    Intersection nearest(m_pWorld);
    double t;
    double tmin = std::numeric_limits<double>::max();
    
    for (int i = 0; i < m_pWorld->m_objects.size(); ++i)
    {
        if (m_pWorld->m_objects[i]->intersect(a_ray, t, inter) && t < tmin)
        {
            nearest = inter;
            tmin = t;
            
            if (dot(nearest.m_normal, a_ray.m_d) > 0)
            {
                // Inside intersection
                nearest.m_normal = -nearest.m_normal;
            }
        }
    }
    
    if (nearest.m_hit)
    {
        return nearest.m_material->shade(nearest);
    }
    else
    {
        return m_pWorld->m_backgroundColor;
    }
}
Esempio n. 15
0
void
mail_listview::select_nearest(const mail_msg* msg)
{
  QStandardItem* item=nearest(msg, 3);
  if (item) {
    setCurrentIndex(item->index());
  }
}
Esempio n. 16
0
            static std::vector<NearestPhoton>::iterator nearest(std::vector<Photon>::const_iterator begin, std::vector<Photon>::const_iterator end, Segment3f const& bound, Point3f const& position, std::vector<NearestPhoton>::iterator nearestBegin, std::vector<NearestPhoton>::iterator nearestNext, std::vector<NearestPhoton>::iterator nearestEnd) {
                if (begin == end) {
                    return nearestNext;
                }
                
                std::vector<Photon>::const_iterator median = begin + (end - begin) / 2;
                float medianSqrDistance = sqrDistance(median->position, position);

                if (nearestNext == nearestEnd) {
                    if (medianSqrDistance < nearestBegin->sqrDistance) {
                        std::pop_heap(nearestBegin, nearestNext--, SqrDistanceLess());
                        nearestNext->photon = median;
                        nearestNext->sqrDistance = medianSqrDistance;
                        std::push_heap(nearestBegin, ++nearestNext, SqrDistanceLess());
                    }
                } else {
                    nearestNext->photon = median;
                    nearestNext->sqrDistance = medianSqrDistance;
                    std::push_heap(nearestBegin, ++nearestNext, SqrDistanceLess());
                }

                int splitAxis = maxAxis(bound);
                if (position[splitAxis] <= median->position[splitAxis]) {
                    Segment3f belowBound = bound;
                    belowBound.max[splitAxis] = median->position[splitAxis];
                    nearestNext = nearest(begin, median, belowBound, position, nearestBegin, nearestNext, nearestEnd);
                } else {
                    Segment3f aboveBound = bound;
                    aboveBound.min[splitAxis] = median->position[splitAxis];
                    nearestNext = nearest(median + 1, end, aboveBound, position, nearestBegin, nearestNext, nearestEnd);
                }

                if (nearestNext != nearestEnd || sqr(median->position[splitAxis] - position[splitAxis]) < nearestBegin->sqrDistance) {
                    if (position[splitAxis] <= median->position[splitAxis]) {
                        Segment3f aboveBound = bound;
                        aboveBound.min[splitAxis] = median->position[splitAxis];
                        nearestNext = nearest(median + 1, end, aboveBound, position, nearestBegin, nearestNext, nearestEnd);
                    } else {
                        Segment3f belowBound = bound;
                        belowBound.max[splitAxis] = median->position[splitAxis];
                        nearestNext = nearest(begin, median, belowBound, position, nearestBegin, nearestNext, nearestEnd);
                    }
                }
                return nearestNext;
            }
Esempio n. 17
0
 void nearest(Node* r, int x, int y,
              int &mID, LL &md2){
   if (!r || !touch(r, x, y, md2)) return;
   LL d2 = dis2(r->x, r->y, x, y);
   if (d2 < md2 || (d2 == md2 && mID < r->id)) {
     mID = r->id;
     md2 = d2;
   }
   // search order depends on split dim
   if ((r->f == 0 && x < r->x) ||
       (r->f == 1 && y < r->y)) {
     nearest(r->L, x, y, mID, md2);
     nearest(r->R, x, y, mID, md2);
   } else {
     nearest(r->R, x, y, mID, md2);
     nearest(r->L, x, y, mID, md2);
   }
 }
int main(){
	int N,M; read(N),read(M);
	point b[N]; Base=b;
	for (int i=0;i<N;++i) b[i].read();
	fd=kD-1;
	kd_tree *flat=build(b,b+N);
	int t;
	while (M--){
		read(t),read(p.p[0]),read(p.p[1]);
		if (t==1) fd=kD-1,insert(flat);
		else ans=ansinf,nearest(flat),printf("%d\n",ans);
	}
}
int main(int argc, const char* argv[])
{
   const size_t w = 400;
   const size_t h = 400;
   cv::Mat image(h,w,CV_8UC3);
   image = cv::Scalar(0,0,0);
   random_int rd(0,std::min(h,w));



   std::vector< POINT > points;

   POINT center(h/2,w/2);
   POINT::value_type min_d = std::numeric_limits<POINT::value_type>::max();
   size_t my = 0;

   for ( size_t i = 0; i < 10; i++ ) {
      points.push_back( POINT( rd(), rd() ) );

      image.at<cv::Vec3b>(points.back()) = cv::Vec3b(255,255,255);

      POINT::value_type d = distance(points.back().x,points.back().y,center.x,center.y);
      if ( d < min_d ) {
         my = i;
         min_d = d;
      }
   }



   POINT myp(points[my]);

   cv::namedWindow( "Display window", cv::WINDOW_AUTOSIZE );
   cv::circle(image,myp,3,cv::Scalar(0,255,0));


   POINT n;
   std::vector< POINT > r( points );

   while ( !r.empty() ) {
      nearest(myp,points,n,r);
      cv::circle(image,n,3,cv::Scalar(0,255,255));
      cv::line(image,myp,n,cv::Scalar(255,255,0));
      cv::line(image,cv::Point(0,y_at_perpendicular_bisector(myp,n,0)),cv::Point(w,y_at_perpendicular_bisector(myp,n,w)),cv::Scalar(0,0,255));
      points = r;
   }

   cv::imshow( "Display window", image ); 
   cv::waitKey(0);
   return 0;
}
Esempio n. 20
0
Point2D KdTree::nearest(Node* x, const Point2D& p, Point2D& champ, double d, bool HNode) {
	if (x == NULL) return champ;
	if (d < x->rect_.distanceSquaredTo(p)) return champ;

	double distance = x->p_.distanceSquaredTo(p);
	if (distance < d) {
		d = distance;
		champ = x->p_;
	}

	// Decide if vertical or horizontal node
	int cmp;
	if (!HNode) cmp = x->comparebyX(p);
	else        cmp = x->comparebyY(p);

	Point2D rchamp = champ;
	double rd;
	if (cmp < 0) {
		rchamp = nearest(x->lb, p, champ, d, !HNode);
		rd = rchamp.distanceSquaredTo(p);
		if (rd < d) {
			champ = rchamp;
			d = rd;
		}
		champ = nearest(x->rt, p, champ, d, !HNode);
	}
	else { //if (cmp > 0) {
		rchamp = nearest(x->rt, p, champ, d, !HNode);
		rd = rchamp.distanceSquaredTo(p);
		if (rd < d) {
			champ = rchamp;
			d = rd;
		}
		champ = nearest(x->lb, p, champ, d, !HNode);
	}

	return champ;
}
Esempio n. 21
0
cv::Point2i findNNEuclid(const cv::Mat& img, cv::Point2i p) {
  cv::Point2i nearest(0, 0);
  double minDist = std::numeric_limits<double>::max();
  for (int i = 0; i < img.rows/2; i+=4) {
    for (int j = 0; j < img.cols; j+=4) {
      double dist = euclidDistance(img, img, p, cv::Point2i(j, i), 4);
      if (dist < minDist) {
        minDist = dist;
        nearest = cv::Point2i(j, i);
      }
    }
  }
  return nearest;
}
Esempio n. 22
0
 static A0& compute(A0& yi, const A1& inputs, char method, boost::mpl::long_<4> const &)
 {
   const child0 & x   =  boost::proto::child_c<0>(inputs);
   const child1 & y   =  boost::proto::child_c<1>(inputs);
   const child2 & xi  =  boost::proto::child_c<2>(inputs);
   switch (method)
   {
     case 'n' : yi = nearest(x, y, xi);  return yi;
       //          case 's' : yi = spline(x, y, xi);return yi;
       //           case 'c' : yi = cubic(x, y, xi);return yi;
       //           case 'p' : yi = pship(x, y, xi);return yi;
     default  : yi = linear(x, y, xi); return yi;
   }
   return yi;
 }
Esempio n. 23
0
cv::Point2i nearestDiff(const cv::Mat& img1, const cv::Mat& img2, cv::Point2i p) {
  cv::Point2i nearest(0, 0);
  cv::Mat diff(img1.size(), CV_8U);
  double minDist = std::numeric_limits<double>::max();
  for (int i = 0; i < img2.rows; i+=8) {
    for (int j = 0; j < img2.cols; j+=8) {
      double dist = euclidDistance(img1, img2, p, cv::Point2i(j, i), 8);
      if (dist < minDist) {
        minDist = dist;
        nearest = cv::Point2i(j, i);
      }
    }
  }
  return nearest;
}
Esempio n. 24
0
// Retrieve the quntization error
REAL CFCluster::errComp( REAL* data, int sampNum, int dim, REAL* center, int cenNum )
{
	REAL total=0;
	REAL dmin;
	int index;

	for( int n=0; n<sampNum; n++ )
	{
		index = nearest( data+(_int64)n*dim, dim, center, cenNum, dmin );
		total += dmin;
	}
	total /= sampNum;

	return total;
}
Esempio n. 25
0
    static A0& compute(A0& yi, A1& inputs, const char method, boost::mpl::long_<5> const &)
    {
      typedef typename boost::proto::result_of::child_c<A1&,4>::value_type        child4;

      const child0 & x   =  boost::proto::child_c<0>(inputs);
      const child1 & y   =  boost::proto::child_c<1>(inputs);
      const child2 & xi  =  boost::proto::child_c<2>(inputs);
      const child4 & ext =  boost::proto::child_c<4>(inputs);
      switch (method)
      {
        case 'n' : yi = nearest(x, y, xi, ext); return yi;
          //           case 's' : yi = spline(x, y, xi, ext);return yi;
          //           case 'c' : yi = cubic(x, y, xi, ext);return yi;
          //           case 'p' : yi = pship(x, y, xi, ext);return yi;
        default  : yi = linear(x, y, xi, ext); return yi;
      }
    }
Esempio n. 26
0
cv::Point2i findNN(const cv::Mat& avgs, uchar target) {
  cv::Point2i nearest(0, 0);

  uchar val;
  int min_thresh = 256;

  for (int i = 0; i < avgs.rows; i++) {
    for (int j = 0; j < avgs.cols; j++) {
      val = avgs.at<uchar>(i, j);
      if (std::abs(val - target) < min_thresh) {
        min_thresh = std::abs(val - target);
        nearest = cv::Point2i(j, i);
      }
    }
  }
  return nearest;
}
Esempio n. 27
0
        /**
         * Grow the tree in the direction of @state
         *
         * @return the new tree Node (may be nullptr if we hit Obstacles)
         * @param source The Node to connect from.  If source == nullptr, then
         *             the closest tree point is used
         */
        virtual Node<T> *extend(const T &target, Node<T> *source = nullptr) {
            //  if we weren't given a source point, try to find a close node
            if (!source) {
                source = nearest(target);
                if (!source) {
                    return nullptr;
                }
            }

            //  if they're the same point, don't add it to the tree again
            float dist;
            if (_reverse) {
                dist = _stateSpace->distance(target, source->state());
            } else {
                dist = _stateSpace->distance(source->state(), target);
            }
            // FIXME: this distance check should be against a relative, not
            // absolute threshold
            if (dist < 0.0001) {
                return nullptr;
            }

            //  Get a state that's in the direction of @target from @source.
            //  This should take a step in that direction, but not go all the
            //  way unless the they're really close together.
            T intermediateState = _stateSpace->intermediateState(
                source->state(), target, stepSize(), _reverse);

            //  Make sure there's actually a direct path from @source to
            //  @intermediateState.  If not, abort
            bool transitionValid;
            if (_reverse) {
                transitionValid = _stateSpace->transitionValid(
                    intermediateState, source->state());
            } else {
                transitionValid = _stateSpace->transitionValid(
                    source->state(), intermediateState);
            }
            if (!transitionValid) return nullptr;

            //  Add a node to the tree for this state
            Node<T> *n = new Node<T>(intermediateState, source);
            _nodes.push_back(n);
            return n;
        }
Esempio n. 28
0
void trace(Ray &r, Scene &scene) {
	if (r.done) return;
	Intersection nearest(Infinity);
	for (size_t i = 0; i < scene.spheres.size(); i++) {
		Sphere &s = scene.spheres[i];
		Intersection inter = s.intersects(r);
		if (inter.t > 0 && inter.t < nearest.t) {
			nearest = inter;
			nearest.material = &s.material;
		}
	}
	Vector3 nearestDisp = (Vector3)(r.dir*(Number)min(nearest.t, (Number)100));
	if (nearest.t < Infinity) {
		addVectorDir(r.pos, nearestDisp);
		addVectorDir((Vector3) (r.pos + nearestDisp), nearest.normal);
	}
	r.nearest = nearest;
}
Esempio n. 29
0
bool Library::Intersect(FatRay* ray, uint32_t me) {
    assert(_mbvh != nullptr);

    HitRecord nearest(0, 0, numeric_limits<float>::infinity());

    _mbvh->Traverse(ray->slim, &nearest,
     [this, me](uint32_t mesh_index, const SlimRay& mesh_ray, HitRecord* mesh_hit, bool* mesh_suspend) {
        Mesh *mesh = _meshes[mesh_index];
        TraversalState state = mesh->bvh->Traverse(mesh_ray, mesh_hit,
         [me, mesh_index, mesh](uint32_t tri_index, const SlimRay& tri_ray, HitRecord* tri_hit, bool* tri_suspend) {
            float t = numeric_limits<float>::quiet_NaN();
            LocalGeometry local;

            // Transform the ray to object space.
            SlimRay xformed_ray = tri_ray.TransformTo(mesh->xform_inv);

            const Triangle& tri = mesh->faces[tri_index];
            if (tri.Intersect(mesh->vertices, xformed_ray, &t, &local) && t < tri_hit->t) {
                tri_hit->worker = me;
                tri_hit->mesh = mesh_index;
                tri_hit->t = t;
                tri_hit->geom = local;
                return true;
            }

            return false;
        });
        return state.hit;
    });

    if (nearest.worker > 0 && nearest.t < ray->hit.t) {
        ray->hit = nearest;

        // Correct the interpolated normal.
        vec4 n(ray->hit.geom.n, 0.0f);
        ray->hit.geom.n = normalize(
         vec3(_meshes[ray->hit.mesh]->xform_inv_tr * n));

        return true;
    }

    return false;
}
Esempio n. 30
0
VECTOR2I GRID_HELPER::Align( const VECTOR2I& aPoint ) const
{
    const VECTOR2D gridOffset( GetOrigin() );
    const VECTOR2D gridSize( GetGrid() );

    VECTOR2I nearest( KiROUND( ( aPoint.x - gridOffset.x ) / gridSize.x ) * gridSize.x + gridOffset.x,
                      KiROUND( ( aPoint.y - gridOffset.y ) / gridSize.y ) * gridSize.y + gridOffset.y );

    if( !m_auxAxis )
        return nearest;

    if( std::abs( m_auxAxis->x - aPoint.x ) < std::abs( nearest.x - aPoint.x ) )
        nearest.x = m_auxAxis->x;

    if( std::abs( m_auxAxis->y - aPoint.y ) < std::abs( nearest.y - aPoint.y ) )
        nearest.y = m_auxAxis->y;

    return nearest;
}