@@ -11,6 +11,8 @@ import (
1111)
1212
1313// DimError represents a failure due to mismatched dimensions.
14+ //
15+ // 表示由于维度不匹配导致的失败。
1416type DimError struct {
1517 Expected int
1618 Actual int
@@ -22,46 +24,60 @@ func (err DimError) Error() string {
2224
2325// DistError is an improper distance measurement. It implements the error
2426// and is generated when a distance-related assertion fails.
27+ //
28+ // 表示不正确的距离测量。它实现了 `error` 接口,并在距离相关的断言失败时生成。
2529type DistError float32
2630
2731func (err DistError ) Error () string {
2832 return "rtreego: improper distance"
2933}
3034
3135// Point represents a point in n-dimensional Euclidean space.
36+ //
37+ // 表示 n 维欧几里得空间中的一个点。
3238type Point []float32
3339
40+ func (p Point ) Copy () Point {
41+ result := make (Point , len (p ))
42+ copy (result , p )
43+ return result
44+ }
45+
3446// Dist computes the Euclidean distance between two points p and q.
47+ //
48+ // 计算 p 和 q 两点之间的欧几里得距离。就是两点间 每个维度上的差值平方和的平方根
3549func (p Point ) dist (q Point ) float32 {
3650 if len (p ) != len (q ) {
3751 panic (DimError {len (p ), len (q )})
3852 }
39- sum := 0.0
53+ sum := float32 ( 0.0 )
4054 for i := range p {
4155 dx := p [i ] - q [i ]
42- sum += float64 ( dx * dx )
56+ sum += dx * dx
4357 }
44- return float32 (math .Sqrt (sum ))
58+ return float32 (math .Sqrt (float64 ( sum ) ))
4559}
4660
4761// minDist computes the square of the distance from a point to a rectangle.
4862// If the point is contained in the rectangle then the distance is zero.
4963//
5064// Implemented per Definition 2 of "Nearest Neighbor Queries" by
5165// N. Roussopoulos, S. Kelley and F. Vincent, ACM SIGMOD, pages 71-79, 1995.
52- func (p Point ) minDist (r * Rect ) float32 {
66+ //
67+ // 计算从一个点到一个矩形的距离的平方。如果该点包含在矩形内,则距离为零。
68+ func (p Point ) minDist (r Rect ) float64 {
5369 if len (p ) != len (r .p ) {
5470 panic (DimError {len (p ), len (r .p )})
5571 }
5672
57- sum := float32 ( 0.0 )
73+ sum := 0.0
5874 for i , pi := range p {
5975 if pi < r .p [i ] {
6076 d := pi - r .p [i ]
61- sum += d * d
77+ sum += float64 ( d ) * float64 ( d )
6278 } else if pi > r .q [i ] {
6379 d := pi - r .q [i ]
64- sum += d * d
80+ sum += float64 ( d ) * float64 ( d )
6581 } else {
6682 sum += 0
6783 }
@@ -75,7 +91,9 @@ func (p Point) minDist(r *Rect) float32 {
7591//
7692// Implemented per Definition 4 of "Nearest Neighbor Queries" by
7793// N. Roussopoulos, S. Kelley and F. Vincent, ACM SIGMOD, pages 71-79, 1995.
78- func (p Point ) minMaxDist (r * Rect ) float32 {
94+ //
95+ // 计算从`p`到`r`上各点的最大距离中的最小值。如果`r`是某些几何对象的边界框,那么在`r`中至少有一个对象位于`p`的minMaxDist(p, r)范围内
96+ func (p Point ) minMaxDist (r Rect ) float64 {
7997 if len (p ) != len (r .p ) {
8098 panic (DimError {len (p ), len (r .p )})
8199 }
@@ -101,18 +119,18 @@ func (p Point) minMaxDist(r *Rect) float32 {
101119 // This formula can be computed in linear time by precomputing
102120 // S = sum{1<=i<=n}(|pi - rMi|^2).
103121
104- S := float32 ( 0.0 )
122+ S := 0.0
105123 for i := range p {
106124 d := p [i ] - rM (i )
107- S += d * d
125+ S += float64 ( d ) * float64 ( d )
108126 }
109127
110128 // Compute MinMaxDist using the precomputed S.
111- min := float32 ( math .MaxFloat32 )
129+ min := math .MaxFloat64
112130 for k := range p {
113131 d1 := p [k ] - rM (k )
114132 d2 := p [k ] - rm (k )
115- d := S - d1 * d1 + d2 * d2
133+ d := S - float64 ( d1 ) * float64 ( d1 ) + float64 ( d2 ) * float64 ( d2 )
116134 if d < min {
117135 min = d
118136 }
@@ -128,17 +146,19 @@ type Rect struct {
128146}
129147
130148// PointCoord returns the coordinate of the point of the rectangle at i
131- func (r * Rect ) PointCoord (i int ) float32 {
149+ //
150+ // 返回矩形在索引 i 处的坐标。
151+ func (r Rect ) PointCoord (i int ) float32 {
132152 return r .p [i ]
133153}
134154
135155// LengthsCoord returns the coordinate of the lengths of the rectangle at i
136- func (r * Rect ) LengthsCoord (i int ) float32 {
156+ func (r Rect ) LengthsCoord (i int ) float32 {
137157 return r .q [i ] - r .p [i ]
138158}
139159
140160// Equal returns true if the two rectangles are equal
141- func (r * Rect ) Equal (other * Rect ) bool {
161+ func (r Rect ) Equal (other Rect ) bool {
142162 for i , e := range r .p {
143163 if e != other .p [i ] {
144164 return false
@@ -152,7 +172,7 @@ func (r *Rect) Equal(other *Rect) bool {
152172 return true
153173}
154174
155- func (r * Rect ) String () string {
175+ func (r Rect ) String () string {
156176 s := make ([]string , len (r .p ))
157177 for i , a := range r .p {
158178 b := r .q [i ]
@@ -164,8 +184,7 @@ func (r *Rect) String() string {
164184// NewRect constructs and returns a pointer to a Rect given a corner point and
165185// the lengths of each dimension. The point p should be the most-negative point
166186// on the rectangle (in every dimension) and every length should be positive.
167- func NewRect (p Point , lengths []float32 ) (r * Rect , err error ) {
168- r = new (Rect )
187+ func NewRect (p Point , lengths []float32 ) (r Rect , err error ) {
169188 r .p = p
170189 if len (p ) != len (lengths ) {
171190 err = & DimError {len (p ), len (lengths )}
@@ -183,26 +202,32 @@ func NewRect(p Point, lengths []float32) (r *Rect, err error) {
183202}
184203
185204// NewRectFromPoints constructs and returns a pointer to a Rect given a corner points.
186- func NewRectFromPoints (minPoint , maxPoint Point ) (r * Rect , err error ) {
205+ func NewRectFromPoints (minPoint , maxPoint Point ) (r Rect , err error ) {
187206 if len (minPoint ) != len (maxPoint ) {
188207 err = & DimError {len (minPoint ), len (maxPoint )}
189208 return
190209 }
191210
192- //checking that min and max points is swapping
211+ // check that min and max point coordinates require swapping
212+ copied := false
193213 for i , p := range minPoint {
194214 if minPoint [i ] > maxPoint [i ] {
215+ if ! copied {
216+ minPoint = minPoint .Copy ()
217+ maxPoint = maxPoint .Copy ()
218+ copied = true
219+ }
195220 minPoint [i ] = maxPoint [i ]
196221 maxPoint [i ] = p
197222 }
198223 }
199224
200- r = & Rect {p : minPoint , q : maxPoint }
225+ r = Rect {p : minPoint , q : maxPoint }
201226 return
202227}
203228
204229// Size computes the measure of a rectangle (the product of its side lengths).
205- func (r * Rect ) Size () float32 {
230+ func (r Rect ) Size () float32 {
206231 size := float32 (1.0 )
207232 for i , a := range r .p {
208233 b := r .q [i ]
@@ -212,7 +237,7 @@ func (r *Rect) Size() float32 {
212237}
213238
214239// margin computes the sum of the edge lengths of a rectangle.
215- func (r * Rect ) margin () float32 {
240+ func (r Rect ) margin () float32 {
216241 // The number of edges in an n-dimensional rectangle is n * 2^(n-1)
217242 // (http://en.wikipedia.org/wiki/Hypercube_graph). Thus the number
218243 // of edges of length (ai - bi), where the rectangle is determined
@@ -230,7 +255,7 @@ func (r *Rect) margin() float32 {
230255}
231256
232257// containsPoint tests whether p is located inside or on the boundary of r.
233- func (r * Rect ) containsPoint (p Point ) bool {
258+ func (r Rect ) containsPoint (p Point ) bool {
234259 if len (p ) != len (r .p ) {
235260 panic (DimError {len (r .p ), len (p )})
236261 }
@@ -247,7 +272,7 @@ func (r *Rect) containsPoint(p Point) bool {
247272}
248273
249274// containsRect tests whether r2 is is located inside r1.
250- func (r * Rect ) containsRect (r2 * Rect ) bool {
275+ func (r Rect ) containsRect (r2 Rect ) bool {
251276 if len (r .p ) != len (r2 .p ) {
252277 panic (DimError {len (r .p ), len (r2 .p )})
253278 }
@@ -257,6 +282,7 @@ func (r *Rect) containsRect(r2 *Rect) bool {
257282 // enforced by constructor: a1 <= b1 and a2 <= b2.
258283 // so containment holds if and only if a1 <= a2 <= b2 <= b1
259284 // for every dimension.
285+ // float32精度不够高,精确到第六位就行了
260286 if a1 - a2 > 0.000001 || b2 - b1 > 0.000001 {
261287 return false
262288 }
@@ -267,7 +293,7 @@ func (r *Rect) containsRect(r2 *Rect) bool {
267293
268294// intersect computes the intersection of two rectangles. If no intersection
269295// exists, the intersection is nil.
270- func intersect (r1 , r2 * Rect ) bool {
296+ func intersect (r1 , r2 Rect ) bool {
271297 dim := len (r1 .p )
272298 if len (r2 .p ) != dim {
273299 panic (DimError {dim , len (r2 .p )})
@@ -312,19 +338,18 @@ func intersect(r1, r2 *Rect) bool {
312338}
313339
314340// ToRect constructs a rectangle containing p with side lengths 2*tol.
315- func (p Point ) ToRect (tol float32 ) * Rect {
341+ func (p Point ) ToRect (tol float32 ) Rect {
316342 dim := len (p )
317343 a , b := make ([]float32 , dim ), make ([]float32 , dim )
318344 for i := range p {
319345 a [i ] = p [i ] - tol
320346 b [i ] = p [i ] + tol
321347 }
322- return & Rect {a , b }
348+ return Rect {a , b }
323349}
324350
325351// boundingBox constructs the smallest rectangle containing both r1 and r2.
326- func boundingBox (r1 , r2 * Rect ) (bb * Rect ) {
327- bb = new (Rect )
352+ func boundingBox (r1 , r2 Rect ) (bb Rect ) {
328353 dim := len (r1 .p )
329354 bb .p = make ([]float32 , dim )
330355 bb .q = make ([]float32 , dim )
@@ -345,16 +370,3 @@ func boundingBox(r1, r2 *Rect) (bb *Rect) {
345370 }
346371 return
347372}
348-
349- // boundingBoxN constructs the smallest rectangle containing all of r...
350- func boundingBoxN (rects ... * Rect ) (bb * Rect ) {
351- if len (rects ) == 1 {
352- bb = rects [0 ]
353- return
354- }
355- bb = boundingBox (rects [0 ], rects [1 ])
356- for _ , rect := range rects [2 :] {
357- bb = boundingBox (bb , rect )
358- }
359- return
360- }
0 commit comments