func main() {
points := [][]int{{2, 2}, {2, 3}, {2, 7}, {6, 6}, {5, 2}}
routes := [][]int{{2, 3, 4, 5}, {1, 3, 4, 5}}
fmt.Println(solution(points, routes))
}
func solution(points [][]int, routes [][]int) int {
result := 0
cnt := 0
pointsMap := make(map[int][2]int, 0)
currentHeadingRoute := make([][2]int, 0)
for i := 0; i < len(routes); i++ {
initPointAndDirection := [2]int{2, routes[i][1]}
currentHeadingRoute = append(currentHeadingRoute, initPointAndDirection)
var tmp [2]int
tmp[0] = points[routes[i][0]-1][0]
tmp[1] = points[routes[i][0]-1][1]
pointsMap[i] = tmp
}
pointChan := make(chan [][2]int)
go func() {
for {
if cnt == 0 {
tmpArray := make([][2]int, 0)
for _, value := range pointsMap {
tmpArray = append(tmpArray, value)
}
pointChan <- tmpArray
cnt++
continue
}
tmpArray := make([][2]int, 0)
outerLoop:
for i := 0; i < len(routes); i++ {
previousPoint := pointsMap[i]
var destinationPoint [2]int
destinationPoint[0] = points[currentHeadingRoute[i][1]-1][0]
destinationPoint[1] = points[currentHeadingRoute[i][1]-1][1]
currentPoint := previousPoint
if currentPoint == destinationPoint {
if len(routes[i]) == currentHeadingRoute[i][0] {
continue outerLoop
} else {
currentHeadingRoute[i][0] = currentHeadingRoute[i][0] + 1
currentHeadingRoute[i][1] = routes[i][currentHeadingRoute[i][0]-1]
destinationPoint[0] = points[currentHeadingRoute[i][1]-1][0]
destinationPoint[1] = points[currentHeadingRoute[i][1]-1][1]
}
}
if previousPoint[0] != destinationPoint[0] {
if previousPoint[0] > destinationPoint[0] {
currentPoint[0] = previousPoint[0] - 1
} else {
currentPoint[0] = previousPoint[0] + 1
}
tmpArray = append(tmpArray, currentPoint)
pointsMap[i] = currentPoint
continue
}
if previousPoint[1] != destinationPoint[1] {
if previousPoint[1] > destinationPoint[1] {
currentPoint[1] = previousPoint[1] - 1
} else {
currentPoint[1] = previousPoint[1] + 1
}
tmpArray = append(tmpArray, currentPoint)
pointsMap[i] = currentPoint
continue
}
}
if len(tmpArray) == 0 {
close(pointChan)
break
}
pointChan <- tmpArray
cnt++
}
}()
for {
select {
case tmpPoints, ok := <-pointChan:
if !ok {
return result
}
duplicateMap := make(map[[2]int]int, 0)
for _, value := range tmpPoints {
if _, exists := duplicateMap[value]; !exists {
duplicateMap[value] = 1
} else {
duplicateMap[value] = duplicateMap[value] + 1
}
}
for _, value := range duplicateMap {
if value >= 2 {
result = result + 1
}
}
}
}
}