using System; using System.Collections; namespace KDTree { // Token: 0x02000008 RID: 8 public class NearestNeighbour : IEnumerator { // Token: 0x06000037 RID: 55 RVA: 0x00003360 File Offset: 0x00001560 public NearestNeighbour(KDNode pRoot, double[] tSearchPoint, DistanceFunctions kDistance, int iMaxPoints, double fThreshold) { if (tSearchPoint.Length != pRoot.iDimensions) { throw new Exception("Dimensionality of search point and kd-tree are not the same."); } this.tSearchPoint = new double[tSearchPoint.Length]; Array.Copy(tSearchPoint, this.tSearchPoint, tSearchPoint.Length); this.iPointsRemaining = Math.Min(iMaxPoints, pRoot.Size); this.fThreshold = fThreshold; this.kDistanceFunction = kDistance; this.pRoot = pRoot; this.iMaxPointsReturned = iMaxPoints; this._CurrentDistance = -1.0; this.pEvaluated = new IntervalHeap(); this.pPending = new MinHeap>(); this.pPending.Insert(0.0, pRoot); } // Token: 0x06000038 RID: 56 RVA: 0x00003444 File Offset: 0x00001644 public bool MoveNext() { bool flag; if (this.iPointsRemaining == 0) { this._Current = default(T); flag = false; } else { while (this.pPending.Size > 0 && (this.pEvaluated.Size == 0 || this.pPending.MinKey < this.pEvaluated.MinKey)) { KDNode kdnode = this.pPending.Min; this.pPending.RemoveMin(); while (!kdnode.IsLeaf) { KDNode kdnode2; if (this.tSearchPoint[kdnode.iSplitDimension] > kdnode.fSplitValue) { kdnode2 = kdnode.pLeft; kdnode = kdnode.pRight; } else { kdnode2 = kdnode.pRight; kdnode = kdnode.pLeft; } double num = this.kDistanceFunction.DistanceToRectangle(this.tSearchPoint, kdnode2.tMinBound, kdnode2.tMaxBound); if (this.fThreshold < 0.0 || num <= this.fThreshold) { if (this.pEvaluated.Size < this.iPointsRemaining || num <= this.pEvaluated.MaxKey) { this.pPending.Insert(num, kdnode2); } } } if (kdnode.bSinglePoint) { double num = this.kDistanceFunction.Distance(kdnode.tPoints[0], this.tSearchPoint); if (this.fThreshold < 0.0 || num < this.fThreshold) { if (this.pEvaluated.Size < this.iPointsRemaining || num <= this.pEvaluated.MaxKey) { for (int i = 0; i < kdnode.Size; i++) { if (this.pEvaluated.Size == this.iPointsRemaining) { this.pEvaluated.ReplaceMax(num, kdnode.tData[i]); } else { this.pEvaluated.Insert(num, kdnode.tData[i]); } } } } } else { for (int i = 0; i < kdnode.Size; i++) { double num = this.kDistanceFunction.Distance(kdnode.tPoints[i], this.tSearchPoint); if (this.fThreshold < 0.0 || num < this.fThreshold) { if (this.pEvaluated.Size < this.iPointsRemaining) { this.pEvaluated.Insert(num, kdnode.tData[i]); } else if (num < this.pEvaluated.MaxKey) { this.pEvaluated.ReplaceMax(num, kdnode.tData[i]); } } } } } if (this.pEvaluated.Size == 0) { flag = false; } else { this.iPointsRemaining--; this._CurrentDistance = this.pEvaluated.MinKey; this._Current = this.pEvaluated.Min; this.pEvaluated.RemoveMin(); flag = true; } } return flag; } // Token: 0x06000039 RID: 57 RVA: 0x000037D4 File Offset: 0x000019D4 public void Reset() { this.iPointsRemaining = Math.Min(this.iMaxPointsReturned, this.pRoot.Size); this._CurrentDistance = -1.0; this.pEvaluated = new IntervalHeap(); this.pPending = new MinHeap>(); this.pPending.Insert(0.0, this.pRoot); } // Token: 0x1700000D RID: 13 // (get) Token: 0x0600003A RID: 58 RVA: 0x00003840 File Offset: 0x00001A40 object IEnumerator.Current { get { return this._Current; } } // Token: 0x1700000E RID: 14 // (get) Token: 0x0600003B RID: 59 RVA: 0x00003860 File Offset: 0x00001A60 public double CurrentDistance { get { return this._CurrentDistance; } } // Token: 0x1700000F RID: 15 // (get) Token: 0x0600003C RID: 60 RVA: 0x00003878 File Offset: 0x00001A78 public T Current { get { return this._Current; } } // Token: 0x04000017 RID: 23 private double[] tSearchPoint; // Token: 0x04000018 RID: 24 private DistanceFunctions kDistanceFunction; // Token: 0x04000019 RID: 25 private MinHeap> pPending; // Token: 0x0400001A RID: 26 private IntervalHeap pEvaluated; // Token: 0x0400001B RID: 27 private KDNode pRoot = null; // Token: 0x0400001C RID: 28 private int iMaxPointsReturned = 0; // Token: 0x0400001D RID: 29 private int iPointsRemaining; // Token: 0x0400001E RID: 30 private double fThreshold; // Token: 0x0400001F RID: 31 private double _CurrentDistance = -1.0; // Token: 0x04000020 RID: 32 private T _Current = default(T); } }