-
Notifications
You must be signed in to change notification settings - Fork 8
/
findClosestValue.go
84 lines (66 loc) · 1.83 KB
/
findClosestValue.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
package main
import "math"
type BST struct {
Value int
Left *BST
Right *BST
}
func walkTree(tree *BST, closestValueSoFar float64, distanceSoFar float64, target int) int {
if tree == nil {
return int(closestValueSoFar)
}
currentDistance := math.Abs(float64(tree.Value - target))
if currentDistance < distanceSoFar {
closestValueSoFar = float64(tree.Value)
distanceSoFar = currentDistance
}
if target < tree.Value {
return walkTree(tree.Left, closestValueSoFar, distanceSoFar, target)
} else {
return walkTree(tree.Right, closestValueSoFar, distanceSoFar, target)
}
}
func (tree *BST) FindClosestValueV1(target int) int {
if tree == nil {
return -1
}
closestValueSoFar := float64(tree.Value)
distanceSoFar := 1000000.0
return walkTree(tree, closestValueSoFar, distanceSoFar, target)
}
func absdiff(a, b int) int {
if a > b {
return a - b
}
return b - a
}
func (tree *BST) FindClosestValue(target int) int {
return tree.findClosestValue(target, tree.Value)
}
func (tree *BST) findClosestValue(target, closest int) int {
if absdiff(target, closest) > absdiff(target, tree.Value) {
closest = tree.Value
}
if target < tree.Value && tree.Left != nil {
return tree.Left.findClosestValue(target, closest)
} else if target > tree.Value && tree.Right != nil {
return tree.Right.findClosestValue(target, closest)
}
return closest
}
func (tree *BST) findClosestValueV3(target, closest int) int {
currentNode := tree
for currentNode != nil {
if absdiff(target, closest) > absdiff(target, currentNode.Value) {
closest = currentNode.Value
}
if target < currentNode.Value {
currentNode = currentNode.Left
} else if target > currentNode.Value {
currentNode = currentNode.Right
} else {
break
}
}
return closest
}