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
export default function isCyclic(object, seen = new WeakSet().add(object)) { | |
const props = getProps(object) | |
let len = props.length | |
while (len--) { | |
const value = object[props[len]] | |
if (value instanceof Object) { | |
if (seen.has(value)) { | |
return true | |
} |
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
/** | |
* @param asyncFn - A promise-returning function. e.g. an HTTP call. | |
* @param expiresIn - The number of milliseconds for the result from calling `asyncFn` to expire. | |
* @returns A memoized function that will always resolve to the first result of calling `asyncFn`, | |
* as long as the result has not expired. | |
*/ | |
export function memoPromise(asyncFn, expiresIn) { | |
const emptyId = Symbol("empty") | |
const memo = {} |
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
// This code is mostly useless. I put it here for | |
// the purpose of entertainment... | |
function detectIfUserIsFromChina() { | |
const img = new Image() | |
img.setAttribute("src", `https://www.google.com/favicon.ico?t=${Date.now()}`) | |
img.setAttribute("style", "width:0;height:0;visibility:hidden;") | |
document.body.appendChild(img) | |
return new Promise(res => { | |
img.onerror = () => res(true) |
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
let timeout = null; | |
const queue = new Set(); | |
function process() { | |
for (const task of queue) { | |
task(); | |
} | |
queue.clear(); | |
timeout = null; | |
} |
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
function traverse(node, processTask, continuation) { | |
processTask(node, function handleChildren() { | |
const children = node.childNodes; | |
function handleOne(i, len, continuation) { | |
if (i < len) { | |
traverse(children[i], processTask, function handleNext() { | |
handleOne(i + 1, len, continuation); | |
}); | |
} else { |
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
class TrieNode { | |
constructor(char) { | |
this.char = char; | |
this.validWord = false; | |
this.parent = null; | |
this.children = []; | |
} | |
} | |
class Trie { |
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
// Utility function for detecting generators. | |
let isGenerator = x => { | |
return Function.isGenerator && | |
Function.isGenerator.call(x) | |
} | |
// Data type represents channel into which values | |
// can be `put`, or `received` from. Channel is | |
// very much like queue where reads and writes are | |
// synchronized via continuation passing. |
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
function toList(next, reversed) { | |
const arr = []; | |
let value = next(); | |
while (value !== undefined) { | |
if (reversed) { | |
arr.unshift(value); | |
value = next(); | |
} else { | |
arr.push(value); | |
value = next(); |
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
const curry = fn => (...args) => | |
args.length >= fn.length ? fn(...args) : curry(fn.bind(undefined, ...args)) | |
const always = a => b => a | |
const compose = (...fns) => args => fns.reduceRight((x, f) => f(x), args) | |
const getFunctor = x => | |
Object.freeze({ | |
value: x, |
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
/* | |
* Easing Functions - inspired from http://gizma.com/easing/ | |
* only considering the t value for the range [0, 1] => [0, 1] | |
*/ | |
EasingFunctions = { | |
// no easing, no acceleration | |
linear: function (t) { return t }, | |
// accelerating from zero velocity | |
easeInQuad: function (t) { return t*t }, | |
// decelerating to zero velocity |
NewerOlder