-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathday07_pt2.js
145 lines (135 loc) · 3.92 KB
/
day07_pt2.js
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
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
const input = require("fs")
.readFileSync("day07_input.txt")
.toString()
.split(/\r?\n/)
let tower = {}
input.forEach((line) => {
let lineArray = line.split(" ")
//console.log(lineArray)
let program = {
holding: [],
heldBy: "",
weight: parseInt(lineArray[1].replace(/\(|\)/g, "")),
}
if (lineArray.length > 3) {
for (let i = 3; i < lineArray.length; i++) {
let heldProgram = lineArray[i].replace(",", "")
program.holding.push(heldProgram)
}
}
let towerName = lineArray[0]
tower[towerName] = program
})
//add heldBy to each program in the tower
for (const program in tower) {
//console.log(program)
if (tower[program].holding.length > 0) {
tower[program].holding.forEach((heldProgram) => {
//console.log(` ${heldProgram} is being updated `)
tower[heldProgram].heldBy = program
let test = tower[heldProgram].heldBy
})
}
}
//add cummulative weights to each node
for (const program in tower) {
let newWeight = tower[program].weight
let descendents = getDescendents(program, tower)
descendents.forEach((descendent) => {
newWeight += tower[descendent].weight
})
tower[program].cumWeight = newWeight
}
//start with trunk, check it's childrens weights, if a discpreancy exists continue to check that child's children until there is no discrepancy.
let currentNode
for (const program in tower) {
//console.log(program)
//console.log(tower[program])
if (tower[program].holding.length > 0 && tower[program].heldBy.length === 0) {
currentNode = program
}
}
let discrepancy = true
let previousNeighbors
while (discrepancy) {
//console.log("while loop top")
//console.log({ currentNode })
let children = getChildren(currentNode, tower)
//console.log({ children })
let childrenCumWeights = children.map((child) => {
return tower[child].cumWeight
})
//console.log({ childrenCumWeights })
let discrepantIndex = returnIndexOfOutlier(childrenCumWeights)
//console.log({ discrepantIndex })
if (discrepantIndex === undefined) {
discrepancy = false
console.log(
`the discrepant node is ${currentNode}, it's individual weight is ${
tower[currentNode].weight
} and its neighbors weights are ${previousNeighbors}, it's weight should be ${
tower[currentNode].weight + differenceOfOutlier(previousNeighbors)
}`
)
}
previousNeighbors = childrenCumWeights
currentNode = children[discrepantIndex]
}
//-------FUNCTIONS FOR RUNTIME
function getDescendents(program, tower) {
// get children of initial tower and place in queue
let queue = getChildren(program, tower)
let descendents = []
// check if any of the children have children, if they do, add to queue them to the queue
while (queue.length > 0) {
if (getChildren(queue[0], tower)) {
let children = getChildren(queue[0], tower)
children.forEach((child) => {
queue.push(child)
})
}
let checkedChild = queue.shift()
descendents.push(checkedChild)
}
return descendents
}
function getChildren(program, tower) {
return [...tower[program].holding]
}
function checkIfEqual(obj) {
let arr = []
for (const property in obj) {
arr.push(obj[property])
}
return arr.every((weight) => arr[0] === weight)
}
function getInequalValue(obj) {
let indexedObj = Object.keys(obj)
let arr = []
for (const property in obj) {
arr.push(obj[property])
}
let differentIndex = returnIndexOfOutlier(arr)
return indexedObj[differentIndex]
}
function returnIndexOfOutlier(arr) {
for (let i = 0; i < arr.length; i++) {
let diffCount = 0
for (let j = 0; j < arr.length; j++) {
if (arr[i] !== arr[j]) {
diffCount++
}
}
if (diffCount > 1) {
return i
}
}
}
function differenceOfOutlier(arr) {
let outlierIndex = returnIndexOfOutlier(arr)
if (arr[outlierIndex + 1]) {
return arr[outlierIndex + 1] - arr[outlierIndex]
} else {
return arr[outlierIndex - 1] - arr[outlierIndex]
}
}