Last active
March 27, 2022 09:07
-
-
Save WhiskeyTuesday/16167b19cc4c13ef9b0c7bfb0c0e7d9e to your computer and use it in GitHub Desktop.
Impromptu travelling monk kata
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
Proof that the monk ascending the hill and the monk descending the hill | |
in the riddle do cross within a meter of each other at some point along | |
the path to the temple even if they are moving at random speeds. | |
Technically this doesn't ensure that the trips take equal time to cover | |
equal distance, but it actually doesn't matter. That part of the question | |
is a red herring, as is the day usually specified to have been spent on | |
the mountaintop in between. Because the two journies (or you can think of | |
it as two diffent monks leaving at the same time) are conducted at the | |
same average speed the meeting occurs somewhere near the middle of the | |
distance, if the descending monk was going much faster the two would | |
meet closer to the bottom, and the opposite is also obviously true | |
anyway, it's relatively simple if you imagine it as two monks but if | |
you need to prove it to youself and you understand javascript, here's your | |
proof I guess. | |
AUTHOR - @WhiskeyTuesday | |
LICENCE - WTFPL 3.1 - https://ph.dtf.wtf/u/wtfplv31 for more details. | |
*/ | |
// create an array where each element represents the distance travelled | |
// (between 0 and 100 milimeters) in one second (over a 24 hour period) | |
const ascent = [...Array(24 * 60 * 60)] | |
.map(() => Math.floor(Math.random() * 100)); | |
// you may understand this easier as a map over ascent where we sum | |
// all of ascent up to the current index at each element (but this | |
// is like a billion times faster so I did it this way) | |
const ascentPositionsAtTimes = [...ascent]; | |
ascentPositionsAtTimes.forEach((distanceCovered, idx) => { | |
const positionSoFar = idx === 0 | |
? 0 | |
: ascentPositionsAtTimes[idx - 1]; | |
ascentPositionsAtTimes[idx] = positionSoFar + distanceCovered; | |
return 0; | |
}); | |
// the same as the ascent (but measured from the top, obviously) | |
const descent = [...Array(24 * 60 * 60)] | |
.map(() => Math.floor(Math.random() * 100)); | |
// calculate the total distance travelled | |
const totalDistance = ascent.reduce((acc, distance) => acc + distance); | |
// this is the same as on the way up except the absolute position | |
// with 0 as the bottom and totalDistance as the top is | |
// calculated by subtracting the distance covered so far from the | |
// totalDistance we calculated before | |
const descentPositionsAtTimes = [...descent]; | |
descentPositionsAtTimes.forEach((distanceCovered, idx) => { | |
const distanceRemaining = idx === 0 | |
? totalDistance | |
: descentPositionsAtTimes[idx - 1]; | |
descentPositionsAtTimes[idx] = distanceRemaining - distanceCovered; | |
return 0; | |
}); | |
// now we iterate through each one second "slice" of time on the | |
// descent trip and see what the absolute position in mms was | |
// and what the absolute position in mms of the ascending monk | |
// was at the same timestamp is and if the two positions are | |
// within 1 meter of each other's at the same timestamp we | |
// console log the timestamp (array index) and position of | |
// each monk | |
descentPositionsAtTimes.forEach((pos, idx) => { | |
const within1mBelow = pos > ascentPositionsAtTimes[idx] - 1000; | |
const within1mAbove = pos < ascentPositionsAtTimes[idx] + 1000; | |
if (within1mAbove && within1mBelow) { | |
console.log(idx, ascentPositionsAtTimes[idx], pos); | |
} | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment