From b4668466a519f7e4f08a1b8067f1c7156a07a424 Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Wed, 13 Dec 2017 21:42:58 +0530 Subject: [PATCH 01/92] Create join_array_like_objects.md --- snippets/join_array_like_objects.md | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 snippets/join_array_like_objects.md diff --git a/snippets/join_array_like_objects.md b/snippets/join_array_like_objects.md new file mode 100644 index 000000000..57acd6731 --- /dev/null +++ b/snippets/join_array_like_objects.md @@ -0,0 +1,11 @@ +### Joining an array-like object + +The following example joins array-like object (arguments), by calling Function.prototype.call on Array.prototype.join. + +``` +function f(a, b, c) { + var s = Array.prototype.join.call(arguments); + console.log(s); // '1,a,true' +} +f(1, 'a', true); +``` From fea9f8553206caf7a3b530271a0483caa653ad19 Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Wed, 13 Dec 2017 21:52:51 +0530 Subject: [PATCH 02/92] Create check_for_boolean --- snippets/check_for_boolean | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 snippets/check_for_boolean diff --git a/snippets/check_for_boolean b/snippets/check_for_boolean new file mode 100644 index 000000000..a96719aea --- /dev/null +++ b/snippets/check_for_boolean @@ -0,0 +1,10 @@ +### Check for Boolean Primitive Values + +Check if a value is classified as a boolean primitive. Return true or false. + +function booWho(bool) { + return typeof bool === 'boolean'; +} + +// test here +booWho(null); From 210104ef7a0e97634488b52f5bcdc0ec519e7479 Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Wed, 13 Dec 2017 21:56:13 +0530 Subject: [PATCH 03/92] Rename check_for_boolean to check_for_boolean.md --- snippets/{check_for_boolean => check_for_boolean.md} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename snippets/{check_for_boolean => check_for_boolean.md} (100%) diff --git a/snippets/check_for_boolean b/snippets/check_for_boolean.md similarity index 100% rename from snippets/check_for_boolean rename to snippets/check_for_boolean.md From 65a70a1ed609ac42600a54c2fd841720dda62e87 Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Wed, 13 Dec 2017 22:00:06 +0530 Subject: [PATCH 04/92] Create drop_elements_in_array.md --- snippets/drop_elements_in_array.md | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 snippets/drop_elements_in_array.md diff --git a/snippets/drop_elements_in_array.md b/snippets/drop_elements_in_array.md new file mode 100644 index 000000000..73e2688b5 --- /dev/null +++ b/snippets/drop_elements_in_array.md @@ -0,0 +1,19 @@ +### Drop It + +Drop the elements of an array (first argument), starting from the front, until the predicate (second argument) returns true. + +Method - +- Use a while loop with Array.prototype.shift() to continue checking and dropping the first element of the array until the function returns true. It also makes sure the array is not empty first to avoid infinite loops. +- Return the filtered array. + +``` +function dropElements(arr, func) { + while(arr.length > 0 && !func(arr[0])) { + arr.shift(); + } + return arr; +} + +// test here +dropElements([1, 2, 3, 4], function(n) {return n >= 3;}); +``` From c236de3e67d68e4d9faf283dec86a0e1f333046d Mon Sep 17 00:00:00 2001 From: Christian Bender Date: Wed, 13 Dec 2017 23:02:42 +0100 Subject: [PATCH 05/92] collatz algorithm collatz algorithm as function --- snippets/collatz.md | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 snippets/collatz.md diff --git a/snippets/collatz.md b/snippets/collatz.md new file mode 100644 index 000000000..120f96e27 --- /dev/null +++ b/snippets/collatz.md @@ -0,0 +1,11 @@ +### Collatz algorithm + +If n even then returns **n/2** otherwise (n is odd) **3n+1**. +It uses the ternary operator. + +``` javascript + const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); + // collatz(8) --> 4 + // collatz(5) --> 16 + +``` \ No newline at end of file From 38e5a30585433ef4c67190df8c00d650a96d7ab3 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 11:32:08 +0200 Subject: [PATCH 06/92] Update and rename check_for_boolean.md to check-for-boolean-primitive-values.md --- snippets/check-for-boolean-primitive-values.md | 8 ++++++++ snippets/check_for_boolean.md | 10 ---------- 2 files changed, 8 insertions(+), 10 deletions(-) create mode 100644 snippets/check-for-boolean-primitive-values.md delete mode 100644 snippets/check_for_boolean.md diff --git a/snippets/check-for-boolean-primitive-values.md b/snippets/check-for-boolean-primitive-values.md new file mode 100644 index 000000000..308e3a085 --- /dev/null +++ b/snippets/check-for-boolean-primitive-values.md @@ -0,0 +1,8 @@ +### Check for boolean primitive values + +Use `typeof` to check if a value is classified as a boolean primitive. + +```js +const isBool = val => typeof val === 'boolean'; +// isBool(null) -> false +``` diff --git a/snippets/check_for_boolean.md b/snippets/check_for_boolean.md deleted file mode 100644 index a96719aea..000000000 --- a/snippets/check_for_boolean.md +++ /dev/null @@ -1,10 +0,0 @@ -### Check for Boolean Primitive Values - -Check if a value is classified as a boolean primitive. Return true or false. - -function booWho(bool) { - return typeof bool === 'boolean'; -} - -// test here -booWho(null); From c37d4a24182031736dd78b915b7b4f32fe6bbf37 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 11:36:20 +0200 Subject: [PATCH 07/92] Update and rename drop_elements_in_array.md to drop-elements-in-array.md --- snippets/drop-elements-in-array.md | 12 ++++++++++++ snippets/drop_elements_in_array.md | 19 ------------------- 2 files changed, 12 insertions(+), 19 deletions(-) create mode 100644 snippets/drop-elements-in-array.md delete mode 100644 snippets/drop_elements_in_array.md diff --git a/snippets/drop-elements-in-array.md b/snippets/drop-elements-in-array.md new file mode 100644 index 000000000..0ad2ab5e9 --- /dev/null +++ b/snippets/drop-elements-in-array.md @@ -0,0 +1,12 @@ +### Drop elements in array + +Loop through the array, using `Array.shift()` to drop the first element of the array until the returned value from the function is `true`. +Returns the remaining elements. + +```js +const dropElements = (arr,func) => { + while(arr.length > 0 && !func(arr[0])) arr.shift(); + return arr; +} +// dropElements([1, 2, 3, 4], n => n >= 3) -> [3,4] +``` diff --git a/snippets/drop_elements_in_array.md b/snippets/drop_elements_in_array.md deleted file mode 100644 index 73e2688b5..000000000 --- a/snippets/drop_elements_in_array.md +++ /dev/null @@ -1,19 +0,0 @@ -### Drop It - -Drop the elements of an array (first argument), starting from the front, until the predicate (second argument) returns true. - -Method - -- Use a while loop with Array.prototype.shift() to continue checking and dropping the first element of the array until the function returns true. It also makes sure the array is not empty first to avoid infinite loops. -- Return the filtered array. - -``` -function dropElements(arr, func) { - while(arr.length > 0 && !func(arr[0])) { - arr.shift(); - } - return arr; -} - -// test here -dropElements([1, 2, 3, 4], function(n) {return n >= 3;}); -``` From 78d5fa31f8fa95ab80aa9916cb41ce282dfdb7b9 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 12:18:42 +0200 Subject: [PATCH 08/92] Build README --- README.md | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/README.md b/README.md index 1015e7c72..a050fb089 100644 --- a/README.md +++ b/README.md @@ -10,6 +10,7 @@ ## Contents * [Anagrams of string (with duplicates)](#anagrams-of-string-with-duplicates) +* [Array concatenation](#array-concatenation) * [Array difference](#array-difference) * [Array intersection](#array-intersection) * [Array union](#array-union) @@ -95,6 +96,15 @@ const anagrams = str => { // anagrams('abc') -> ['abc','acb','bac','bca','cab','cba'] ``` +### Array concatenation + +Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. + +```js +const ArrayConcat = (arr, ...args) => arr.concat(...args); +// ArrayConcat([1], [1, 2, 3, [4]]) -> [1, 2, 3, [4]] +``` + ### Array difference Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values not contained in `b`. From c30cf9307df0f125359872677068aa0a56072108 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 12:29:51 +0200 Subject: [PATCH 09/92] Fixed arrayConcat example --- README.md | 4 ++-- snippets/array-concatenation.md | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index a050fb089..ee3f560f7 100644 --- a/README.md +++ b/README.md @@ -101,8 +101,8 @@ const anagrams = str => { Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. ```js -const ArrayConcat = (arr, ...args) => arr.concat(...args); -// ArrayConcat([1], [1, 2, 3, [4]]) -> [1, 2, 3, [4]] +const arrayConcat = (arr, ...args) => arr.concat(...args); +// arrayConcat([1], [1, 2, 3, [4]]) -> [1, 1, 2, 3, [4]] ``` ### Array difference diff --git a/snippets/array-concatenation.md b/snippets/array-concatenation.md index 39d978d6e..b7b26ea26 100644 --- a/snippets/array-concatenation.md +++ b/snippets/array-concatenation.md @@ -3,6 +3,6 @@ Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. ```js -const ArrayConcat = (arr, ...args) => arr.concat(...args); -// ArrayConcat([1], [1, 2, 3, [4]]) -> [1, 2, 3, [4]] +const arrayConcat = (arr, ...args) => arr.concat(...args); +// arrayConcat([1], [1, 2, 3, [4]]) -> [1, 1, 2, 3, [4]] ``` From d304cb6e7d1b2b559968d261cbbc80a0e5c882bd Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 12:31:43 +0200 Subject: [PATCH 10/92] Update arrayConcat example --- README.md | 2 +- snippets/array-concatenation.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index ee3f560f7..ed642cf3f 100644 --- a/README.md +++ b/README.md @@ -102,7 +102,7 @@ Use `Array.concat()` to concatenate and array with any additional arrays and/or ```js const arrayConcat = (arr, ...args) => arr.concat(...args); -// arrayConcat([1], [1, 2, 3, [4]]) -> [1, 1, 2, 3, [4]] +// arrayConcat([1], 2, [3], [[4]]) -> [1,2,3,[4]] ``` ### Array difference diff --git a/snippets/array-concatenation.md b/snippets/array-concatenation.md index b7b26ea26..b4e2fa205 100644 --- a/snippets/array-concatenation.md +++ b/snippets/array-concatenation.md @@ -4,5 +4,5 @@ Use `Array.concat()` to concatenate and array with any additional arrays and/or ```js const arrayConcat = (arr, ...args) => arr.concat(...args); -// arrayConcat([1], [1, 2, 3, [4]]) -> [1, 1, 2, 3, [4]] +// arrayConcat([1], 2, [3], [[4]]) -> [1,2,3,[4]] ``` From df5428c64846b4e7dd52f8d1d0a37b6da89fcda2 Mon Sep 17 00:00:00 2001 From: atomiks Date: Thu, 14 Dec 2017 21:34:48 +1100 Subject: [PATCH 11/92] Create element-is-visible-in-viewport.md https://codepen.io/anon/pen/MrwYzx Adjust the `transform: translate()` to test it out --- snippets/element-is-visible-in-viewport.md | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 snippets/element-is-visible-in-viewport.md diff --git a/snippets/element-is-visible-in-viewport.md b/snippets/element-is-visible-in-viewport.md new file mode 100644 index 000000000..68a690d0d --- /dev/null +++ b/snippets/element-is-visible-in-viewport.md @@ -0,0 +1,19 @@ +### Element is visible in viewport + +Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values +to determine if a given element is visible in the viewport. +Omit the second argument to determine if the element is entirely visible, or specify `true` to determine if +it is partially visible. + +```js +const elementIsVisibleInViewport = (el, partiallyVisible = false) => { + const { top, left, bottom, right } = el.getBoundingClientRect(); + return partiallyVisible + ? ((top > 0 && top < innerHeight) || (bottom > 0 && bottom < innerHeight)) && + ((left > 0 && left < innerWidth) || (right > 0 && right < innerWidth)) + : top >= 0 && left >= 0 && bottom <= innerHeight && right <= innerWidth; +} +// e.g. 100x100 viewport and a 10x10px element at position {top: -1, left: 0, bottom: 9, right: 10} +// elementIsInViewport(el) -> false (not fully visible) +// elementIsInViewport(el, true) -> true (partially visible) +``` From 3b0a8885cc03b266144c7410ea745aec72339a82 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 12:50:15 +0200 Subject: [PATCH 12/92] Build README --- README.md | 24 ++++++++++++++++++++++++ snippets/join_array_like_objects.md | 11 ----------- 2 files changed, 24 insertions(+), 11 deletions(-) delete mode 100644 snippets/join_array_like_objects.md diff --git a/README.md b/README.md index ed642cf3f..6a9476c6f 100644 --- a/README.md +++ b/README.md @@ -19,6 +19,7 @@ * [Capitalize first letter of every word](#capitalize-first-letter-of-every-word) * [Capitalize first letter](#capitalize-first-letter) * [Chain asynchronous functions](#chain-asynchronous-functions) +* [Check for boolean primitive values](#check-for-boolean-primitive-values) * [Check for palindrome](#check-for-palindrome) * [Chunk array](#chunk-array) * [Compact](#compact) @@ -28,6 +29,7 @@ * [Deep flatten array](#deep-flatten-array) * [Distance between two points](#distance-between-two-points) * [Divisible by number](#divisible-by-number) +* [Drop elements in array](#drop-elements-in-array) * [Escape regular expression](#escape-regular-expression) * [Even or odd number](#even-or-odd-number) * [Factorial](#factorial) @@ -186,6 +188,15 @@ chainAsync([ */ ``` +### Check for boolean primitive values + +Use `typeof` to check if a value is classified as a boolean primitive. + +```js +const isBool = val => typeof val === 'boolean'; +// isBool(null) -> false +``` + ### Check for palindrome Convert string `toLowerCase()` and use `replace()` to remove non-alphanumeric characters from it. @@ -286,6 +297,19 @@ const isDivisible = (dividend, divisor) => dividend % divisor === 0; // isDivisible(6,3) -> true ``` +### Drop elements in array + +Loop through the array, using `Array.shift()` to drop the first element of the array until the returned value from the function is `true`. +Returns the remaining elements. + +```js +const dropElements = (arr,func) => { + while(arr.length > 0 && !func(arr[0])) arr.shift(); + return arr; +} +// dropElements([1, 2, 3, 4], n => n >= 3) -> [3,4] +``` + ### Escape regular expression Use `replace()` to escape special characters. diff --git a/snippets/join_array_like_objects.md b/snippets/join_array_like_objects.md deleted file mode 100644 index 57acd6731..000000000 --- a/snippets/join_array_like_objects.md +++ /dev/null @@ -1,11 +0,0 @@ -### Joining an array-like object - -The following example joins array-like object (arguments), by calling Function.prototype.call on Array.prototype.join. - -``` -function f(a, b, c) { - var s = Array.prototype.join.call(arguments); - console.log(s); // '1,a,true' -} -f(1, 'a', true); -``` From 2346be526797534ec871f7787be653c899f8a540 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 12:56:02 +0200 Subject: [PATCH 13/92] Added isX functions --- README.md | 65 ++++++++++++++++--- .../check-for-boolean-primitive-values.md | 8 --- snippets/is-boolean.md | 9 +++ snippets/is-function.md | 9 +++ snippets/is-number.md | 9 +++ snippets/is-string.md | 9 +++ snippets/is-symbol.md | 9 +++ 7 files changed, 100 insertions(+), 18 deletions(-) delete mode 100644 snippets/check-for-boolean-primitive-values.md create mode 100644 snippets/is-boolean.md create mode 100644 snippets/is-function.md create mode 100644 snippets/is-number.md create mode 100644 snippets/is-string.md create mode 100644 snippets/is-symbol.md diff --git a/README.md b/README.md index 6a9476c6f..822750209 100644 --- a/README.md +++ b/README.md @@ -19,7 +19,6 @@ * [Capitalize first letter of every word](#capitalize-first-letter-of-every-word) * [Capitalize first letter](#capitalize-first-letter) * [Chain asynchronous functions](#chain-asynchronous-functions) -* [Check for boolean primitive values](#check-for-boolean-primitive-values) * [Check for palindrome](#check-for-palindrome) * [Chunk array](#chunk-array) * [Compact](#compact) @@ -47,6 +46,11 @@ * [Initial of list](#initial-of-list) * [Initialize array with range](#initialize-array-with-range) * [Initialize array with values](#initialize-array-with-values) +* [Is boolean](#is-boolean) +* [Is function](#is-function) +* [Is number](#is-number) +* [Is string](#is-string) +* [Is symbol](#is-symbol) * [Last of list](#last-of-list) * [Measure time taken by function](#measure-time-taken-by-function) * [Median of array of numbers](#median-of-array-of-numbers) @@ -188,15 +192,6 @@ chainAsync([ */ ``` -### Check for boolean primitive values - -Use `typeof` to check if a value is classified as a boolean primitive. - -```js -const isBool = val => typeof val === 'boolean'; -// isBool(null) -> false -``` - ### Check for palindrome Convert string `toLowerCase()` and use `replace()` to remove non-alphanumeric characters from it. @@ -485,6 +480,56 @@ const initializeArray = (n, value = 0) => Array(n).fill(value); // initializeArray(5, 2) -> [2,2,2,2,2] ``` +### Is boolean + +Use `typeof` to check if a value is classified as a boolean primitive. + +```js +const isBoolean = val => typeof val === 'boolean'; +// isBoolean(null) -> false +// isBoolean(false) -> true +``` + +### Is boolean + +Use `typeof` to check if a value is classified as a function primitive. + +```js +const isFunction = val => val && typeof val === 'function'; +// isFunction('x') -> false +// isFunction(x => x) -> true +``` + +### Is number + +Use `typeof` to check if a value is classified as a number primitive. + +```js +const isNumber = val => typeof val === 'number'; +// isNumber('1') -> false +// isNumber(1) -> true +``` + +### Is string + +Use `typeof` to check if a value is classified as a string primitive. + +```js +const isString = val => typeof val === 'string'; +// isString(10) -> false +// isString('10') -> true +``` + +### Is symbol + +Use `typeof` to check if a value is classified as a symbol primitive. + +```js +const isSymbol = val => typeof val === 'symbol'; +// isSymbol('x') -> false +// isSymbol(Symbol('x')) -> true +``` + ### Last of list Use `arr.slice(-1)[0]` to get the last element of the given array. diff --git a/snippets/check-for-boolean-primitive-values.md b/snippets/check-for-boolean-primitive-values.md deleted file mode 100644 index 308e3a085..000000000 --- a/snippets/check-for-boolean-primitive-values.md +++ /dev/null @@ -1,8 +0,0 @@ -### Check for boolean primitive values - -Use `typeof` to check if a value is classified as a boolean primitive. - -```js -const isBool = val => typeof val === 'boolean'; -// isBool(null) -> false -``` diff --git a/snippets/is-boolean.md b/snippets/is-boolean.md new file mode 100644 index 000000000..8625add35 --- /dev/null +++ b/snippets/is-boolean.md @@ -0,0 +1,9 @@ +### Is boolean + +Use `typeof` to check if a value is classified as a boolean primitive. + +```js +const isBoolean = val => typeof val === 'boolean'; +// isBoolean(null) -> false +// isBoolean(false) -> true +``` diff --git a/snippets/is-function.md b/snippets/is-function.md new file mode 100644 index 000000000..a406ee543 --- /dev/null +++ b/snippets/is-function.md @@ -0,0 +1,9 @@ +### Is boolean + +Use `typeof` to check if a value is classified as a function primitive. + +```js +const isFunction = val => val && typeof val === 'function'; +// isFunction('x') -> false +// isFunction(x => x) -> true +``` diff --git a/snippets/is-number.md b/snippets/is-number.md new file mode 100644 index 000000000..a647b39ed --- /dev/null +++ b/snippets/is-number.md @@ -0,0 +1,9 @@ +### Is number + +Use `typeof` to check if a value is classified as a number primitive. + +```js +const isNumber = val => typeof val === 'number'; +// isNumber('1') -> false +// isNumber(1) -> true +``` diff --git a/snippets/is-string.md b/snippets/is-string.md new file mode 100644 index 000000000..6721c59c6 --- /dev/null +++ b/snippets/is-string.md @@ -0,0 +1,9 @@ +### Is string + +Use `typeof` to check if a value is classified as a string primitive. + +```js +const isString = val => typeof val === 'string'; +// isString(10) -> false +// isString('10') -> true +``` diff --git a/snippets/is-symbol.md b/snippets/is-symbol.md new file mode 100644 index 000000000..53d4ce67c --- /dev/null +++ b/snippets/is-symbol.md @@ -0,0 +1,9 @@ +### Is symbol + +Use `typeof` to check if a value is classified as a symbol primitive. + +```js +const isSymbol = val => typeof val === 'symbol'; +// isSymbol('x') -> false +// isSymbol(Symbol('x')) -> true +``` From 4583d71edc70295d3ebcb1b9d929ae21c05e360f Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 13:04:09 +0200 Subject: [PATCH 14/92] Build README --- README.md | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/README.md b/README.md index 822750209..1ff40dc0d 100644 --- a/README.md +++ b/README.md @@ -29,6 +29,7 @@ * [Distance between two points](#distance-between-two-points) * [Divisible by number](#divisible-by-number) * [Drop elements in array](#drop-elements-in-array) +* [Element is visible in viewport](#element-is-visible-in-viewport) * [Escape regular expression](#escape-regular-expression) * [Even or odd number](#even-or-odd-number) * [Factorial](#factorial) @@ -305,6 +306,26 @@ const dropElements = (arr,func) => { // dropElements([1, 2, 3, 4], n => n >= 3) -> [3,4] ``` +### Element is visible in viewport + +Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values +to determine if a given element is visible in the viewport. +Omit the second argument to determine if the element is entirely visible, or specify `true` to determine if +it is partially visible. + +```js +const elementIsVisibleInViewport = (el, partiallyVisible = false) => { + const { top, left, bottom, right } = el.getBoundingClientRect(); + return partiallyVisible + ? ((top > 0 && top < innerHeight) || (bottom > 0 && bottom < innerHeight)) && + ((left > 0 && left < innerWidth) || (right > 0 && right < innerWidth)) + : top >= 0 && left >= 0 && bottom <= innerHeight && right <= innerWidth; +} +// e.g. 100x100 viewport and a 10x10px element at position {top: -1, left: 0, bottom: 9, right: 10} +// elementIsInViewport(el) -> false (not fully visible) +// elementIsInViewport(el, true) -> true (partially visible) +``` + ### Escape regular expression Use `replace()` to escape special characters. From 9bd37780557ff219fd6a1e865f9779550106335e Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 13:05:13 +0200 Subject: [PATCH 15/92] Additional guidelines in CONTRIBUTING --- CONTRIBUTING.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 09e28829b..db1670488 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -45,6 +45,8 @@ Here's what you can do to help: - Try to give meaningful names to variables. For example use `letter`, instead of `lt`. Some exceptions by convention are: - `arr` for arrays (usually as the snippet function's argument). - `str` for strings. + - `n` for a numeric value (usually as the snippet function's argument). + - `el` for DOM elements (usually as the snippet function's argument). - `val` or `v` for value (usually when iterating a list, mapping, sorting etc.). - `acc` for accumulators in `Array.reduce()`. - `(a,b)` for the two values compared when using `Array.sort()`. From 5cd1ddd83ea564cdd26bc4db85dd26790235bb43 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 13:07:19 +0200 Subject: [PATCH 16/92] Updated builder with links to top --- README.md | 79 +++++++++++++++++++++++++++++++++++- scripts/builder.js | 2 +- static-parts/README-start.md | 2 +- 3 files changed, 80 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 1ff40dc0d..7e3df18b7 100644 --- a/README.md +++ b/README.md @@ -7,7 +7,7 @@ - Contributions welcome, please read the [contribution guide](CONTRIBUTING.md). - Snippets are written in ES6, use the [Babel transpiler](https://babeljs.io/) to ensure backwards-compatibility. -## Contents +## Table of Contents * [Anagrams of string (with duplicates)](#anagrams-of-string-with-duplicates) * [Array concatenation](#array-concatenation) @@ -103,6 +103,7 @@ const anagrams = str => { // anagrams('abc') -> ['abc','acb','bac','bca','cab','cba'] ``` +[⬆ back to top](#table-of-contents) ### Array concatenation Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. @@ -112,6 +113,7 @@ const arrayConcat = (arr, ...args) => arr.concat(...args); // arrayConcat([1], 2, [3], [[4]]) -> [1,2,3,[4]] ``` +[⬆ back to top](#table-of-contents) ### Array difference Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values not contained in `b`. @@ -121,6 +123,7 @@ const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has // difference([1,2,3], [1,2]) -> [3] ``` +[⬆ back to top](#table-of-contents) ### Array intersection Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values contained in `b`. @@ -130,6 +133,7 @@ const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.ha // intersection([1,2,3], [4,3,2]) -> [2,3] ``` +[⬆ back to top](#table-of-contents) ### Array union Create a `Set` with all values of `a` and `b` and convert to an array. @@ -139,6 +143,7 @@ const union = (a, b) => Array.from(new Set([...a, ...b])) // union([1,2,3], [4,3,2]) -> [1,2,3,4] ``` +[⬆ back to top](#table-of-contents) ### Average of array of numbers Use `Array.reduce()` to add each value to an accumulator, initialized with a value of `0`, divide by the `length` of the array. @@ -148,6 +153,7 @@ const average = arr => arr.reduce((acc, val) => acc + val, 0) / arr.length; // average([1,2,3]) -> 2 ``` +[⬆ back to top](#table-of-contents) ### Bottom visible Use `scrollY`, `scrollHeight` and `clientHeight` to determine if the bottom of the page is visible. @@ -158,6 +164,7 @@ const bottomVisible = _ => // bottomVisible() -> true ``` +[⬆ back to top](#table-of-contents) ### Capitalize first letter of every word Use `replace()` to match the first character of each word and `toUpperCase()` to capitalize it. @@ -167,6 +174,7 @@ const capitalizeEveryWord = str => str.replace(/\b[a-z]/g, char => char.toUpperC // capitalizeEveryWord('hello world!') -> 'Hello World!' ``` +[⬆ back to top](#table-of-contents) ### Capitalize first letter Use `slice(0,1)` and `toUpperCase()` to capitalize first letter, `slice(1)` to get the rest of the string. @@ -178,6 +186,7 @@ const capitalize = (str, lowerRest = false) => // capitalize('myName', true) -> 'Myname' ``` +[⬆ back to top](#table-of-contents) ### Chain asynchronous functions Loop through an array of functions containing asynchronous events, calling `next` when each asynchronous event has completed. @@ -193,6 +202,7 @@ chainAsync([ */ ``` +[⬆ back to top](#table-of-contents) ### Check for palindrome Convert string `toLowerCase()` and use `replace()` to remove non-alphanumeric characters from it. @@ -206,6 +216,7 @@ const palindrome = str => { // palindrome('taco cat') -> true ``` +[⬆ back to top](#table-of-contents) ### Chunk array Use `Array.from()` to create a new array, that fits the number of chunks that will be produced. @@ -218,6 +229,7 @@ const chunk = (arr, size) => // chunk([1,2,3,4,5], 2) -> [[1,2],[3,4],5] ``` +[⬆ back to top](#table-of-contents) ### Compact Use `Array.filter()` to filter out falsey values (`false`, `null`, `0`, `""`, `undefined`, and `NaN`). @@ -227,6 +239,7 @@ const compact = (arr) => arr.filter(v => v); // compact([0, 1, false, 2, '', 3, 'a', 'e'*23, NaN, 's', 34]) -> [ 1, 2, 3, 'a', 's', 34 ] ``` +[⬆ back to top](#table-of-contents) ### Count occurrences of a value in array Use `Array.reduce()` to increment a counter each time you encounter the specific value inside the array. @@ -236,6 +249,7 @@ const countOccurrences = (arr, value) => arr.reduce((a, v) => v === value ? a + // countOccurrences([1,1,2,1,2,3], 1) -> 3 ``` +[⬆ back to top](#table-of-contents) ### Current URL Use `window.location.href` to get current URL. @@ -245,6 +259,7 @@ const currentUrl = _ => window.location.href; // currentUrl() -> 'https://google.com' ``` +[⬆ back to top](#table-of-contents) ### Curry Use recursion. @@ -264,6 +279,7 @@ const curry = (f, arity = f.length, next) => // curry(Math.min, 3)(10)(50)(2) -> 2 ``` +[⬆ back to top](#table-of-contents) ### Deep flatten array Use recursion. @@ -275,6 +291,7 @@ const deepFlatten = arr => // deepFlatten([1,[2],[[3],4],5]) -> [1,2,3,4,5] ``` +[⬆ back to top](#table-of-contents) ### Distance between two points Use `Math.hypot()` to calculate the Euclidean distance between two points. @@ -284,6 +301,7 @@ const distance = (x0, y0, x1, y1) => Math.hypot(x1 - x0, y1 - y0); // distance(1,1, 2,3) -> 2.23606797749979 ``` +[⬆ back to top](#table-of-contents) ### Divisible by number Use the modulo operator (`%`) to check if the remainder is equal to `0`. @@ -293,6 +311,7 @@ const isDivisible = (dividend, divisor) => dividend % divisor === 0; // isDivisible(6,3) -> true ``` +[⬆ back to top](#table-of-contents) ### Drop elements in array Loop through the array, using `Array.shift()` to drop the first element of the array until the returned value from the function is `true`. @@ -306,6 +325,7 @@ const dropElements = (arr,func) => { // dropElements([1, 2, 3, 4], n => n >= 3) -> [3,4] ``` +[⬆ back to top](#table-of-contents) ### Element is visible in viewport Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values @@ -326,6 +346,7 @@ const elementIsVisibleInViewport = (el, partiallyVisible = false) => { // elementIsInViewport(el, true) -> true (partially visible) ``` +[⬆ back to top](#table-of-contents) ### Escape regular expression Use `replace()` to escape special characters. @@ -335,6 +356,7 @@ const escapeRegExp = str => str.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'); // escapeRegExp('(test)') -> \\(test\\) ``` +[⬆ back to top](#table-of-contents) ### Even or odd number Checks whether a number is odd or even using the modulo (`%`) operator. @@ -345,6 +367,7 @@ const isEven = num => num % 2 === 0; // isEven(3) -> false ``` +[⬆ back to top](#table-of-contents) ### Factorial Use recursion. @@ -356,6 +379,7 @@ const factorial = n => n <= 1 ? 1 : n * factorial(n - 1); // factorial(6) -> 720 ``` +[⬆ back to top](#table-of-contents) ### Fibonacci array generator Create an empty array of the specific length, initializing the first two values (`0` and `1`). @@ -367,6 +391,7 @@ const fibonacci = n => // fibonacci(5) -> [0,1,1,2,3] ``` +[⬆ back to top](#table-of-contents) ### Filter out non-unique values in an array Use `Array.filter()` for an array containing only the unique values. @@ -376,6 +401,7 @@ const filterNonUnique = arr => arr.filter(i => arr.indexOf(i) === arr.lastIndexO // filterNonUnique([1,2,2,3,4,4,5]) -> [1,3,5] ``` +[⬆ back to top](#table-of-contents) ### Flatten array Use `Array.reduce()` to get all elements inside the array and `concat()` to flatten them. @@ -385,6 +411,7 @@ const flatten = arr => arr.reduce((a, v) => a.concat(v), []); // flatten([1,[2],3,4]) -> [1,2,3,4] ``` +[⬆ back to top](#table-of-contents) ### Get max value from array Use `Math.max()` combined with the spread operator (`...`) to get the maximum value in the array. @@ -394,6 +421,7 @@ const arrayMax = arr => Math.max(...arr); // arrayMax([10, 1, 5]) -> 10 ``` +[⬆ back to top](#table-of-contents) ### Get min value from array Use `Math.min()` combined with the spread operator (`...`) to get the minimum value in the array. @@ -403,6 +431,7 @@ const arrayMin = arr => Math.min(...arr); // arrayMin([10, 1, 5]) -> 1 ``` +[⬆ back to top](#table-of-contents) ### Get native type of value Returns lower-cased constructor name of value, "undefined" or "null" if value is undefined or null @@ -413,6 +442,7 @@ const getType = v => // getType(new Set([1,2,3])) -> "set" ``` +[⬆ back to top](#table-of-contents) ### Get scroll position Use `pageXOffset` and `pageYOffset` if they are defined, otherwise `scrollLeft` and `scrollTop`. @@ -425,6 +455,7 @@ const getScrollPos = (el = window) => // getScrollPos() -> {x: 0, y: 200} ``` +[⬆ back to top](#table-of-contents) ### Greatest common divisor (GCD) Use recursion. @@ -436,6 +467,7 @@ const gcd = (x, y) => !y ? x : gcd(y, x % y); // gcd (8, 36) -> 4 ``` +[⬆ back to top](#table-of-contents) ### Group by Use `Array.map()` to map the values of an array to a function or property name. @@ -451,6 +483,7 @@ const groupBy = (arr, func) => // groupBy(['one', 'two', 'three'], 'length') -> {3: ['one', 'two'], 5: ['three']} ``` +[⬆ back to top](#table-of-contents) ### Hamming distance Use XOR operator (`^`) to find the bit difference between the two numbers, convert to binary string using `toString(2)`. @@ -462,6 +495,7 @@ const hammingDistance = (num1, num2) => // hammingDistance(2,3) -> 1 ``` +[⬆ back to top](#table-of-contents) ### Head of list Use `arr[0]` to return the first element of the passed array. @@ -471,6 +505,7 @@ const head = arr => arr[0]; // head([1,2,3]) -> 1 ``` +[⬆ back to top](#table-of-contents) ### Initial of list Use `arr.slice(0,-1)`to return all but the last element of the array. @@ -480,6 +515,7 @@ const initial = arr => arr.slice(0, -1); // initial([1,2,3]) -> [1,2] ``` +[⬆ back to top](#table-of-contents) ### Initialize array with range Use `Array(end-start)` to create an array of the desired length, `Array.map()` to fill with the desired values in a range. @@ -491,6 +527,7 @@ const initializeArrayRange = (end, start = 0) => // initializeArrayRange(5) -> [0,1,2,3,4] ``` +[⬆ back to top](#table-of-contents) ### Initialize array with values Use `Array(n)` to create an array of the desired length, `fill(v)` to fill it with the desired values. @@ -501,6 +538,7 @@ const initializeArray = (n, value = 0) => Array(n).fill(value); // initializeArray(5, 2) -> [2,2,2,2,2] ``` +[⬆ back to top](#table-of-contents) ### Is boolean Use `typeof` to check if a value is classified as a boolean primitive. @@ -511,6 +549,7 @@ const isBoolean = val => typeof val === 'boolean'; // isBoolean(false) -> true ``` +[⬆ back to top](#table-of-contents) ### Is boolean Use `typeof` to check if a value is classified as a function primitive. @@ -521,6 +560,7 @@ const isFunction = val => val && typeof val === 'function'; // isFunction(x => x) -> true ``` +[⬆ back to top](#table-of-contents) ### Is number Use `typeof` to check if a value is classified as a number primitive. @@ -531,6 +571,7 @@ const isNumber = val => typeof val === 'number'; // isNumber(1) -> true ``` +[⬆ back to top](#table-of-contents) ### Is string Use `typeof` to check if a value is classified as a string primitive. @@ -541,6 +582,7 @@ const isString = val => typeof val === 'string'; // isString('10') -> true ``` +[⬆ back to top](#table-of-contents) ### Is symbol Use `typeof` to check if a value is classified as a symbol primitive. @@ -551,6 +593,7 @@ const isSymbol = val => typeof val === 'symbol'; // isSymbol(Symbol('x')) -> true ``` +[⬆ back to top](#table-of-contents) ### Last of list Use `arr.slice(-1)[0]` to get the last element of the given array. @@ -560,6 +603,7 @@ const last = arr => arr.slice(-1)[0]; // last([1,2,3]) -> 3 ``` +[⬆ back to top](#table-of-contents) ### Measure time taken by function Use `performance.now()` to get start and end time for the function, `console.log()` the time taken. @@ -574,6 +618,7 @@ const timeTaken = callback => { // timeTaken(() => Math.pow(2, 10)) -> 1024 (0.010000000009313226 logged in console) ``` +[⬆ back to top](#table-of-contents) ### Median of array of numbers Find the middle of the array, use `Array.sort()` to sort the values. @@ -588,6 +633,7 @@ const median = arr => { // median([0,10,-2,7]) -> 3.5 ``` +[⬆ back to top](#table-of-contents) ### Object from key-value pairs Use `Array.reduce()` to create and combine key-value pairs. @@ -597,6 +643,7 @@ const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); // objectFromPairs([['a',1],['b',2]]) -> {a: 1, b: 2} ``` +[⬆ back to top](#table-of-contents) ### Object to key-value pairs Use `Object.keys()` and `Array.map()` to iterate over the object's keys and produce an array with key-value pairs. @@ -606,6 +653,7 @@ const objectToPairs = obj => Object.keys(obj).map(k => [k, obj[k]]); // objectToPairs({a: 1, b: 2}) -> [['a',1],['b',2]]) ``` +[⬆ back to top](#table-of-contents) ### Ordinal suffix of number Use the modulo operator (`%`) to find values of single and tens digits. @@ -622,6 +670,7 @@ const toOrdinalSuffix = num => { // toOrdinalSuffix("123") -> "123rd" ``` +[⬆ back to top](#table-of-contents) ### Percentile Use `Array.reduce()` to calculate how many numbers are below the value and how many are the same value and @@ -633,6 +682,7 @@ const percentile = (arr, val) => // percentile([1,2,3,4,5,6,7,8,9,10], 6) -> 55 ``` +[⬆ back to top](#table-of-contents) ### Pick Use `Array.reduce()` to convert the filtered/picked keys back to a object with the corresponding key:value pair if the key exist in the obj. @@ -644,6 +694,7 @@ const pick = (obj, arr) => // pick(object, ['a', 'c'])['a'] -> 1 ``` +[⬆ back to top](#table-of-contents) ### Pipe Use `Array.reduce()` to pass value through functions. @@ -653,6 +704,7 @@ const pipe = (...funcs) => arg => funcs.reduce((acc, func) => func(acc), arg); // pipe(btoa, x => x.toUpperCase())("Test") -> "VGVZDA==" ``` +[⬆ back to top](#table-of-contents) ### Powerset Use `Array.reduce()` combined with `Array.map()` to iterate over elements and combine into an array containing all combinations. @@ -663,6 +715,7 @@ const powerset = arr => // powerset([1,2]) -> [[], [1], [2], [2,1]] ``` +[⬆ back to top](#table-of-contents) ### Promisify Use currying to return a function returning a `Promise` that calls the original function. @@ -681,6 +734,7 @@ const promisify = func => // delay(2000).then(() => console.log('Hi!')) -> Promise resolves after 2s ``` +[⬆ back to top](#table-of-contents) ### Random integer in range Use `Math.random()` to generate a random number and map it to the desired range, using `Math.floor()` to make it an integer. @@ -690,6 +744,7 @@ const randomIntegerInRange = (min, max) => Math.floor(Math.random() * (max - min // randomIntegerInRange(0, 5) -> 2 ``` +[⬆ back to top](#table-of-contents) ### Random number in range Use `Math.random()` to generate a random value, map it to the desired range using multiplication. @@ -699,6 +754,7 @@ const randomInRange = (min, max) => Math.random() * (max - min) + min; // randomInRange(2,10) -> 6.0211363285087005 ``` +[⬆ back to top](#table-of-contents) ### Redirect to URL Use `window.location.href` or `window.location.replace()` to redirect to `url`. @@ -710,6 +766,7 @@ const redirect = (url, asLink = true) => // redirect('https://google.com') ``` +[⬆ back to top](#table-of-contents) ### Reverse a string Use array destructuring and `Array.reverse()` to reverse the order of the characters in the string. @@ -720,6 +777,7 @@ const reverseString = str => [...str].reverse().join(''); // reverseString('foobar') -> 'raboof' ``` +[⬆ back to top](#table-of-contents) ### RGB to hexadecimal Convert given RGB parameters to hexadecimal string using bitwise left-shift operator (`<<`) and `toString(16)`, then `padStart(6,'0')` to get a 6-digit hexadecimal value. @@ -729,6 +787,7 @@ const rgbToHex = (r, g, b) => ((r << 16) + (g << 8) + b).toString(16).padStart(6 // rgbToHex(255, 165, 1) -> 'ffa501' ``` +[⬆ back to top](#table-of-contents) ### Run promises in series Run an array of promises in series using `Array.reduce()` by creating a promise chain, where each promise returns the next promise when resolved. @@ -739,6 +798,7 @@ const series = ps => ps.reduce((p, next) => p.then(next), Promise.resolve()); // series([() => delay(1000), () => delay(2000)]) -> executes each promise sequentially, taking a total of 3 seconds to complete ``` +[⬆ back to top](#table-of-contents) ### Scroll to top Get distance from top using `document.documentElement.scrollTop` or `document.body.scrollTop`. @@ -755,6 +815,7 @@ const scrollToTop = _ => { // scrollToTop() ``` +[⬆ back to top](#table-of-contents) ### Shuffle array Use `Array.sort()` to reorder elements, using `Math.random()` in the comparator. @@ -764,6 +825,7 @@ const shuffle = arr => arr.sort(() => Math.random() - 0.5); // shuffle([1,2,3]) -> [2,3,1] ``` +[⬆ back to top](#table-of-contents) ### Similarity between arrays Use `filter()` to remove values that are not part of `values`, determined using `includes()`. @@ -773,6 +835,7 @@ const similarity = (arr, values) => arr.filter(v => values.includes(v)); // similarity([1,2,3], [1,2,4]) -> [1,2] ``` +[⬆ back to top](#table-of-contents) ### Sleep Delay executing part of an `async` function, by putting it to sleep, returning a `Promise`. @@ -788,6 +851,7 @@ async function sleepyWork() { */ ``` +[⬆ back to top](#table-of-contents) ### Sort characters in string (alphabetical) Split the string using `split('')`, `Array.sort()` utilizing `localeCompare()`, recombine using `join('')`. @@ -798,6 +862,7 @@ const sortCharactersInString = str => // sortCharactersInString('cabbage') -> 'aabbceg' ``` +[⬆ back to top](#table-of-contents) ### Standard deviation Use `Array.reduce()` to calculate the mean, variance and the sum of the variance of the values, the variance of the values, then @@ -816,6 +881,7 @@ const standardDeviation = (arr, usePopulation = false) => { // standardDeviation([10,2,38,23,38,23,21], true) -> 12.29899614287479 (population) ``` +[⬆ back to top](#table-of-contents) ### Sum of array of numbers Use `Array.reduce()` to add each value to an accumulator, initialized with a value of `0`. @@ -825,6 +891,7 @@ const sum = arr => arr.reduce((acc, val) => acc + val, 0); // sum([1,2,3,4]) -> 10 ``` +[⬆ back to top](#table-of-contents) ### Swap values of two variables Use array destructuring to swap values between two variables. @@ -834,6 +901,7 @@ Use array destructuring to swap values between two variables. // [x, y] = [y, x] ``` +[⬆ back to top](#table-of-contents) ### Tail of list Return `arr.slice(1)` if the array's `length` is more than `1`, otherwise return the whole array. @@ -844,6 +912,7 @@ const tail = arr => arr.length > 1 ? arr.slice(1) : arr; // tail([1]) -> [1] ``` +[⬆ back to top](#table-of-contents) ### Take Use `Array.slice()` to create a slice of the array with `n` elements taken from the beginning. @@ -855,6 +924,7 @@ const take = (arr, n = 1) => arr.slice(0, n); // take([1, 2, 3], 0) -> [] ``` +[⬆ back to top](#table-of-contents) ### Truncate a String Determine if the string's `length` is greater than `num`. @@ -866,6 +936,7 @@ const truncate = (str, num) => // truncate('boomerang', 7) -> 'boom...' ``` +[⬆ back to top](#table-of-contents) ### Unique values of array Use ES6 `Set` and the `...rest` operator to discard all duplicated values. @@ -875,6 +946,7 @@ const unique = arr => [...new Set(arr)]; // unique([1,2,2,3,4,4,5]) -> [1,2,3,4,5] ``` +[⬆ back to top](#table-of-contents) ### URL parameters Use `match()` with an appropriate regular expression to get all key-value pairs, `Array.reduce()` to map and combine them into a single object. @@ -888,6 +960,7 @@ const getUrlParameters = url => // getUrlParameters('http://url.com/page?name=Adam&surname=Smith') -> {name: 'Adam', surname: 'Smith'} ``` +[⬆ back to top](#table-of-contents) ### UUID generator Use `crypto` API to generate a UUID, compliant with [RFC4122](https://www.ietf.org/rfc/rfc4122.txt) version 4. @@ -900,6 +973,7 @@ const uuid = _ => // uuid() -> '7982fcfe-5721-4632-bede-6000885be57d' ``` +[⬆ back to top](#table-of-contents) ### Validate email Use a regular experssion to check if the email is valid. @@ -911,6 +985,7 @@ const validateEmail = str => // validateEmail(mymail@gmail.com) -> true ``` +[⬆ back to top](#table-of-contents) ### Validate number Use `!isNaN` in combination with `parseFloat()` to check if the argument is a number. @@ -922,6 +997,7 @@ const validateNumber = n => !isNaN(parseFloat(n)) && isFinite(n) && Number(n) == // validateNumber('10') -> true ``` +[⬆ back to top](#table-of-contents) ### Value or default Returns value, or default value if passed value is `falsy`. @@ -931,6 +1007,7 @@ const valueOrDefault = (value, d) => value || d; // valueOrDefault(NaN, 30) -> 30 ``` +[⬆ back to top](#table-of-contents) ## Credits *Icons made by [Smashicons](https://www.flaticon.com/authors/smashicons) from [www.flaticon.com](https://www.flaticon.com/) is licensed by [CC 3.0 BY](http://creativecommons.org/licenses/by/3.0/).* diff --git a/scripts/builder.js b/scripts/builder.js index b9a5d5bc8..220469705 100644 --- a/scripts/builder.js +++ b/scripts/builder.js @@ -45,7 +45,7 @@ try { output += `* [${snippet[0][0].toUpperCase() + snippet[0].replace(/-/g,' ').slice(1,snippet[0].length-3)}](#${snippet[0].slice(0,snippet[0].length-3).replace(/\(/g,'').replace(/\)/g,'').toLowerCase()})\n` output += '\n'; for(var snippet of Object.entries(snippets)) - output += `${snippet[1]+'\n'}`; + output += `${snippet[1]+'\n[⬆ back to top](#table-of-contents)\n'}`; output += `${endPart+'\n'}`; fs.writeFileSync('README.md', output); } diff --git a/static-parts/README-start.md b/static-parts/README-start.md index 1bfdbba0e..6a6504483 100644 --- a/static-parts/README-start.md +++ b/static-parts/README-start.md @@ -7,4 +7,4 @@ - Contributions welcome, please read the [contribution guide](CONTRIBUTING.md). - Snippets are written in ES6, use the [Babel transpiler](https://babeljs.io/) to ensure backwards-compatibility. -## Contents +## Table of Contents From 7de373b34f03a9402c72b4ebef2ce0e581905256 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 13:10:06 +0200 Subject: [PATCH 17/92] Add isArray --- README.md | 12 ++++++++++++ snippets/is-array.md | 9 +++++++++ 2 files changed, 21 insertions(+) create mode 100644 snippets/is-array.md diff --git a/README.md b/README.md index 7e3df18b7..b838a8f6c 100644 --- a/README.md +++ b/README.md @@ -47,6 +47,7 @@ * [Initial of list](#initial-of-list) * [Initialize array with range](#initialize-array-with-range) * [Initialize array with values](#initialize-array-with-values) +* [Is array](#is-array) * [Is boolean](#is-boolean) * [Is function](#is-function) * [Is number](#is-number) @@ -538,6 +539,17 @@ const initializeArray = (n, value = 0) => Array(n).fill(value); // initializeArray(5, 2) -> [2,2,2,2,2] ``` +[⬆ back to top](#table-of-contents) +### Is array + +Use `Array.isArray()` to check if a value is classified as an array. + +```js +const isArray = val => val && Array.isArray(val); +// isArray(null) -> false +// isArray([1]) -> true +``` + [⬆ back to top](#table-of-contents) ### Is boolean diff --git a/snippets/is-array.md b/snippets/is-array.md new file mode 100644 index 000000000..7652f74c9 --- /dev/null +++ b/snippets/is-array.md @@ -0,0 +1,9 @@ +### Is array + +Use `Array.isArray()` to check if a value is classified as an array. + +```js +const isArray = val => val && Array.isArray(val); +// isArray(null) -> false +// isArray([1]) -> true +``` From 1e0f46cb6c7753093e03d365dfce08a96d89db8c Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 13:17:20 +0200 Subject: [PATCH 18/92] Fix typo --- README.md | 8 ++++---- snippets/element-is-visible-in-viewport.md | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index b838a8f6c..3d80a141b 100644 --- a/README.md +++ b/README.md @@ -329,8 +329,8 @@ const dropElements = (arr,func) => { [⬆ back to top](#table-of-contents) ### Element is visible in viewport -Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values -to determine if a given element is visible in the viewport. +Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values +to determine if a given element is visible in the viewport. Omit the second argument to determine if the element is entirely visible, or specify `true` to determine if it is partially visible. @@ -343,8 +343,8 @@ const elementIsVisibleInViewport = (el, partiallyVisible = false) => { : top >= 0 && left >= 0 && bottom <= innerHeight && right <= innerWidth; } // e.g. 100x100 viewport and a 10x10px element at position {top: -1, left: 0, bottom: 9, right: 10} -// elementIsInViewport(el) -> false (not fully visible) -// elementIsInViewport(el, true) -> true (partially visible) +// elementIsVisibleInViewport(el) -> false (not fully visible) +// elementIsVisibleInViewport(el, true) -> true (partially visible) ``` [⬆ back to top](#table-of-contents) diff --git a/snippets/element-is-visible-in-viewport.md b/snippets/element-is-visible-in-viewport.md index 68a690d0d..70ff83134 100644 --- a/snippets/element-is-visible-in-viewport.md +++ b/snippets/element-is-visible-in-viewport.md @@ -1,7 +1,7 @@ ### Element is visible in viewport -Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values -to determine if a given element is visible in the viewport. +Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values +to determine if a given element is visible in the viewport. Omit the second argument to determine if the element is entirely visible, or specify `true` to determine if it is partially visible. @@ -14,6 +14,6 @@ const elementIsVisibleInViewport = (el, partiallyVisible = false) => { : top >= 0 && left >= 0 && bottom <= innerHeight && right <= innerWidth; } // e.g. 100x100 viewport and a 10x10px element at position {top: -1, left: 0, bottom: 9, right: 10} -// elementIsInViewport(el) -> false (not fully visible) -// elementIsInViewport(el, true) -> true (partially visible) +// elementIsVisibleInViewport(el) -> false (not fully visible) +// elementIsVisibleInViewport(el, true) -> true (partially visible) ``` From ac5c3d3f15d976db43bafe612074d47ebae08ae8 Mon Sep 17 00:00:00 2001 From: Alberto Schiabel Date: Thu, 14 Dec 2017 12:43:44 +0100 Subject: [PATCH 19/92] Fixed typo Is boolean => Is function --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 3d80a141b..1fb118d6f 100644 --- a/README.md +++ b/README.md @@ -562,7 +562,7 @@ const isBoolean = val => typeof val === 'boolean'; ``` [⬆ back to top](#table-of-contents) -### Is boolean +### Is function Use `typeof` to check if a value is classified as a function primitive. From 54dc5e9e39b6b7384f3e265ecfa9ac4517010ae4 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 13:46:06 +0200 Subject: [PATCH 20/92] Update is-function.md --- snippets/is-function.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/is-function.md b/snippets/is-function.md index a406ee543..d4247a512 100644 --- a/snippets/is-function.md +++ b/snippets/is-function.md @@ -1,4 +1,4 @@ -### Is boolean +### Is function Use `typeof` to check if a value is classified as a function primitive. From c54c4db01836a2606ba839464c8d525f4d531042 Mon Sep 17 00:00:00 2001 From: Leandro Franciscato Date: Thu, 14 Dec 2017 10:36:36 -0200 Subject: [PATCH 21/92] Adding get-days-difference-between-dates --- README.md | 13 ++++++++++++- snippets/get-days-difference-between-dates.md | 8 ++++++++ 2 files changed, 20 insertions(+), 1 deletion(-) create mode 100644 snippets/get-days-difference-between-dates.md diff --git a/README.md b/README.md index 1fb118d6f..9552e9f29 100644 --- a/README.md +++ b/README.md @@ -36,6 +36,7 @@ * [Fibonacci array generator](#fibonacci-array-generator) * [Filter out non unique values in an array](#filter-out-non-unique-values-in-an-array) * [Flatten array](#flatten-array) +* [Get days difference between dates](#get-days-difference-between-dates) * [Get max value from array](#get-max-value-from-array) * [Get min value from array](#get-min-value-from-array) * [Get native type of value](#get-native-type-of-value) @@ -66,7 +67,7 @@ * [Promisify](#promisify) * [Random integer in range](#random-integer-in-range) * [Random number in range](#random-number-in-range) -* [Redirect to URL](#redirect-to-url) +* [Redirect to url](#redirect-to-url) * [Reverse a string](#reverse-a-string) * [RGB to hexadecimal](#rgb-to-hexadecimal) * [Run promises in series](#run-promises-in-series) @@ -412,6 +413,16 @@ const flatten = arr => arr.reduce((a, v) => a.concat(v), []); // flatten([1,[2],3,4]) -> [1,2,3,4] ``` +[⬆ back to top](#table-of-contents) +### Get Days Difference Between Dates + +Returns the number of days between two Dates. + +```js +const getDaysDiffBetweenDates = (dateInitial, dateFinal) => (dateFinal - dateInitial) / (1000 * 3600 * 24); +//getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 +``` + [⬆ back to top](#table-of-contents) ### Get max value from array diff --git a/snippets/get-days-difference-between-dates.md b/snippets/get-days-difference-between-dates.md new file mode 100644 index 000000000..152cd7167 --- /dev/null +++ b/snippets/get-days-difference-between-dates.md @@ -0,0 +1,8 @@ +### Get Days Difference Between Dates + +Returns the number of days between two Dates. + +```js +const getDaysDiffBetweenDates = (dateInitial, dateFinal) => (dateFinal - dateInitial) / (1000 * 3600 * 24); +//getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 +``` From 114fd89732662af46807de041fbed8bd76d989af Mon Sep 17 00:00:00 2001 From: Christian Bender Date: Thu, 14 Dec 2017 13:48:57 +0100 Subject: [PATCH 22/92] changed I changed 'javascript' in 'js' --- snippets/collatz.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/collatz.md b/snippets/collatz.md index 120f96e27..f92718b6c 100644 --- a/snippets/collatz.md +++ b/snippets/collatz.md @@ -3,7 +3,7 @@ If n even then returns **n/2** otherwise (n is odd) **3n+1**. It uses the ternary operator. -``` javascript +``` js const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); // collatz(8) --> 4 // collatz(5) --> 16 From 44feb706cd537c5979cd5b837e0b904d4a78961f Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 14:51:44 +0200 Subject: [PATCH 23/92] Update and rename collatz.md to collatz-algorithm.md --- snippets/collatz-algorithm.md | 9 +++++++++ snippets/collatz.md | 11 ----------- 2 files changed, 9 insertions(+), 11 deletions(-) create mode 100644 snippets/collatz-algorithm.md delete mode 100644 snippets/collatz.md diff --git a/snippets/collatz-algorithm.md b/snippets/collatz-algorithm.md new file mode 100644 index 000000000..730bdd9e3 --- /dev/null +++ b/snippets/collatz-algorithm.md @@ -0,0 +1,9 @@ +### Collatz algorithm + +If `n` is even, return `n/2`. Otherwise return `3n+1`. + +```js +const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); +// collatz(8) --> 4 +// collatz(5) --> 16 +``` diff --git a/snippets/collatz.md b/snippets/collatz.md deleted file mode 100644 index f92718b6c..000000000 --- a/snippets/collatz.md +++ /dev/null @@ -1,11 +0,0 @@ -### Collatz algorithm - -If n even then returns **n/2** otherwise (n is odd) **3n+1**. -It uses the ternary operator. - -``` js - const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); - // collatz(8) --> 4 - // collatz(5) --> 16 - -``` \ No newline at end of file From 76fc2317d3a79010153f9939b828f1c17d25a415 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 14:53:37 +0200 Subject: [PATCH 24/92] Build README --- README.md | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/README.md b/README.md index 1fb118d6f..2fccd2d85 100644 --- a/README.md +++ b/README.md @@ -21,6 +21,7 @@ * [Chain asynchronous functions](#chain-asynchronous-functions) * [Check for palindrome](#check-for-palindrome) * [Chunk array](#chunk-array) +* [Collatz algorithm](#collatz-algorithm) * [Compact](#compact) * [Count occurrences of a value in array](#count-occurrences-of-a-value-in-array) * [Current URL](#current-url) @@ -230,6 +231,17 @@ const chunk = (arr, size) => // chunk([1,2,3,4,5], 2) -> [[1,2],[3,4],5] ``` +[⬆ back to top](#table-of-contents) +### Collatz algorithm + +If `n` is even, return `n/2`. Otherwise return `3n+1`. + +```js +const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); +// collatz(8) --> 4 +// collatz(5) --> 16 +``` + [⬆ back to top](#table-of-contents) ### Compact From c42ed5f746a573536ec2bc798e4416e34d582bb5 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 15:41:40 +0200 Subject: [PATCH 25/92] Create fill-array.md --- snippets/fill-array.md | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 snippets/fill-array.md diff --git a/snippets/fill-array.md b/snippets/fill-array.md new file mode 100644 index 000000000..a08c4362e --- /dev/null +++ b/snippets/fill-array.md @@ -0,0 +1,10 @@ +### Fill array + +Use `Array.map()` to map values between `start` (inclusive) and `end` (exclusive) to `value`. +Omit `start` to start at the first element and/or `end` to finish at the last. + +```js +const fillArray = (arr, value, start = 0, end = arr.length) => + arr.map((v,i) => i>=start && i [1,'8','8',4] +``` From 22331697df69b65ac7ed619dd6608a454574ae3d Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 16:10:43 +0200 Subject: [PATCH 26/92] Create flatten-array-up-to-depth.md In reference to #100. --- snippets/flatten-array-up-to-depth.md | 13 +++++++++++++ 1 file changed, 13 insertions(+) create mode 100644 snippets/flatten-array-up-to-depth.md diff --git a/snippets/flatten-array-up-to-depth.md b/snippets/flatten-array-up-to-depth.md new file mode 100644 index 000000000..d28af98fb --- /dev/null +++ b/snippets/flatten-array-up-to-depth.md @@ -0,0 +1,13 @@ +### Flatten array up to depth + +Use recursion, decrementing `depth` by 1 for each level of depth. +Use `Array.reduce()` and `Array.concat()` to merge elements or arrays. +Base case, for `depth` equal to `1` stops recursion. +Omit the second element, `depth` to flatten only to a depth of `1` (single flatten). + +```js +const flattenDepth = (arr, depth = 1) => + depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth (v, depth-1) : v), []) + : arr.reduce((a,v) => a.concat(v),[]); +// flattenDepth([1,[2],[[[3],4],5]], 2) -> [1,2,[3],4,5] +``` From adbba8810a291e9c20656a4cb5cce4534f599e49 Mon Sep 17 00:00:00 2001 From: iamsoorena Date: Thu, 14 Dec 2017 18:00:15 +0330 Subject: [PATCH 27/92] add json to file function --- snippets/write-json-to-file.md | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 snippets/write-json-to-file.md diff --git a/snippets/write-json-to-file.md b/snippets/write-json-to-file.md new file mode 100644 index 000000000..6a0ae21a0 --- /dev/null +++ b/snippets/write-json-to-file.md @@ -0,0 +1,9 @@ +### Write a JSON to a file + +Write a `json` object to a `.json` file. +```js +const fs = require('fs') + +const jsonToFile = (obj, filename) => fs.writeFile(`${filename}.json`, JSON.stringify(obj, null, 4)) +// jsonToFile({test: "is passed"}, 'testJsonFile') +``` From 4ae535d46deadf5b410452db6d734f6c00dc4f20 Mon Sep 17 00:00:00 2001 From: Elder Henrique Souza Date: Thu, 14 Dec 2017 12:57:03 -0200 Subject: [PATCH 28/92] minor refactor to group by --- snippets/group-by.md | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/snippets/group-by.md b/snippets/group-by.md index ab833c9d2..44505eb2f 100644 --- a/snippets/group-by.md +++ b/snippets/group-by.md @@ -5,10 +5,9 @@ Use `Array.reduce()` to create an object, where the keys are produced from the m ```js const groupBy = (arr, func) => - (typeof func === 'function' ? arr.map(func) : arr.map(val => val[func])) - .reduce((acc, val, i) => { - acc[val] = acc[val] === undefined ? [arr[i]] : acc[val].concat(arr[i]); return acc; - }, {}); + arr + .map(typeof func === 'function' ? func : val => val[func]) + .reduce((acc, val, i) => { acc[val] = (acc[val] || []).concat(arr[i]); return acc; }, {}) // groupBy([6.1, 4.2, 6.3], Math.floor) -> {4: [4.2], 6: [6.1, 6.3]} // groupBy(['one', 'two', 'three'], 'length') -> {3: ['one', 'two'], 5: ['three']} ``` From 21b8b18f6bec3f7fca5aa29c668a86be1d160799 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 16:59:30 +0200 Subject: [PATCH 29/92] Update group-by.md --- snippets/group-by.md | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/snippets/group-by.md b/snippets/group-by.md index 44505eb2f..ec8074ea2 100644 --- a/snippets/group-by.md +++ b/snippets/group-by.md @@ -5,9 +5,8 @@ Use `Array.reduce()` to create an object, where the keys are produced from the m ```js const groupBy = (arr, func) => - arr - .map(typeof func === 'function' ? func : val => val[func]) - .reduce((acc, val, i) => { acc[val] = (acc[val] || []).concat(arr[i]); return acc; }, {}) + arr.map(typeof func === 'function' ? func : val => val[func]) + .reduce((acc, val, i) => { acc[val] = (acc[val] || []).concat(arr[i]); return acc; }, {}); // groupBy([6.1, 4.2, 6.3], Math.floor) -> {4: [4.2], 6: [6.1, 6.3]} // groupBy(['one', 'two', 'three'], 'length') -> {3: ['one', 'two'], 5: ['three']} ``` From 8244c204dde346fe9e6bd7864fd4ef947c274eb8 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 17:02:10 +0200 Subject: [PATCH 30/92] Build README --- README.md | 35 +++++++++++++++++++++++++++++++---- 1 file changed, 31 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 2fccd2d85..65a72b1a0 100644 --- a/README.md +++ b/README.md @@ -35,7 +35,9 @@ * [Even or odd number](#even-or-odd-number) * [Factorial](#factorial) * [Fibonacci array generator](#fibonacci-array-generator) +* [Fill array](#fill-array) * [Filter out non unique values in an array](#filter-out-non-unique-values-in-an-array) +* [Flatten array up to depth](#flatten-array-up-to-depth) * [Flatten array](#flatten-array) * [Get max value from array](#get-max-value-from-array) * [Get min value from array](#get-min-value-from-array) @@ -404,6 +406,18 @@ const fibonacci = n => // fibonacci(5) -> [0,1,1,2,3] ``` +[⬆ back to top](#table-of-contents) +### Fill array + +Use `Array.map()` to map values between `start` (inclusive) and `end` (exclusive) to `value`. +Omit `start` to start at the first element and/or `end` to finish at the last. + +```js +const fillArray = (arr, value, start = 0, end = arr.length) => + arr.map((v,i) => i>=start && i [1,'8','8',4] +``` + [⬆ back to top](#table-of-contents) ### Filter out non-unique values in an array @@ -414,6 +428,21 @@ const filterNonUnique = arr => arr.filter(i => arr.indexOf(i) === arr.lastIndexO // filterNonUnique([1,2,2,3,4,4,5]) -> [1,3,5] ``` +[⬆ back to top](#table-of-contents) +### Flatten array up to depth + +Use recursion, decrementing `depth` by 1 for each level of depth. +Use `Array.reduce()` and `Array.concat()` to merge elements or arrays. +Base case, for `depth` equal to `1` stops recursion. +Omit the second element, `depth` to flatten only to a depth of `1` (single flatten). + +```js +const flattenDepth = (arr, depth = 1) => + depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth (v, depth-1) : v), []) + : arr.reduce((a,v) => a.concat(v),[]); +// flattenDepth([1,[2],[[[3],4],5]], 2) -> [1,2,[3],4,5] +``` + [⬆ back to top](#table-of-contents) ### Flatten array @@ -488,10 +517,8 @@ Use `Array.reduce()` to create an object, where the keys are produced from the m ```js const groupBy = (arr, func) => - (typeof func === 'function' ? arr.map(func) : arr.map(val => val[func])) - .reduce((acc, val, i) => { - acc[val] = acc[val] === undefined ? [arr[i]] : acc[val].concat(arr[i]); return acc; - }, {}); + arr.map(typeof func === 'function' ? func : val => val[func]) + .reduce((acc, val, i) => { acc[val] = (acc[val] || []).concat(arr[i]); return acc; }, {}); // groupBy([6.1, 4.2, 6.3], Math.floor) -> {4: [4.2], 6: [6.1, 6.3]} // groupBy(['one', 'two', 'three'], 'length') -> {3: ['one', 'two'], 5: ['three']} ``` From 99b900853cf82910be517647ecbafc2bc11b8d8b Mon Sep 17 00:00:00 2001 From: iamsoorena Date: Thu, 14 Dec 2017 18:34:05 +0330 Subject: [PATCH 31/92] add a functions that deeply cleans json objects from unwanted keys --- snippets/json-cleaner.md | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) create mode 100644 snippets/json-cleaner.md diff --git a/snippets/json-cleaner.md b/snippets/json-cleaner.md new file mode 100644 index 000000000..46ef745dc --- /dev/null +++ b/snippets/json-cleaner.md @@ -0,0 +1,20 @@ +### Clean Json objects + +Clean your json object from unwanted keys, deeply. +provide set of `keys` to keep and an indicator for `children` if there is any. + +```js +const cleanObj = (obj, keys = [], childIndicator) => { + Object.keys(obj).forEach(key => { + if (key === childIndicator) { + cleanObj(obj[key], keys, childIndicator) + } else if (!keys.includes(key)) { + delete obj[key] + } + }) +} +/* + dirtyObj = { a: 1, b: 2, children: {a: 1, b :2}} + let cleaned = cleanObj(dirtyObj, [a]) // { a: 1, children : { a: 1}} + */ +``` From e9e63a96304251247b0b437e5fde762819008540 Mon Sep 17 00:00:00 2001 From: Elder Henrique Souza Date: Thu, 14 Dec 2017 13:11:45 -0200 Subject: [PATCH 32/92] minor refactor to curry --- snippets/curry.md | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/snippets/curry.md b/snippets/curry.md index edb95461f..b47492721 100644 --- a/snippets/curry.md +++ b/snippets/curry.md @@ -6,13 +6,10 @@ Otherwise return a curried function `f` that expects the rest of the arguments. If you want to curry a function that accepts a variable number of arguments (a variadic function, e.g. `Math.min()`), you can optionally pass the number of arguments to the second parameter `arity`. ```js -const curry = (f, arity = f.length, next) => - (next = prevArgs => - nextArg => { - const args = [ ...prevArgs, nextArg ]; - return args.length >= arity ? f(...args) : next(args); - } - )([]); +const curry = (fn, arity = fn.length, ...args) => + arity <= args.length + ? fn(...args) + : curry.bind(null, fn, arity, ...args) // curry(Math.pow)(2)(10) -> 1024 // curry(Math.min, 3)(10)(50)(2) -> 2 ``` From b106585c08d53e324b902a319ecba5e450d486de Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stefan=20Feje=C5=A1?= Date: Thu, 14 Dec 2017 16:25:35 +0100 Subject: [PATCH 33/92] Fix grammar and spelling --- CONTRIBUTING.md | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index db1670488..d2bdbf7e1 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -12,9 +12,9 @@ Here's what you can do to help: ### Snippet submission and Pull request guidelines - **DO NOT MODIFY THE README.md FILE!** Make changes to individual snippet files. You can optionally run `npm run build-list` to update the README.md file automatically, based on the changes you have made. -- **Snippet filenames** must correspond to the title of the snippet. For example if your snippet is titled `### Awesome snippet` the filename should be `awesome-snippet.md`. +- **Snippet filenames** must correspond to the title of the snippet. For example, if your snippet is titled `### Awesome snippet` the filename should be `awesome-snippet.md`. - Use `kebab-case`, not `snake_case`. - - Avoid capitalization of words, except if the whole word is capitalized (e.g `URL` should be capitalized in the filename and the snippet title). + - Avoid capitalization of words, except if the whole word is capitalized (e.g. `URL` should be capitalized in the filename and the snippet title). - If there are parentheses in the title, add them to the filename (e.g. `awesome-snippet-(extra-awesome).md` if your snippet's title is `Awesome snippet (extra awesome)`). - **Snippet titles** should have only the first letter of the first word capitalized. Certain words can be in capitals (e.g. `URL`, `RGB`), but this is on a per-snippet basis. - All snippet titles must be prefixed with `###` and be at the very first line of your snippet. @@ -28,21 +28,21 @@ Here's what you can do to help: - Try to keep your snippets' code short and to the point. Use modern techniques and features. Make sure to test your code before submitting. - All snippets must be followed by one (more if necessary) test case after the code, on a new line, in the form of a comment, along with the expected output. The syntax for this is `myFunction('testInput') -> 'testOutput'`. Use multiline comments only if necessary. - Try to make your function name unique, so that it does not conflict with existing snippets. -- Snippets should be short (usually below 10 lines). If your snippet is longer than that, you can still submit it and we can help you shorten it or figure out ways to improve it. +- Snippets should be short (usually below 10 lines). If your snippet is longer than that, you can still submit it, and we can help you shorten it or figure out ways to improve it. - Snippets *should* solve real-world problems, no matter how simple. - Snippets *should* be abstract enough to be applied to different scenarios. -- It is not mandatory, but highly appreciated if you provide **test cases** and/or performance tests (we recommend using [jsPerf](https://jsperf.com/)). +- It is not mandatory but highly appreciated if you provide **test cases** and/or performance tests (we recommend using [jsPerf](https://jsperf.com/)). - You can start creating a new snippet, by using the [snippet template](snippet-template.md) to format your snippets. ### Additional guidelines and conventions regarding snippets - When describing snippets, refer to methods, using their full name. For example, use `Array.reduce()`, instead of `reduce()`. -- If your snippet contains argument with default parameters, explain what happens if they are ommited when calling the function and what the default case is. +- If your snippet contains argument with default parameters, explain what happens if they are omitted when calling the function and what the default case is. - If your snippet uses recursion, explain the base cases. - Always use `const functionName` for function definitions. -- Use variables only when necessary. Prefer `const` when the values are not altered after assignment, otherwise use `let`. Avoid using `var`. +- Use variables only when necessary. Prefer `const` when the values are not altered after assignment, otherwise, use `let`. Avoid using `var`. - Use `camelCase` for function and variable names if they consist of more than one word. -- Try to give meaningful names to variables. For example use `letter`, instead of `lt`. Some exceptions by convention are: +- Try to give meaningful names to variables. For example use `letter`, instead of `lt`. Some exceptions to convention are: - `arr` for arrays (usually as the snippet function's argument). - `str` for strings. - `n` for a numeric value (usually as the snippet function's argument). @@ -54,7 +54,7 @@ Here's what you can do to help: - `func` for function arguments. - `nums` for arrays of numbers. - Use `_` if your function takes no arguments or if an argument inside some function (e.g. `Array.reduce()`) is not used anywhere in your code. -- Specify default parameters for arguments, if necessary. It is preferred to put default parameters last, unless you have pretty good reason not to. +- Specify default parameters for arguments, if necessary. It is preferred to put default parameters last unless you have pretty good reason not to. - If your snippet's function takes variadic arguments, use `..args` (although in certain cases, it might be needed to use a different name). - If your snippet function's body is a single statement, omit the `return` keyword and use an expression instead. - Always use soft tabs (2 spaces), never hard tabs. @@ -72,5 +72,5 @@ Here's what you can do to help: - Use arrow functions as much as possible, except when you can't. - Use semicolons whenever necessary. If your snippet function's body is a single statement, return an expression and add a semicolon at the end. - Leave a single space after a comma (`,`) character. -- Try to strike a balance between readability, brevity and performance. +- Try to strike a balance between readability, brevity, and performance. - Never use `eval()`. Your snippet will be disqualified immediately. From 4a71bb886ff5b39e3fb809a7a86abc3cbda410fd Mon Sep 17 00:00:00 2001 From: Marcel Michau Date: Thu, 14 Dec 2017 17:53:32 +0200 Subject: [PATCH 34/92] Minor grammar fix in array-concatenation snippet & rebuilt README --- README.md | 4 ++-- snippets/array-concatenation.md | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 65a72b1a0..ba2c3d8bd 100644 --- a/README.md +++ b/README.md @@ -69,7 +69,7 @@ * [Promisify](#promisify) * [Random integer in range](#random-integer-in-range) * [Random number in range](#random-number-in-range) -* [Redirect to URL](#redirect-to-url) +* [Redirect to url](#redirect-to-url) * [Reverse a string](#reverse-a-string) * [RGB to hexadecimal](#rgb-to-hexadecimal) * [Run promises in series](#run-promises-in-series) @@ -110,7 +110,7 @@ const anagrams = str => { [⬆ back to top](#table-of-contents) ### Array concatenation -Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. +Use `Array.concat()` to concatenate an array with any additional arrays and/or values, specified in `args`. ```js const arrayConcat = (arr, ...args) => arr.concat(...args); diff --git a/snippets/array-concatenation.md b/snippets/array-concatenation.md index b4e2fa205..992036905 100644 --- a/snippets/array-concatenation.md +++ b/snippets/array-concatenation.md @@ -1,6 +1,6 @@ ### Array concatenation -Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. +Use `Array.concat()` to concatenate an array with any additional arrays and/or values, specified in `args`. ```js const arrayConcat = (arr, ...args) => arr.concat(...args); From e5c1d29ce6d074e90f7dd5094e0c3d649bb44a04 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 17:56:12 +0200 Subject: [PATCH 35/92] Added tagger script, tagged snippets retroactively --- package-lock.json | 65 ++-- package.json | 5 +- scripts/tagger.js | 70 ++++ snippets/take.md | 1 - tag_database | 81 ++++ yarn.lock | 913 +++++++++++++++++++++++++++++++++++++++++++++- 6 files changed, 1080 insertions(+), 55 deletions(-) create mode 100644 scripts/tagger.js create mode 100644 tag_database diff --git a/package-lock.json b/package-lock.json index be8bcab8d..4344c4b9b 100644 --- a/package-lock.json +++ b/package-lock.json @@ -65,16 +65,6 @@ "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-1.4.0.tgz", "integrity": "sha1-06ioOzGapneTZisT52HHkRQiMG4=" }, - "ansi-regex": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-0.2.1.tgz", - "integrity": "sha1-DY6UaWej2BQ/k+JOKYUl/BsiNfk=" - }, - "ansi-styles": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-1.1.0.tgz", - "integrity": "sha1-6uy/Zs1waIJ2Cy9GkVgrj1XXp94=" - }, "anymatch": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-1.3.2.tgz", @@ -333,21 +323,39 @@ "integrity": "sha1-Sm+gc5nCa7pH8LJJa00PtAjFVQ0=" }, "chalk": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-0.5.1.tgz", - "integrity": "sha1-Zjs6ZItotV0EaQ1JFnqoN4WPIXQ=", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.0.tgz", + "integrity": "sha512-Az5zJR2CBujap2rqXGaJKaPHyJ0IrUimvYNX+ncCy8PJP4ltOGTrHUIo097ZaL2zMeKYpiCdqDvS6zdrTFok3Q==", + "dev": true, "requires": { - "ansi-styles": "1.1.0", + "ansi-styles": "3.2.0", "escape-string-regexp": "1.0.5", - "has-ansi": "0.1.0", - "strip-ansi": "0.3.0", - "supports-color": "0.2.0" + "supports-color": "4.5.0" }, "dependencies": { + "ansi-styles": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", + "integrity": "sha512-NnSOmMEYtVR2JVMIGTzynRkkaxtiq1xnFBcdQD/DnNCYPoEPsVJhM98BDyaoNOQIi7p4okdi3E27eN7GQbsUug==", + "dev": true, + "requires": { + "color-convert": "1.9.1" + } + }, + "has-flag": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", + "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", + "dev": true + }, "supports-color": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-0.2.0.tgz", - "integrity": "sha1-2S3iaU6z9nMjlz1649i1W0wiGQo=" + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", + "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", + "dev": true, + "requires": { + "has-flag": "2.0.0" + } } } }, @@ -442,7 +450,6 @@ "resolved": "https://registry.npmjs.org/concurrently/-/concurrently-3.5.1.tgz", "integrity": "sha512-689HrwGw8Rbk1xtV9C4dY6TPJAvIYZbRbnKSAtfJ7tHqICFGoZ0PCWYjxfmerRyxBG0o3sbG3pe7N8vqPwIHuQ==", "requires": { - "chalk": "0.5.1", "commander": "2.6.0", "date-fns": "1.29.0", "lodash": "4.17.4", @@ -1346,14 +1353,6 @@ "function-bind": "1.1.1" } }, - "has-ansi": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-0.1.0.tgz", - "integrity": "sha1-hPJlqujA5qiKEtcCKJS3VoiUxi4=", - "requires": { - "ansi-regex": "0.2.1" - } - }, "has-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", @@ -2855,14 +2854,6 @@ "safe-buffer": "5.1.1" } }, - "strip-ansi": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-0.3.0.tgz", - "integrity": "sha1-JfSOoiynkYfzF0pNuHWTR7sSYiA=", - "requires": { - "ansi-regex": "0.2.1" - } - }, "strip-bom": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", diff --git a/package.json b/package.json index a616c02d0..2e12c8aac 100644 --- a/package.json +++ b/package.json @@ -11,10 +11,13 @@ "description": "A collection of useful Javascript snippets.", "version": "1.0.0", "main": "index.js", - "devDependencies": {}, + "devDependencies": { + "chalk": "^2.3.0" + }, "scripts": { "build-list": "node ./scripts/builder.js", "lint": "node ./scripts/lintSnippet.js", + "tag": "node ./scripts/tagger.js", "start": "concurrently --kill-others \"nodemon -e js,md -i README.md -x \\\"npm run build-list\\\"\" \"live-server ./build\"" }, "repository": { diff --git a/scripts/tagger.js b/scripts/tagger.js new file mode 100644 index 000000000..6e2329e28 --- /dev/null +++ b/scripts/tagger.js @@ -0,0 +1,70 @@ +var fs = require('fs-extra'); +var path = require('path'); +var chalk = require('chalk'); + +var snippetsPath = './snippets'; + +var snippets = {}, output = '', tagDbData = {}, missingTags = 0, tagDbStats = {}; + +const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); +const countOccurrences = (arr, value) => arr.reduce((a, v) => v === value ? a + 1 : a + 0, 0); + + +console.time('Tagger'); + +try { + var snippetFilenames = fs.readdirSync(snippetsPath); + snippetFilenames.sort((a, b) => { + a = a.toLowerCase(); + b = b.toLowerCase(); + if (a < b) { + return -1; + } + if (a > b) { + return 1; + } + return 0; + }); + for(var snippet of snippetFilenames){ + snippets[snippet] = fs.readFileSync(path.join(snippetsPath,snippet),'utf8'); + } +} +catch (err){ + console.log('Error during snippet loading: '+err); + process.exit(1); +} + +try { + tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').map(v => v.split(':').slice(0,2))); + // for(var tag of [...new Set(Object.entries(tagDbData).map(x => x[1]))]) + // tagDbStats[tag] = Object.values(tagDbData).filter(v => v === tag); + // console.log(tagDbStats); + tagDbStats = Object.entries(tagDbData).reduce((acc, val) => {acc.hasOwnProperty(val[1]) ? acc[val[1]]++ : acc[val[1]] = 1; return acc;}, {}); +} +catch (err){ + console.log('Error during tag database loading: '+err); + process.exit(1); +} + +try { + for(var snippet of Object.entries(snippets)) + if(tagDbData.hasOwnProperty(snippet[0].slice(0,-3)) && tagDbData[snippet[0].slice(0,-3)].trim()) + output += `${snippet[0].slice(0,-3)}:${tagDbData[snippet[0].slice(0,-3)].trim()}\n`; + else { + output += `${snippet[0].slice(0,-3)}:\n`; + missingTags++; + console.log(`${chalk.red('Tag missing:')} ${snippet[0].slice(0,-3)}`); + } + fs.writeFileSync('tag_database', output); +} +catch (err){ + console.log('Error during README generation: '+err); + process.exit(1); +} +console.log(`\n===Tag database statistics===`) +for(var tagData of Object.entries(tagDbStats).filter(v => v[0] !== 'undefined')){ + console.log(`${chalk.green(tagData[0])}: ${tagData[1]} snippets`); +} +console.log(`${chalk.blue('Untagged snippets:')} ${missingTags}\n`); + +console.timeEnd('Tagger'); diff --git a/snippets/take.md b/snippets/take.md index 80142031d..44d6ff0bc 100644 --- a/snippets/take.md +++ b/snippets/take.md @@ -4,7 +4,6 @@ Use `Array.slice()` to create a slice of the array with `n` elements taken from ```js const take = (arr, n = 1) => arr.slice(0, n); - // take([1, 2, 3], 5) -> [1, 2, 3] // take([1, 2, 3], 0) -> [] ``` diff --git a/tag_database b/tag_database new file mode 100644 index 000000000..5619a0369 --- /dev/null +++ b/tag_database @@ -0,0 +1,81 @@ +anagrams-of-string-(with-duplicates):string +array-concatenation:array +array-difference:array +array-intersection:array +array-union:array +average-of-array-of-numbers:array +bottom-visible:browser +capitalize-first-letter-of-every-word:string +capitalize-first-letter:string +chain-asynchronous-functions:function +check-for-palindrome:string +chunk-array:array +collatz-algorithm:math +compact:array +count-occurrences-of-a-value-in-array:array +current-URL:browser +curry:function +deep-flatten-array:array +distance-between-two-points:math +divisible-by-number:math +drop-elements-in-array:array +element-is-visible-in-viewport:browser +escape-regular-expression:utility +even-or-odd-number:math +factorial:math +fibonacci-array-generator:math +fill-array:array +filter-out-non-unique-values-in-an-array:array +flatten-array-up-to-depth:array +flatten-array:array +get-max-value-from-array:array +get-min-value-from-array:array +get-native-type-of-value:utility +get-scroll-position:browser +greatest-common-divisor-(GCD):math +group-by:array +hamming-distance:math +head-of-list:array +initial-of-list:array +initialize-array-with-range:array +initialize-array-with-values:array +is-array:utility +is-boolean:utility +is-function:utility +is-number:utility +is-string:utility +is-symbol:utility +last-of-list:array +measure-time-taken-by-function:utility +median-of-array-of-numbers:array +object-from-key-value-pairs:object +object-to-key-value-pairs:object +ordinal-suffix-of-number:utility +percentile:math +pick:array +pipe:function +powerset:math +promisify:function +random-integer-in-range:utility +random-number-in-range:utility +redirect-to-URL:browser +reverse-a-string:string +RGB-to-hexadecimal:utility +run-promises-in-series:function +scroll-to-top:browser +shuffle-array:array +similarity-between-arrays:array +sleep:function +sort-characters-in-string-(alphabetical):string +standard-deviation:math +sum-of-array-of-numbers:array +swap-values-of-two-variables:utility +tail-of-list:array +take:array +truncate-a-string:string +unique-values-of-array:array +URL-parameters:utility +UUID-generator:utility +validate-email:utility +validate-number:utility +value-or-default:utility diff --git a/yarn.lock b/yarn.lock index b5f1f6579..9dc4ac57e 100644 --- a/yarn.lock +++ b/yarn.lock @@ -13,7 +13,25 @@ accepts@~1.3.4: mime-types "~2.1.16" negotiator "0.6.1" -ajv@^4.9.1: +acorn-jsx@^3.0.0: + version "3.0.1" + resolved "https://registry.yarnpkg.com/acorn-jsx/-/acorn-jsx-3.0.1.tgz#afdf9488fb1ecefc8348f6fb22f464e32a58b36b" + dependencies: + acorn "^3.0.4" + +acorn@^3.0.4: + version "3.3.0" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-3.3.0.tgz#45e37fb39e8da3f25baee3ff5369e2bb5f22017a" + +acorn@^5.2.1: + version "5.2.1" + resolved "https://registry.yarnpkg.com/acorn/-/acorn-5.2.1.tgz#317ac7821826c22c702d66189ab8359675f135d7" + +ajv-keywords@^1.0.0: + version "1.5.1" + resolved "https://registry.yarnpkg.com/ajv-keywords/-/ajv-keywords-1.5.1.tgz#314dd0a4b3368fad3dfcdc54ede6171b886daf3c" + +ajv@^4.7.0, ajv@^4.9.1: version "4.11.8" resolved "https://registry.yarnpkg.com/ajv/-/ajv-4.11.8.tgz#82ffb02b29e662ae53bdc20af15947706739c536" dependencies: @@ -26,6 +44,10 @@ ansi-align@^2.0.0: dependencies: string-width "^2.0.0" +ansi-escapes@^1.1.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/ansi-escapes/-/ansi-escapes-1.4.0.tgz#d3a8a83b319aa67793662b13e761c7911422306e" + ansi-regex@^0.2.0, ansi-regex@^0.2.1: version "0.2.1" resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-0.2.1.tgz#0d8e946967a3d8143f93e24e298525fc1b2235f9" @@ -42,6 +64,10 @@ ansi-styles@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-1.1.0.tgz#eaecbf66cd706882760b2f4691582b8f55d7a7de" +ansi-styles@^2.2.1: + version "2.2.1" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-2.2.1.tgz#b432dd3358b634cf75e1e4664368240533c1ddbe" + ansi-styles@^3.1.0: version "3.2.0" resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-3.2.0.tgz#c159b8d5be0f9e5a6f346dab94f16ce022161b88" @@ -92,10 +118,31 @@ arr-flatten@^1.0.1: version "1.1.0" resolved "https://registry.yarnpkg.com/arr-flatten/-/arr-flatten-1.1.0.tgz#36048bbff4e7b47e136644316c99669ea5ae91f1" +array-union@^1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/array-union/-/array-union-1.0.2.tgz#9a34410e4f4e3da23dea375be5be70f24778ec39" + dependencies: + array-uniq "^1.0.1" + +array-uniq@^1.0.1: + version "1.0.3" + resolved "https://registry.yarnpkg.com/array-uniq/-/array-uniq-1.0.3.tgz#af6ac877a25cc7f74e058894753858dfdb24fdb6" + array-unique@^0.2.1: version "0.2.1" resolved "https://registry.yarnpkg.com/array-unique/-/array-unique-0.2.1.tgz#a1d97ccafcbc2625cc70fadceb36a50c58b01a53" +array.prototype.find@^2.0.1: + version "2.0.4" + resolved "https://registry.yarnpkg.com/array.prototype.find/-/array.prototype.find-2.0.4.tgz#556a5c5362c08648323ddaeb9de9d14bc1864c90" + dependencies: + define-properties "^1.1.2" + es-abstract "^1.7.0" + +arrify@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/arrify/-/arrify-1.0.1.tgz#898508da2226f380df904728456849c1501a4b0d" + asn1@~0.2.3: version "0.2.3" resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.3.tgz#dac8787713c9966849fc8180777ebe9c1ddf3b86" @@ -124,6 +171,14 @@ aws4@^1.2.1: version "1.6.0" resolved "https://registry.yarnpkg.com/aws4/-/aws4-1.6.0.tgz#83ef5ca860b2b32e4a0deedee8c771b9db57471e" +babel-code-frame@^6.16.0: + version "6.26.0" + resolved "https://registry.yarnpkg.com/babel-code-frame/-/babel-code-frame-6.26.0.tgz#63fd43f7dc1e3bb7ce35947db8fe369a3f58c74b" + dependencies: + chalk "^1.1.3" + esutils "^2.0.2" + js-tokens "^3.0.2" + balanced-match@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.0.tgz#89b4d199ab2bee49de164ea02b89ce462d71b767" @@ -191,6 +246,20 @@ braces@^1.8.2: preserve "^0.2.0" repeat-element "^1.1.2" +builtin-modules@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-1.1.1.tgz#270f076c5a72c02f5b65a47df94c5fe3a278892f" + +caller-path@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/caller-path/-/caller-path-0.1.0.tgz#94085ef63581ecd3daa92444a8fe94e82577751f" + dependencies: + callsites "^0.2.0" + +callsites@^0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/callsites/-/callsites-0.2.0.tgz#afab96262910a7f33c19a5775825c69f34e350ca" + camelcase@^4.0.0: version "4.1.0" resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-4.1.0.tgz#d545635be1e33c542649c69173e5de6acfae34dd" @@ -213,7 +282,17 @@ chalk@0.5.1: strip-ansi "^0.3.0" supports-color "^0.2.0" -chalk@^2.0.1: +chalk@^1.0.0, chalk@^1.1.1, chalk@^1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/chalk/-/chalk-1.1.3.tgz#a8115c55e4a702fe4d150abd3872822a7e09fc98" + dependencies: + ansi-styles "^2.2.1" + escape-string-regexp "^1.0.2" + has-ansi "^2.0.0" + strip-ansi "^3.0.0" + supports-color "^2.0.0" + +chalk@^2.0.1, chalk@^2.3.0: version "2.3.0" resolved "https://registry.yarnpkg.com/chalk/-/chalk-2.3.0.tgz#b5ea48efc9c1793dccc9b4767c93914d3f2d52ba" dependencies: @@ -236,10 +315,24 @@ chokidar@^1.6.0, chokidar@^1.7.0: optionalDependencies: fsevents "^1.0.0" +circular-json@^0.3.1: + version "0.3.3" + resolved "https://registry.yarnpkg.com/circular-json/-/circular-json-0.3.3.tgz#815c99ea84f6809529d2f45791bdf82711352d66" + cli-boxes@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/cli-boxes/-/cli-boxes-1.0.0.tgz#4fa917c3e59c94a004cd61f8ee509da651687143" +cli-cursor@^1.0.1: + version "1.0.2" + resolved "https://registry.yarnpkg.com/cli-cursor/-/cli-cursor-1.0.2.tgz#64da3f7d56a54412e59794bd62dc35295e8f2987" + dependencies: + restore-cursor "^1.0.1" + +cli-width@^2.0.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/cli-width/-/cli-width-2.2.0.tgz#ff19ede8a9a5e579324147b0c11f0fbcbabed639" + co@^4.6.0: version "4.6.0" resolved "https://registry.yarnpkg.com/co/-/co-4.6.0.tgz#6ea6bdf3d853ae54ccb8e47bfa0bf3f9031fb184" @@ -276,6 +369,14 @@ concat-map@0.0.1: version "0.0.1" resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" +concat-stream@^1.5.2: + version "1.6.0" + resolved "https://registry.yarnpkg.com/concat-stream/-/concat-stream-1.6.0.tgz#0aac662fd52be78964d5532f694784e70110acf7" + dependencies: + inherits "^2.0.3" + readable-stream "^2.2.2" + typedarray "^0.0.6" + concurrently@^3.5.1: version "3.5.1" resolved "https://registry.yarnpkg.com/concurrently/-/concurrently-3.5.1.tgz#ee8b60018bbe86b02df13e5249453c6ececd2521" @@ -313,6 +414,10 @@ console-control-strings@^1.0.0, console-control-strings@~1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/console-control-strings/-/console-control-strings-1.1.0.tgz#3d7cf4464db6446ea644bf4b39507f9851008e8e" +contains-path@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/contains-path/-/contains-path-0.1.0.tgz#fe8cf184ff6670b6baef01a9d4861a5cbec4120a" + core-util-is@1.0.2, core-util-is@~1.0.0: version "1.0.2" resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7" @@ -348,6 +453,12 @@ crypto-random-string@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/crypto-random-string/-/crypto-random-string-1.0.0.tgz#a230f64f568310e1498009940790ec99545bca7e" +d@1: + version "1.0.0" + resolved "https://registry.yarnpkg.com/d/-/d-1.0.0.tgz#754bb5bfe55451da69a58b94d45f4c5b0462d58f" + dependencies: + es5-ext "^0.10.9" + dashdash@^1.12.0: version "1.14.1" resolved "https://registry.yarnpkg.com/dashdash/-/dashdash-1.14.1.tgz#853cfa0f7cbe2fed5de20326b8dd581035f6e2f0" @@ -358,7 +469,11 @@ date-fns@^1.23.0: version "1.29.0" resolved "https://registry.yarnpkg.com/date-fns/-/date-fns-1.29.0.tgz#12e609cdcb935127311d04d33334e2960a2a54e6" -debug@2.6.9, debug@^2.2.0, debug@^2.6.8: +debug-log@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/debug-log/-/debug-log-1.0.1.tgz#2307632d4c04382b8df8a32f70b895046d52745f" + +debug@2.6.9, debug@^2.1.1, debug@^2.2.0, debug@^2.6.8: version "2.6.9" resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f" dependencies: @@ -374,6 +489,40 @@ deep-extend@~0.4.0: version "0.4.2" resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.4.2.tgz#48b699c27e334bf89f10892be432f6e4c7d34a7f" +deep-is@~0.1.3: + version "0.1.3" + resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.3.tgz#b369d6fb5dbc13eecf524f91b070feedc357cf34" + +define-properties@^1.1.2: + version "1.1.2" + resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.1.2.tgz#83a73f2fea569898fb737193c8f873caf6d45c94" + dependencies: + foreach "^2.0.5" + object-keys "^1.0.8" + +deglob@^2.1.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/deglob/-/deglob-2.1.0.tgz#4d44abe16ef32c779b4972bd141a80325029a14a" + dependencies: + find-root "^1.0.0" + glob "^7.0.5" + ignore "^3.0.9" + pkg-config "^1.1.0" + run-parallel "^1.1.2" + uniq "^1.0.1" + +del@^2.0.2: + version "2.2.2" + resolved "https://registry.yarnpkg.com/del/-/del-2.2.2.tgz#c12c981d067846c84bcaf862cff930d907ffd1a8" + dependencies: + globby "^5.0.0" + is-path-cwd "^1.0.0" + is-path-in-cwd "^1.0.0" + object-assign "^4.0.1" + pify "^2.0.0" + pinkie-promise "^2.0.0" + rimraf "^2.2.8" + delayed-stream@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/delayed-stream/-/delayed-stream-1.0.0.tgz#df3ae199acadfb7d440aaae0b29e2272b24ec619" @@ -394,6 +543,19 @@ detect-libc@^1.0.2: version "1.0.3" resolved "https://registry.yarnpkg.com/detect-libc/-/detect-libc-1.0.3.tgz#fa137c4bd698edf55cd5cd02ac559f91a4c4ba9b" +doctrine@1.5.0, doctrine@^1.2.2: + version "1.5.0" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-1.5.0.tgz#379dce730f6166f76cefa4e6707a159b02c5a6fa" + dependencies: + esutils "^2.0.2" + isarray "^1.0.0" + +doctrine@^2.0.0: + version "2.0.2" + resolved "https://registry.yarnpkg.com/doctrine/-/doctrine-2.0.2.tgz#68f96ce8efc56cc42651f1faadb4f175273b0075" + dependencies: + esutils "^2.0.2" + dot-prop@^4.1.0: version "4.2.0" resolved "https://registry.yarnpkg.com/dot-prop/-/dot-prop-4.2.0.tgz#1f19e0c2e1aa0e32797c49799f2837ac6af69c57" @@ -426,22 +588,256 @@ entities@~1.1.1: version "1.1.1" resolved "https://registry.yarnpkg.com/entities/-/entities-1.1.1.tgz#6e5c2d0a5621b5dadaecef80b90edfb5cd7772f0" +error-ex@^1.2.0: + version "1.3.1" + resolved "https://registry.yarnpkg.com/error-ex/-/error-ex-1.3.1.tgz#f855a86ce61adc4e8621c3cda21e7a7612c3a8dc" + dependencies: + is-arrayish "^0.2.1" + +es-abstract@^1.7.0: + version "1.10.0" + resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.10.0.tgz#1ecb36c197842a00d8ee4c2dfd8646bb97d60864" + dependencies: + es-to-primitive "^1.1.1" + function-bind "^1.1.1" + has "^1.0.1" + is-callable "^1.1.3" + is-regex "^1.0.4" + +es-to-primitive@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.1.1.tgz#45355248a88979034b6792e19bb81f2b7975dd0d" + dependencies: + is-callable "^1.1.1" + is-date-object "^1.0.1" + is-symbol "^1.0.1" + +es5-ext@^0.10.14, es5-ext@^0.10.35, es5-ext@^0.10.9, es5-ext@~0.10.14: + version "0.10.37" + resolved "https://registry.yarnpkg.com/es5-ext/-/es5-ext-0.10.37.tgz#0ee741d148b80069ba27d020393756af257defc3" + dependencies: + es6-iterator "~2.0.1" + es6-symbol "~3.1.1" + +es6-iterator@^2.0.1, es6-iterator@~2.0.1: + version "2.0.3" + resolved "https://registry.yarnpkg.com/es6-iterator/-/es6-iterator-2.0.3.tgz#a7de889141a05a94b0854403b2d0a0fbfa98f3b7" + dependencies: + d "1" + es5-ext "^0.10.35" + es6-symbol "^3.1.1" + +es6-map@^0.1.3: + version "0.1.5" + resolved "https://registry.yarnpkg.com/es6-map/-/es6-map-0.1.5.tgz#9136e0503dcc06a301690f0bb14ff4e364e949f0" + dependencies: + d "1" + es5-ext "~0.10.14" + es6-iterator "~2.0.1" + es6-set "~0.1.5" + es6-symbol "~3.1.1" + event-emitter "~0.3.5" + es6-promise@^3.3.1: version "3.3.1" resolved "https://registry.yarnpkg.com/es6-promise/-/es6-promise-3.3.1.tgz#a08cdde84ccdbf34d027a1451bc91d4bcd28a613" +es6-set@~0.1.5: + version "0.1.5" + resolved "https://registry.yarnpkg.com/es6-set/-/es6-set-0.1.5.tgz#d2b3ec5d4d800ced818db538d28974db0a73ccb1" + dependencies: + d "1" + es5-ext "~0.10.14" + es6-iterator "~2.0.1" + es6-symbol "3.1.1" + event-emitter "~0.3.5" + +es6-symbol@3.1.1, es6-symbol@^3.1.1, es6-symbol@~3.1.1: + version "3.1.1" + resolved "https://registry.yarnpkg.com/es6-symbol/-/es6-symbol-3.1.1.tgz#bf00ef4fdab6ba1b46ecb7b629b4c7ed5715cc77" + dependencies: + d "1" + es5-ext "~0.10.14" + +es6-weak-map@^2.0.1: + version "2.0.2" + resolved "https://registry.yarnpkg.com/es6-weak-map/-/es6-weak-map-2.0.2.tgz#5e3ab32251ffd1538a1f8e5ffa1357772f92d96f" + dependencies: + d "1" + es5-ext "^0.10.14" + es6-iterator "^2.0.1" + es6-symbol "^3.1.1" + escape-html@~1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/escape-html/-/escape-html-1.0.3.tgz#0258eae4d3d0c0974de1c169188ef0051d1d1988" -escape-string-regexp@^1.0.0, escape-string-regexp@^1.0.5: +escape-string-regexp@^1.0.0, escape-string-regexp@^1.0.2, escape-string-regexp@^1.0.5: version "1.0.5" resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" +escope@^3.6.0: + version "3.6.0" + resolved "https://registry.yarnpkg.com/escope/-/escope-3.6.0.tgz#e01975e812781a163a6dadfdd80398dc64c889c3" + dependencies: + es6-map "^0.1.3" + es6-weak-map "^2.0.1" + esrecurse "^4.1.0" + estraverse "^4.1.1" + +eslint-config-semistandard@^11.0.0: + version "11.0.0" + resolved "https://registry.yarnpkg.com/eslint-config-semistandard/-/eslint-config-semistandard-11.0.0.tgz#44eef7cfdfd47219e3a7b81b91b540e880bb2615" + +eslint-config-standard-jsx@4.0.1: + version "4.0.1" + resolved "https://registry.yarnpkg.com/eslint-config-standard-jsx/-/eslint-config-standard-jsx-4.0.1.tgz#cd4e463d0268e2d9e707f61f42f73f5b3333c642" + +eslint-config-standard@^10.2.1: + version "10.2.1" + resolved "https://registry.yarnpkg.com/eslint-config-standard/-/eslint-config-standard-10.2.1.tgz#c061e4d066f379dc17cd562c64e819b4dd454591" + +eslint-import-resolver-node@^0.2.0: + version "0.2.3" + resolved "https://registry.yarnpkg.com/eslint-import-resolver-node/-/eslint-import-resolver-node-0.2.3.tgz#5add8106e8c928db2cba232bcd9efa846e3da16c" + dependencies: + debug "^2.2.0" + object-assign "^4.0.1" + resolve "^1.1.6" + +eslint-module-utils@^2.0.0: + version "2.1.1" + resolved "https://registry.yarnpkg.com/eslint-module-utils/-/eslint-module-utils-2.1.1.tgz#abaec824177613b8a95b299639e1b6facf473449" + dependencies: + debug "^2.6.8" + pkg-dir "^1.0.0" + +eslint-plugin-import@~2.2.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/eslint-plugin-import/-/eslint-plugin-import-2.2.0.tgz#72ba306fad305d67c4816348a4699a4229ac8b4e" + dependencies: + builtin-modules "^1.1.1" + contains-path "^0.1.0" + debug "^2.2.0" + doctrine "1.5.0" + eslint-import-resolver-node "^0.2.0" + eslint-module-utils "^2.0.0" + has "^1.0.1" + lodash.cond "^4.3.0" + minimatch "^3.0.3" + pkg-up "^1.0.0" + +eslint-plugin-node@~4.2.2: + version "4.2.3" + resolved "https://registry.yarnpkg.com/eslint-plugin-node/-/eslint-plugin-node-4.2.3.tgz#c04390ab8dbcbb6887174023d6f3a72769e63b97" + dependencies: + ignore "^3.0.11" + minimatch "^3.0.2" + object-assign "^4.0.1" + resolve "^1.1.7" + semver "5.3.0" + +eslint-plugin-promise@~3.5.0: + version "3.5.0" + resolved "https://registry.yarnpkg.com/eslint-plugin-promise/-/eslint-plugin-promise-3.5.0.tgz#78fbb6ffe047201627569e85a6c5373af2a68fca" + +eslint-plugin-react@~6.10.0: + version "6.10.3" + resolved "https://registry.yarnpkg.com/eslint-plugin-react/-/eslint-plugin-react-6.10.3.tgz#c5435beb06774e12c7db2f6abaddcbf900cd3f78" + dependencies: + array.prototype.find "^2.0.1" + doctrine "^1.2.2" + has "^1.0.1" + jsx-ast-utils "^1.3.4" + object.assign "^4.0.4" + +eslint-plugin-standard@~3.0.1: + version "3.0.1" + resolved "https://registry.yarnpkg.com/eslint-plugin-standard/-/eslint-plugin-standard-3.0.1.tgz#34d0c915b45edc6f010393c7eef3823b08565cf2" + +eslint@~3.19.0: + version "3.19.0" + resolved "https://registry.yarnpkg.com/eslint/-/eslint-3.19.0.tgz#c8fc6201c7f40dd08941b87c085767386a679acc" + dependencies: + babel-code-frame "^6.16.0" + chalk "^1.1.3" + concat-stream "^1.5.2" + debug "^2.1.1" + doctrine "^2.0.0" + escope "^3.6.0" + espree "^3.4.0" + esquery "^1.0.0" + estraverse "^4.2.0" + esutils "^2.0.2" + file-entry-cache "^2.0.0" + glob "^7.0.3" + globals "^9.14.0" + ignore "^3.2.0" + imurmurhash "^0.1.4" + inquirer "^0.12.0" + is-my-json-valid "^2.10.0" + is-resolvable "^1.0.0" + js-yaml "^3.5.1" + json-stable-stringify "^1.0.0" + levn "^0.3.0" + lodash "^4.0.0" + mkdirp "^0.5.0" + natural-compare "^1.4.0" + optionator "^0.8.2" + path-is-inside "^1.0.1" + pluralize "^1.2.1" + progress "^1.1.8" + require-uncached "^1.0.2" + shelljs "^0.7.5" + strip-bom "^3.0.0" + strip-json-comments "~2.0.1" + table "^3.7.8" + text-table "~0.2.0" + user-home "^2.0.0" + +espree@^3.4.0: + version "3.5.2" + resolved "https://registry.yarnpkg.com/espree/-/espree-3.5.2.tgz#756ada8b979e9dcfcdb30aad8d1a9304a905e1ca" + dependencies: + acorn "^5.2.1" + acorn-jsx "^3.0.0" + +esprima@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.0.tgz#4499eddcd1110e0b218bacf2fa7f7f59f55ca804" + +esquery@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/esquery/-/esquery-1.0.0.tgz#cfba8b57d7fba93f17298a8a006a04cda13d80fa" + dependencies: + estraverse "^4.0.0" + +esrecurse@^4.1.0: + version "4.2.0" + resolved "https://registry.yarnpkg.com/esrecurse/-/esrecurse-4.2.0.tgz#fa9568d98d3823f9a41d91e902dcab9ea6e5b163" + dependencies: + estraverse "^4.1.0" + object-assign "^4.0.1" + +estraverse@^4.0.0, estraverse@^4.1.0, estraverse@^4.1.1, estraverse@^4.2.0: + version "4.2.0" + resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-4.2.0.tgz#0dee3fed31fcd469618ce7342099fc1afa0bdb13" + +esutils@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/esutils/-/esutils-2.0.2.tgz#0abf4f1caa5bcb1f7a9d8acc6dea4faaa04bac9b" + etag@~1.8.1: version "1.8.1" resolved "https://registry.yarnpkg.com/etag/-/etag-1.8.1.tgz#41ae2eeb65efa62268aebfea83ac7d79299b0887" +event-emitter@~0.3.5: + version "0.3.5" + resolved "https://registry.yarnpkg.com/event-emitter/-/event-emitter-0.3.5.tgz#df8c69eef1647923c7157b9ce83840610b02cc39" + dependencies: + d "1" + es5-ext "~0.10.14" + event-stream@latest, event-stream@~3.3.0: version "3.3.4" resolved "https://registry.yarnpkg.com/event-stream/-/event-stream-3.3.4.tgz#4ab4c9a0f5a54db9338b4c34d86bfce8f4b35571" @@ -466,6 +862,10 @@ execa@^0.7.0: signal-exit "^3.0.0" strip-eof "^1.0.0" +exit-hook@^1.0.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/exit-hook/-/exit-hook-1.1.1.tgz#f05ca233b48c05d54fff07765df8507e95c02ff8" + expand-brackets@^0.1.4: version "0.1.5" resolved "https://registry.yarnpkg.com/expand-brackets/-/expand-brackets-0.1.5.tgz#df07284e342a807cd733ac5af72411e581d1177b" @@ -492,12 +892,30 @@ extsprintf@1.3.0, extsprintf@^1.2.0: version "1.3.0" resolved "https://registry.yarnpkg.com/extsprintf/-/extsprintf-1.3.0.tgz#96918440e3041a7a414f8c52e3c574eb3c3e1e05" +fast-levenshtein@~2.0.4: + version "2.0.6" + resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917" + faye-websocket@0.11.x: version "0.11.1" resolved "https://registry.yarnpkg.com/faye-websocket/-/faye-websocket-0.11.1.tgz#f0efe18c4f56e4f40afc7e06c719fd5ee6188f38" dependencies: websocket-driver ">=0.5.1" +figures@^1.3.5: + version "1.7.0" + resolved "https://registry.yarnpkg.com/figures/-/figures-1.7.0.tgz#cbe1e3affcf1cd44b80cadfed28dc793a9701d2e" + dependencies: + escape-string-regexp "^1.0.5" + object-assign "^4.1.0" + +file-entry-cache@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/file-entry-cache/-/file-entry-cache-2.0.0.tgz#c392990c3e684783d838b8c84a45d8a048458361" + dependencies: + flat-cache "^1.2.1" + object-assign "^4.0.1" + filename-regex@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26" @@ -522,6 +940,32 @@ finalhandler@0.5.1: statuses "~1.3.1" unpipe "~1.0.0" +find-root@^1.0.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/find-root/-/find-root-1.1.0.tgz#abcfc8ba76f708c42a97b3d685b7e9450bfb9ce4" + +find-up@^1.0.0: + version "1.1.2" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-1.1.2.tgz#6b2e9822b1a2ce0a60ab64d610eccad53cb24d0f" + dependencies: + path-exists "^2.0.0" + pinkie-promise "^2.0.0" + +find-up@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/find-up/-/find-up-2.1.0.tgz#45d1b7e506c717ddd482775a2b77920a3c0c57a7" + dependencies: + locate-path "^2.0.0" + +flat-cache@^1.2.1: + version "1.3.0" + resolved "https://registry.yarnpkg.com/flat-cache/-/flat-cache-1.3.0.tgz#d3030b32b38154f4e3b7e9c709f490f7ef97c481" + dependencies: + circular-json "^0.3.1" + del "^2.0.2" + graceful-fs "^4.1.2" + write "^0.2.1" + for-in@^1.0.1: version "1.0.2" resolved "https://registry.yarnpkg.com/for-in/-/for-in-1.0.2.tgz#81068d295a8142ec0ac726c6e2200c30fb6d5e80" @@ -532,6 +976,10 @@ for-own@^0.1.4: dependencies: for-in "^1.0.1" +foreach@^2.0.5: + version "2.0.5" + resolved "https://registry.yarnpkg.com/foreach/-/foreach-2.0.5.tgz#0bee005018aeb260d0a3af3ae658dd0136ec1b99" + forever-agent@~0.6.1: version "0.6.1" resolved "https://registry.yarnpkg.com/forever-agent/-/forever-agent-0.6.1.tgz#fbc71f0c41adeb37f96c577ad1ed42d8fdacca91" @@ -588,6 +1036,10 @@ fstream@^1.0.0, fstream@^1.0.10, fstream@^1.0.2: mkdirp ">=0.5 0" rimraf "2" +function-bind@^1.0.2, function-bind@^1.1.0, function-bind@^1.1.1: + version "1.1.1" + resolved "https://registry.yarnpkg.com/function-bind/-/function-bind-1.1.1.tgz#a56899d3ea3c9bab874bb9773b7c5ede92f4895d" + gauge@~2.7.3: version "2.7.4" resolved "https://registry.yarnpkg.com/gauge/-/gauge-2.7.4.tgz#2c03405c7538c39d7eb37b317022e325fb018bf7" @@ -601,6 +1053,20 @@ gauge@~2.7.3: strip-ansi "^3.0.1" wide-align "^1.1.0" +generate-function@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/generate-function/-/generate-function-2.0.0.tgz#6858fe7c0969b7d4e9093337647ac79f60dfbe74" + +generate-object-property@^1.1.0: + version "1.2.0" + resolved "https://registry.yarnpkg.com/generate-object-property/-/generate-object-property-1.2.0.tgz#9c0e1c40308ce804f4783618b937fa88f99d50d0" + dependencies: + is-property "^1.0.0" + +get-stdin@^5.0.1: + version "5.0.1" + resolved "https://registry.yarnpkg.com/get-stdin/-/get-stdin-5.0.1.tgz#122e161591e21ff4c52530305693f20e6393a398" + get-stream@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/get-stream/-/get-stream-3.0.0.tgz#8e943d1358dc37555054ecbe2edb05aa174ede14" @@ -624,7 +1090,7 @@ glob-parent@^2.0.0: dependencies: is-glob "^2.0.0" -glob@^7.0.5: +glob@^7.0.0, glob@^7.0.3, glob@^7.0.5: version "7.1.2" resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.2.tgz#c19c9df9a028702d678612384a6552404c636d15" dependencies: @@ -641,6 +1107,21 @@ global-dirs@^0.1.0: dependencies: ini "^1.3.4" +globals@^9.14.0: + version "9.18.0" + resolved "https://registry.yarnpkg.com/globals/-/globals-9.18.0.tgz#aa3896b3e69b487f17e31ed2143d69a8e30c2d8a" + +globby@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/globby/-/globby-5.0.0.tgz#ebd84667ca0dbb330b99bcfc68eac2bc54370e0d" + dependencies: + array-union "^1.0.1" + arrify "^1.0.0" + glob "^7.0.3" + object-assign "^4.0.1" + pify "^2.0.0" + pinkie-promise "^2.0.0" + got@^6.7.1: version "6.7.1" resolved "https://registry.yarnpkg.com/got/-/got-6.7.1.tgz#240cd05785a9a18e561dc1b44b41c763ef1e8db0" @@ -678,6 +1159,12 @@ has-ansi@^0.1.0: dependencies: ansi-regex "^0.2.0" +has-ansi@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/has-ansi/-/has-ansi-2.0.0.tgz#34f5049ce1ecdf2b0649af3ef24e45ed35416d91" + dependencies: + ansi-regex "^2.0.0" + has-flag@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-1.0.0.tgz#9d9e793165ce017a00f00418c43f942a7b1d11fa" @@ -690,6 +1177,12 @@ has-unicode@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/has-unicode/-/has-unicode-2.0.1.tgz#e0e6fe6a28cf51138855e086d1691e771de2a8b9" +has@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/has/-/has-1.0.1.tgz#8461733f538b0837c9361e39a9ab9e9704dc2f28" + dependencies: + function-bind "^1.0.2" + hawk@3.1.3, hawk@~3.1.3: version "3.1.3" resolved "https://registry.yarnpkg.com/hawk/-/hawk-3.1.3.tgz#078444bd7c1640b0fe540d2c9b73d59678e8e1c4" @@ -737,6 +1230,10 @@ ignore-by-default@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/ignore-by-default/-/ignore-by-default-1.0.1.tgz#48ca6d72f6c6a3af00a9ad4ae6876be3889e2b09" +ignore@^3.0.11, ignore@^3.0.9, ignore@^3.2.0: + version "3.3.7" + resolved "https://registry.yarnpkg.com/ignore/-/ignore-3.3.7.tgz#612289bfb3c220e186a58118618d5be8c1bab021" + import-lazy@^2.1.0: version "2.1.0" resolved "https://registry.yarnpkg.com/import-lazy/-/import-lazy-2.1.0.tgz#05698e3d45c88e8d7e9d92cb0584e77f096f3e43" @@ -752,7 +1249,7 @@ inflight@^1.0.4: once "^1.3.0" wrappy "1" -inherits@2, inherits@2.0.3, inherits@^2.0.1, inherits@~2.0.0, inherits@~2.0.3: +inherits@2, inherits@2.0.3, inherits@^2.0.1, inherits@^2.0.3, inherits@~2.0.0, inherits@~2.0.3: version "2.0.3" resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.3.tgz#633c2c83e3da42a502f52466022480f4208261de" @@ -760,6 +1257,32 @@ ini@^1.3.4, ini@~1.3.0: version "1.3.5" resolved "https://registry.yarnpkg.com/ini/-/ini-1.3.5.tgz#eee25f56db1c9ec6085e0c22778083f596abf927" +inquirer@^0.12.0: + version "0.12.0" + resolved "https://registry.yarnpkg.com/inquirer/-/inquirer-0.12.0.tgz#1ef2bfd63504df0bc75785fff8c2c41df12f077e" + dependencies: + ansi-escapes "^1.1.0" + ansi-regex "^2.0.0" + chalk "^1.0.0" + cli-cursor "^1.0.1" + cli-width "^2.0.0" + figures "^1.3.5" + lodash "^4.3.0" + readline2 "^1.0.1" + run-async "^0.1.0" + rx-lite "^3.1.2" + string-width "^1.0.1" + strip-ansi "^3.0.0" + through "^2.3.6" + +interpret@^1.0.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/interpret/-/interpret-1.1.0.tgz#7ed1b1410c6a0e0f78cf95d3b8440c63f78b8614" + +is-arrayish@^0.2.1: + version "0.2.1" + resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.2.1.tgz#77c99840527aa8ecb1a8ba697b80645a7a926a9d" + is-binary-path@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-1.0.1.tgz#75f16642b480f187a711c814161fd3a4a7655898" @@ -770,6 +1293,14 @@ is-buffer@^1.1.5: version "1.1.6" resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-1.1.6.tgz#efaa2ea9daa0d7ab2ea13a97b2b8ad51fefbe8be" +is-callable@^1.1.1, is-callable@^1.1.3: + version "1.1.3" + resolved "https://registry.yarnpkg.com/is-callable/-/is-callable-1.1.3.tgz#86eb75392805ddc33af71c92a0eedf74ee7604b2" + +is-date-object@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.1.tgz#9aa20eb6aeebbff77fbd33e74ca01b33581d3a16" + is-dotfile@^1.0.0: version "1.0.3" resolved "https://registry.yarnpkg.com/is-dotfile/-/is-dotfile-1.0.3.tgz#a6a2f32ffd2dfb04f5ca25ecd0f6b83cf798a1e1" @@ -811,6 +1342,15 @@ is-installed-globally@^0.1.0: global-dirs "^0.1.0" is-path-inside "^1.0.0" +is-my-json-valid@^2.10.0: + version "2.16.1" + resolved "https://registry.yarnpkg.com/is-my-json-valid/-/is-my-json-valid-2.16.1.tgz#5a846777e2c2620d1e69104e5d3a03b1f6088f11" + dependencies: + generate-function "^2.0.0" + generate-object-property "^1.1.0" + jsonpointer "^4.0.0" + xtend "^4.0.0" + is-npm@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-npm/-/is-npm-1.0.0.tgz#f2fb63a65e4905b406c86072765a1a4dc793b9f4" @@ -831,6 +1371,16 @@ is-obj@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/is-obj/-/is-obj-1.0.1.tgz#3e4729ac1f5fde025cd7d83a896dab9f4f67db0f" +is-path-cwd@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-path-cwd/-/is-path-cwd-1.0.0.tgz#d225ec23132e89edd38fda767472e62e65f1106d" + +is-path-in-cwd@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-path-in-cwd/-/is-path-in-cwd-1.0.0.tgz#6477582b8214d602346094567003be8a9eac04dc" + dependencies: + is-path-inside "^1.0.0" + is-path-inside@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-path-inside/-/is-path-inside-1.0.0.tgz#fc06e5a1683fbda13de667aff717bbc10a48f37f" @@ -845,10 +1395,24 @@ is-primitive@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/is-primitive/-/is-primitive-2.0.0.tgz#207bab91638499c07b2adf240a41a87210034575" +is-property@^1.0.0: + version "1.0.2" + resolved "https://registry.yarnpkg.com/is-property/-/is-property-1.0.2.tgz#57fe1c4e48474edd65b09911f26b1cd4095dda84" + is-redirect@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-redirect/-/is-redirect-1.0.0.tgz#1d03dded53bd8db0f30c26e4f95d36fc7c87dc24" +is-regex@^1.0.4: + version "1.0.4" + resolved "https://registry.yarnpkg.com/is-regex/-/is-regex-1.0.4.tgz#5517489b547091b0930e095654ced25ee97e9491" + dependencies: + has "^1.0.1" + +is-resolvable@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/is-resolvable/-/is-resolvable-1.0.1.tgz#acca1cd36dbe44b974b924321555a70ba03b1cf4" + is-retry-allowed@^1.0.0: version "1.1.0" resolved "https://registry.yarnpkg.com/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz#11a060568b67339444033d0125a61a20d564fb34" @@ -857,6 +1421,10 @@ is-stream@^1.0.0, is-stream@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-1.1.0.tgz#12d4a3dd4e68e0b79ceb8dbc84173ae80d91ca44" +is-symbol@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.1.tgz#3cc59f00025194b6ab2e38dbae6689256b660572" + is-typedarray@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a" @@ -865,7 +1433,7 @@ is-wsl@^1.1.0: version "1.1.0" resolved "https://registry.yarnpkg.com/is-wsl/-/is-wsl-1.1.0.tgz#1f16e4aa22b04d1336b66188a66af3c600c3a66d" -isarray@1.0.0, isarray@~1.0.0: +isarray@1.0.0, isarray@^1.0.0, isarray@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11" @@ -883,6 +1451,17 @@ isstream@~0.1.2: version "0.1.2" resolved "https://registry.yarnpkg.com/isstream/-/isstream-0.1.2.tgz#47e63f7af55afa6f92e1500e690eb8b8529c099a" +js-tokens@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-3.0.2.tgz#9866df395102130e38f7f996bceb65443209c25b" + +js-yaml@^3.5.1: + version "3.10.0" + resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.10.0.tgz#2e78441646bd4682e963f22b6e92823c309c62dc" + dependencies: + argparse "^1.0.7" + esprima "^4.0.0" + jsbn@~0.1.0: version "0.1.1" resolved "https://registry.yarnpkg.com/jsbn/-/jsbn-0.1.1.tgz#a5e654c2e5a2deb5f201d96cefbca80c0ef2f513" @@ -891,7 +1470,7 @@ json-schema@0.2.3: version "0.2.3" resolved "https://registry.yarnpkg.com/json-schema/-/json-schema-0.2.3.tgz#b480c892e59a2f05954ce727bd3f2a4e882f9e13" -json-stable-stringify@^1.0.1: +json-stable-stringify@^1.0.0, json-stable-stringify@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz#9a759d39c5f2ff503fd5300646ed445f88c4f9af" dependencies: @@ -911,6 +1490,10 @@ jsonify@~0.0.0: version "0.0.0" resolved "https://registry.yarnpkg.com/jsonify/-/jsonify-0.0.0.tgz#2c74b6ee41d93ca51b7b5aaee8f503631d252a73" +jsonpointer@^4.0.0: + version "4.0.1" + resolved "https://registry.yarnpkg.com/jsonpointer/-/jsonpointer-4.0.1.tgz#4fd92cb34e0e9db3c89c8622ecf51f9b978c6cb9" + jsprim@^1.2.2: version "1.4.1" resolved "https://registry.yarnpkg.com/jsprim/-/jsprim-1.4.1.tgz#313e66bc1e5cc06e438bc1b7499c2e5c56acb6a2" @@ -920,6 +1503,10 @@ jsprim@^1.2.2: json-schema "0.2.3" verror "1.10.0" +jsx-ast-utils@^1.3.4: + version "1.4.1" + resolved "https://registry.yarnpkg.com/jsx-ast-utils/-/jsx-ast-utils-1.4.1.tgz#3867213e8dd79bf1e8f2300c0cfc1efb182c0df1" + kind-of@^3.0.2: version "3.2.2" resolved "https://registry.yarnpkg.com/kind-of/-/kind-of-3.2.2.tgz#31ea21a734bab9bbb0f32466d893aea51e4a3c64" @@ -938,6 +1525,13 @@ latest-version@^3.0.0: dependencies: package-json "^4.0.0" +levn@^0.3.0, levn@~0.3.0: + version "0.3.0" + resolved "https://registry.yarnpkg.com/levn/-/levn-0.3.0.tgz#3b09924edf9f083c0490fdd4c0bc4421e04764ee" + dependencies: + prelude-ls "~1.1.2" + type-check "~0.3.2" + linkify-it@^2.0.0: version "2.0.3" resolved "https://registry.yarnpkg.com/linkify-it/-/linkify-it-2.0.3.tgz#d94a4648f9b1c179d64fa97291268bdb6ce9434f" @@ -962,6 +1556,22 @@ live-server@^1.2.0: send latest serve-index "^1.7.2" +load-json-file@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/load-json-file/-/load-json-file-2.0.0.tgz#7947e42149af80d696cbf797bcaabcfe1fe29ca8" + dependencies: + graceful-fs "^4.1.2" + parse-json "^2.2.0" + pify "^2.0.0" + strip-bom "^3.0.0" + +locate-path@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e" + dependencies: + p-locate "^2.0.0" + path-exists "^3.0.0" + lodash._baseassign@^3.0.0: version "3.2.0" resolved "https://registry.yarnpkg.com/lodash._baseassign/-/lodash._baseassign-3.2.0.tgz#8c38a099500f215ad09e59f1722fd0c52bfe0a4e" @@ -1001,6 +1611,10 @@ lodash.assign@^3.0.0: lodash._createassigner "^3.0.0" lodash.keys "^3.0.0" +lodash.cond@^4.3.0: + version "4.5.2" + resolved "https://registry.yarnpkg.com/lodash.cond/-/lodash.cond-4.5.2.tgz#f471a1da486be60f6ab955d17115523dd1d255d5" + lodash.defaults@^3.1.2: version "3.1.2" resolved "https://registry.yarnpkg.com/lodash.defaults/-/lodash.defaults-3.1.2.tgz#c7308b18dbf8bc9372d701a73493c61192bd2e2c" @@ -1028,7 +1642,7 @@ lodash.restparam@^3.0.0: version "3.6.1" resolved "https://registry.yarnpkg.com/lodash.restparam/-/lodash.restparam-3.6.1.tgz#936a4e309ef330a7645ed4145986c85ae5b20805" -lodash@^4.5.1: +lodash@^4.0.0, lodash@^4.3.0, lodash@^4.5.1: version "4.17.4" resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.4.tgz#78203a4d1c328ae1d86dca6460e369b57f4055ae" @@ -1099,7 +1713,7 @@ mime@1.4.1: version "1.4.1" resolved "https://registry.yarnpkg.com/mime/-/mime-1.4.1.tgz#121f9ebc49e3766f311a76e1fa1c8003c4b03aa6" -minimatch@^3.0.0, minimatch@^3.0.2, minimatch@^3.0.4: +minimatch@^3.0.0, minimatch@^3.0.2, minimatch@^3.0.3, minimatch@^3.0.4: version "3.0.4" resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083" dependencies: @@ -1109,11 +1723,11 @@ minimist@0.0.8: version "0.0.8" resolved "https://registry.yarnpkg.com/minimist/-/minimist-0.0.8.tgz#857fcabfc3397d2625b8228262e86aa7a011b05d" -minimist@^1.2.0: +minimist@^1.1.0, minimist@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.0.tgz#a35008b20f41383eec1fb914f4cd5df79a264284" -"mkdirp@>=0.5 0", mkdirp@^0.5.1: +"mkdirp@>=0.5 0", mkdirp@^0.5.0, mkdirp@^0.5.1: version "0.5.1" resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.1.tgz#30057438eac6cf7f8c4767f38648d6697d75c903" dependencies: @@ -1137,10 +1751,18 @@ ms@2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/ms/-/ms-2.0.0.tgz#5608aeadfc00be6c2901df5f9861788de0d597c8" +mute-stream@0.0.5: + version "0.0.5" + resolved "https://registry.yarnpkg.com/mute-stream/-/mute-stream-0.0.5.tgz#8fbfabb0a98a253d3184331f9e8deb7372fac6c0" + nan@^2.3.0: version "2.8.0" resolved "https://registry.yarnpkg.com/nan/-/nan-2.8.0.tgz#ed715f3fe9de02b57a5e6252d90a96675e1f085a" +natural-compare@^1.4.0: + version "1.4.0" + resolved "https://registry.yarnpkg.com/natural-compare/-/natural-compare-1.4.0.tgz#4abebfeed7541f2c27acfb29bdbbd15c8d5ba4f7" + negotiator@0.6.1: version "0.6.1" resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.1.tgz#2b327184e8992101177b28563fb5e7102acd0ca9" @@ -1218,10 +1840,22 @@ oauth-sign@~0.8.1: version "0.8.2" resolved "https://registry.yarnpkg.com/oauth-sign/-/oauth-sign-0.8.2.tgz#46a6ab7f0aead8deae9ec0565780b7d4efeb9d43" -object-assign@^4, object-assign@^4.1.0, object-assign@latest: +object-assign@^4, object-assign@^4.0.1, object-assign@^4.1.0, object-assign@latest: version "4.1.1" resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" +object-keys@^1.0.10, object-keys@^1.0.8: + version "1.0.11" + resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.0.11.tgz#c54601778ad560f1142ce0e01bcca8b56d13426d" + +object.assign@^4.0.4: + version "4.0.4" + resolved "https://registry.yarnpkg.com/object.assign/-/object.assign-4.0.4.tgz#b1c9cc044ef1b9fe63606fc141abbb32e14730cc" + dependencies: + define-properties "^1.1.2" + function-bind "^1.1.0" + object-keys "^1.0.10" + object.omit@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/object.omit/-/object.omit-2.0.1.tgz#1a9c744829f39dbb858c76ca3579ae2a54ebd1fa" @@ -1245,12 +1879,27 @@ once@^1.3.0, once@^1.3.3: dependencies: wrappy "1" +onetime@^1.0.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/onetime/-/onetime-1.1.0.tgz#a1f7838f8314c516f05ecefcbc4ccfe04b4ed789" + opn@latest: version "5.1.0" resolved "https://registry.yarnpkg.com/opn/-/opn-5.1.0.tgz#72ce2306a17dbea58ff1041853352b4a8fc77519" dependencies: is-wsl "^1.1.0" +optionator@^0.8.2: + version "0.8.2" + resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.8.2.tgz#364c5e409d3f4d6301d6c0b4c05bba50180aeb64" + dependencies: + deep-is "~0.1.3" + fast-levenshtein "~2.0.4" + levn "~0.3.0" + prelude-ls "~1.1.2" + type-check "~0.3.2" + wordwrap "~1.0.0" + os-homedir@^1.0.0: version "1.0.2" resolved "https://registry.yarnpkg.com/os-homedir/-/os-homedir-1.0.2.tgz#ffbc4988336e0e833de0c168c7ef152121aa7fb3" @@ -1270,6 +1919,16 @@ p-finally@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/p-finally/-/p-finally-1.0.0.tgz#3fbcfb15b899a44123b34b6dcc18b724336a2cae" +p-limit@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/p-limit/-/p-limit-1.1.0.tgz#b07ff2d9a5d88bec806035895a2bab66a27988bc" + +p-locate@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/p-locate/-/p-locate-2.0.0.tgz#20a0103b222a70c8fd39cc2e580680f3dde5ec43" + dependencies: + p-limit "^1.1.0" + package-json@^4.0.0: version "4.0.1" resolved "https://registry.yarnpkg.com/package-json/-/package-json-4.0.1.tgz#8869a0401253661c4c4ca3da6c2121ed555f5eed" @@ -1288,10 +1947,26 @@ parse-glob@^3.0.4: is-extglob "^1.0.0" is-glob "^2.0.0" +parse-json@^2.2.0: + version "2.2.0" + resolved "https://registry.yarnpkg.com/parse-json/-/parse-json-2.2.0.tgz#f480f40434ef80741f8469099f8dea18f55a4dc9" + dependencies: + error-ex "^1.2.0" + parseurl@~1.3.1, parseurl@~1.3.2: version "1.3.2" resolved "https://registry.yarnpkg.com/parseurl/-/parseurl-1.3.2.tgz#fc289d4ed8993119460c156253262cdc8de65bf3" +path-exists@^2.0.0: + version "2.1.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-2.1.0.tgz#0feb6c64f0fc518d9a754dd5efb62c7022761f4b" + dependencies: + pinkie-promise "^2.0.0" + +path-exists@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-3.0.0.tgz#ce0ebeaa5f78cb18925ea7d810d7b59b010fd515" + path-is-absolute@^1.0.0: version "1.0.1" resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" @@ -1304,6 +1979,10 @@ path-key@^2.0.0: version "2.0.1" resolved "https://registry.yarnpkg.com/path-key/-/path-key-2.0.1.tgz#411cadb574c5a140d3a4b1910d40d80cc9f40b40" +path-parse@^1.0.5: + version "1.0.5" + resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.5.tgz#3c1adf871ea9cd6c9431b6ea2bd74a0ff055c4c1" + pause-stream@0.0.11: version "0.0.11" resolved "https://registry.yarnpkg.com/pause-stream/-/pause-stream-0.0.11.tgz#fe5a34b0cbce12b5aa6a2b403ee2e73b602f1445" @@ -1314,10 +1993,59 @@ performance-now@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/performance-now/-/performance-now-0.2.0.tgz#33ef30c5c77d4ea21c5a53869d91b56d8f2555e5" +pify@^2.0.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/pify/-/pify-2.3.0.tgz#ed141a6ac043a849ea588498e7dca8b15330e90c" + pify@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/pify/-/pify-3.0.0.tgz#e5a4acd2c101fdf3d9a4d07f0dbc4db49dd28176" +pinkie-promise@^2.0.0: + version "2.0.1" + resolved "https://registry.yarnpkg.com/pinkie-promise/-/pinkie-promise-2.0.1.tgz#2135d6dfa7a358c069ac9b178776288228450ffa" + dependencies: + pinkie "^2.0.0" + +pinkie@^2.0.0: + version "2.0.4" + resolved "https://registry.yarnpkg.com/pinkie/-/pinkie-2.0.4.tgz#72556b80cfa0d48a974e80e77248e80ed4f7f870" + +pkg-conf@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/pkg-conf/-/pkg-conf-2.0.0.tgz#071c87650403bccfb9c627f58751bfe47c067279" + dependencies: + find-up "^2.0.0" + load-json-file "^2.0.0" + +pkg-config@^1.1.0: + version "1.1.1" + resolved "https://registry.yarnpkg.com/pkg-config/-/pkg-config-1.1.1.tgz#557ef22d73da3c8837107766c52eadabde298fe4" + dependencies: + debug-log "^1.0.0" + find-root "^1.0.0" + xtend "^4.0.1" + +pkg-dir@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/pkg-dir/-/pkg-dir-1.0.0.tgz#7a4b508a8d5bb2d629d447056ff4e9c9314cf3d4" + dependencies: + find-up "^1.0.0" + +pkg-up@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/pkg-up/-/pkg-up-1.0.0.tgz#3e08fb461525c4421624a33b9f7e6d0af5b05a26" + dependencies: + find-up "^1.0.0" + +pluralize@^1.2.1: + version "1.2.1" + resolved "https://registry.yarnpkg.com/pluralize/-/pluralize-1.2.1.tgz#d1a21483fd22bb41e58a12fa3421823140897c45" + +prelude-ls@~1.1.2: + version "1.1.2" + resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.1.2.tgz#21932a549f5e52ffd9a827f570e04be62a97da54" + prepend-http@^1.0.1: version "1.0.4" resolved "https://registry.yarnpkg.com/prepend-http/-/prepend-http-1.0.4.tgz#d4f4562b0ce3696e41ac52d0e002e57a635dc6dc" @@ -1330,6 +2058,10 @@ process-nextick-args@~1.0.6: version "1.0.7" resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-1.0.7.tgz#150e20b756590ad3f91093f25a4f2ad8bff30ba3" +progress@^1.1.8: + version "1.1.8" + resolved "https://registry.yarnpkg.com/progress/-/progress-1.1.8.tgz#e260c78f6161cdd9b0e56cc3e0a85de17c7a57be" + proxy-middleware@latest: version "0.15.0" resolved "https://registry.yarnpkg.com/proxy-middleware/-/proxy-middleware-0.15.0.tgz#a3fdf1befb730f951965872ac2f6074c61477a56" @@ -1372,7 +2104,7 @@ rc@^1.0.1, rc@^1.1.6, rc@^1.1.7: minimist "^1.2.0" strip-json-comments "~2.0.1" -readable-stream@^2.0.2, readable-stream@^2.0.6, readable-stream@^2.1.4: +readable-stream@^2.0.2, readable-stream@^2.0.6, readable-stream@^2.1.4, readable-stream@^2.2.2: version "2.3.3" resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.3.3.tgz#368f2512d79f9d46fdfc71349ae7878bbc1eb95c" dependencies: @@ -1393,6 +2125,20 @@ readdirp@^2.0.0: readable-stream "^2.0.2" set-immediate-shim "^1.0.1" +readline2@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/readline2/-/readline2-1.0.1.tgz#41059608ffc154757b715d9989d199ffbf372e35" + dependencies: + code-point-at "^1.0.0" + is-fullwidth-code-point "^1.0.0" + mute-stream "0.0.5" + +rechoir@^0.6.2: + version "0.6.2" + resolved "https://registry.yarnpkg.com/rechoir/-/rechoir-0.6.2.tgz#85204b54dba82d5742e28c96756ef43af50e3384" + dependencies: + resolve "^1.1.6" + regex-cache@^0.4.2: version "0.4.4" resolved "https://registry.yarnpkg.com/regex-cache/-/regex-cache-0.4.4.tgz#75bdc58a2a1496cec48a12835bc54c8d562336dd" @@ -1451,12 +2197,50 @@ request@2.81.0: tunnel-agent "^0.6.0" uuid "^3.0.0" -rimraf@2, rimraf@^2.5.1, rimraf@^2.6.1: +require-uncached@^1.0.2: + version "1.0.3" + resolved "https://registry.yarnpkg.com/require-uncached/-/require-uncached-1.0.3.tgz#4e0d56d6c9662fd31e43011c4b95aa49955421d3" + dependencies: + caller-path "^0.1.0" + resolve-from "^1.0.0" + +resolve-from@^1.0.0: + version "1.0.1" + resolved "https://registry.yarnpkg.com/resolve-from/-/resolve-from-1.0.1.tgz#26cbfe935d1aeeeabb29bc3fe5aeb01e93d44226" + +resolve@^1.1.6, resolve@^1.1.7: + version "1.5.0" + resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.5.0.tgz#1f09acce796c9a762579f31b2c1cc4c3cddf9f36" + dependencies: + path-parse "^1.0.5" + +restore-cursor@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/restore-cursor/-/restore-cursor-1.0.1.tgz#34661f46886327fed2991479152252df92daa541" + dependencies: + exit-hook "^1.0.0" + onetime "^1.0.0" + +rimraf@2, rimraf@^2.2.8, rimraf@^2.5.1, rimraf@^2.6.1: version "2.6.2" resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.2.tgz#2ed8150d24a16ea8651e6d6ef0f47c4158ce7a36" dependencies: glob "^7.0.5" +run-async@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/run-async/-/run-async-0.1.0.tgz#c8ad4a5e110661e402a7d21b530e009f25f8e389" + dependencies: + once "^1.3.0" + +run-parallel@^1.1.2: + version "1.1.6" + resolved "https://registry.yarnpkg.com/run-parallel/-/run-parallel-1.1.6.tgz#29003c9a2163e01e2d2dfc90575f2c6c1d61a039" + +rx-lite@^3.1.2: + version "3.1.2" + resolved "https://registry.yarnpkg.com/rx-lite/-/rx-lite-3.1.2.tgz#19ce502ca572665f3b647b10939f97fd1615f102" + rx@2.3.24: version "2.3.24" resolved "https://registry.yarnpkg.com/rx/-/rx-2.3.24.tgz#14f950a4217d7e35daa71bbcbe58eff68ea4b2b7" @@ -1465,12 +2249,31 @@ safe-buffer@5.1.1, safe-buffer@^5.0.1, safe-buffer@~5.1.0, safe-buffer@~5.1.1: version "5.1.1" resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.1.1.tgz#893312af69b2123def71f57889001671eeb2c853" +semistandard@^11.0.0: + version "11.0.0" + resolved "https://registry.yarnpkg.com/semistandard/-/semistandard-11.0.0.tgz#d2d9fc8ac393de21312195e006e50c8861391c47" + dependencies: + eslint "~3.19.0" + eslint-config-semistandard "^11.0.0" + eslint-config-standard "^10.2.1" + eslint-config-standard-jsx "4.0.1" + eslint-plugin-import "~2.2.0" + eslint-plugin-node "~4.2.2" + eslint-plugin-promise "~3.5.0" + eslint-plugin-react "~6.10.0" + eslint-plugin-standard "~3.0.1" + standard-engine "~7.0.0" + semver-diff@^2.0.0: version "2.1.0" resolved "https://registry.yarnpkg.com/semver-diff/-/semver-diff-2.1.0.tgz#4bbb8437c8d37e4b0cf1a68fd726ec6d645d6d36" dependencies: semver "^5.0.3" +semver@5.3.0: + version "5.3.0" + resolved "https://registry.yarnpkg.com/semver/-/semver-5.3.0.tgz#9b2ce5d3de02d17c6012ad326aa6b4d0cf54f94f" + semver@^5.0.3, semver@^5.1.0, semver@^5.3.0: version "5.4.1" resolved "https://registry.yarnpkg.com/semver/-/semver-5.4.1.tgz#e059c09d8571f0540823733433505d3a2f00b18e" @@ -1527,10 +2330,22 @@ shebang-regex@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/shebang-regex/-/shebang-regex-1.0.0.tgz#da42f49740c0b42db2ca9728571cb190c98efea3" +shelljs@^0.7.5: + version "0.7.8" + resolved "https://registry.yarnpkg.com/shelljs/-/shelljs-0.7.8.tgz#decbcf874b0d1e5fb72e14b164a9683048e9acb3" + dependencies: + glob "^7.0.0" + interpret "^1.0.0" + rechoir "^0.6.2" + signal-exit@^3.0.0, signal-exit@^3.0.2: version "3.0.2" resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.2.tgz#b5fdc08f1287ea1178628e415e25132b73646c6d" +slice-ansi@0.0.4: + version "0.0.4" + resolved "https://registry.yarnpkg.com/slice-ansi/-/slice-ansi-0.0.4.tgz#edbf8903f66f7ce2f8eafd6ceed65e264c831b35" + sntp@1.x.x: version "1.0.9" resolved "https://registry.yarnpkg.com/sntp/-/sntp-1.0.9.tgz#6541184cc90aeea6c6e7b35e2659082443c66198" @@ -1565,6 +2380,15 @@ sshpk@^1.7.0: jsbn "~0.1.0" tweetnacl "~0.14.0" +standard-engine@~7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/standard-engine/-/standard-engine-7.0.0.tgz#ebb77b9c8fc2c8165ffa353bd91ba0dff41af690" + dependencies: + deglob "^2.1.0" + get-stdin "^5.0.1" + minimist "^1.1.0" + pkg-conf "^2.0.0" + "statuses@>= 1.3.1 < 2": version "1.4.0" resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.4.0.tgz#bb73d446da2796106efcc1b601a253d6c46bd087" @@ -1622,6 +2446,10 @@ strip-ansi@^4.0.0: dependencies: ansi-regex "^3.0.0" +strip-bom@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/strip-bom/-/strip-bom-3.0.0.tgz#2334c18e9c759f7bdd56fdef7e9ae3d588e68ed3" + strip-eof@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/strip-eof/-/strip-eof-1.0.0.tgz#bb43ff5598a6eb05d89b59fcd129c983313606bf" @@ -1634,6 +2462,10 @@ supports-color@^0.2.0: version "0.2.0" resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-0.2.0.tgz#d92de2694eb3f67323973d7ae3d8b55b4c22190a" +supports-color@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-2.0.0.tgz#535d045ce6b6363fa40117084629995e9df324c7" + supports-color@^3.2.3: version "3.2.3" resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-3.2.3.tgz#65ac0504b3954171d8a64946b2ae3cbb8a5f54f6" @@ -1646,6 +2478,17 @@ supports-color@^4.0.0: dependencies: has-flag "^2.0.0" +table@^3.7.8: + version "3.8.3" + resolved "https://registry.yarnpkg.com/table/-/table-3.8.3.tgz#2bbc542f0fda9861a755d3947fefd8b3f513855f" + dependencies: + ajv "^4.7.0" + ajv-keywords "^1.0.0" + chalk "^1.1.1" + lodash "^4.0.0" + slice-ansi "0.0.4" + string-width "^2.0.0" + tar-pack@^3.4.0: version "3.4.1" resolved "https://registry.yarnpkg.com/tar-pack/-/tar-pack-3.4.1.tgz#e1dbc03a9b9d3ba07e896ad027317eb679a10a1f" @@ -1673,7 +2516,11 @@ term-size@^1.2.0: dependencies: execa "^0.7.0" -through@2, through@~2.3, through@~2.3.1: +text-table@~0.2.0: + version "0.2.0" + resolved "https://registry.yarnpkg.com/text-table/-/text-table-0.2.0.tgz#7f5ee823ae805207c00af2df4a84ec3fcfa570b4" + +through@2, through@^2.3.6, through@~2.3, through@~2.3.1: version "2.3.8" resolved "https://registry.yarnpkg.com/through/-/through-2.3.8.tgz#0dd4c9ffaabc357960b1b724115d7e0e86a2e1f5" @@ -1707,6 +2554,16 @@ tweetnacl@^0.14.3, tweetnacl@~0.14.0: version "0.14.5" resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64" +type-check@~0.3.2: + version "0.3.2" + resolved "https://registry.yarnpkg.com/type-check/-/type-check-0.3.2.tgz#5884cab512cf1d355e3fb784f30804b2b520db72" + dependencies: + prelude-ls "~1.1.2" + +typedarray@^0.0.6: + version "0.0.6" + resolved "https://registry.yarnpkg.com/typedarray/-/typedarray-0.0.6.tgz#867ac74e3864187b1d3d47d996a78ec5c8830777" + uc.micro@^1.0.1, uc.micro@^1.0.3: version "1.0.3" resolved "https://registry.yarnpkg.com/uc.micro/-/uc.micro-1.0.3.tgz#7ed50d5e0f9a9fb0a573379259f2a77458d50192" @@ -1719,6 +2576,10 @@ undefsafe@0.0.3: version "0.0.3" resolved "https://registry.yarnpkg.com/undefsafe/-/undefsafe-0.0.3.tgz#ecca3a03e56b9af17385baac812ac83b994a962f" +uniq@^1.0.1: + version "1.0.1" + resolved "https://registry.yarnpkg.com/uniq/-/uniq-1.0.1.tgz#b31c5ae8254844a3a8281541ce2b04b865a734ff" + unique-string@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/unique-string/-/unique-string-1.0.0.tgz#9e1057cca851abb93398f8b33ae187b99caec11a" @@ -1761,6 +2622,12 @@ url-parse-lax@^1.0.0: dependencies: prepend-http "^1.0.1" +user-home@^2.0.0: + version "2.0.0" + resolved "https://registry.yarnpkg.com/user-home/-/user-home-2.0.0.tgz#9c70bfd8169bc1dcbf48604e0f04b8b49cde9e9f" + dependencies: + os-homedir "^1.0.0" + util-deprecate@~1.0.1: version "1.0.2" resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" @@ -1814,6 +2681,10 @@ widest-line@^1.0.0: dependencies: string-width "^1.0.1" +wordwrap@~1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/wordwrap/-/wordwrap-1.0.0.tgz#27584810891456a4171c8d0226441ade90cbcaeb" + wrappy@1: version "1.0.2" resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" @@ -1826,10 +2697,20 @@ write-file-atomic@^2.0.0: imurmurhash "^0.1.4" signal-exit "^3.0.2" +write@^0.2.1: + version "0.2.1" + resolved "https://registry.yarnpkg.com/write/-/write-0.2.1.tgz#5fc03828e264cea3fe91455476f7a3c566cb0757" + dependencies: + mkdirp "^0.5.1" + xdg-basedir@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/xdg-basedir/-/xdg-basedir-3.0.0.tgz#496b2cc109eca8dbacfe2dc72b603c17c5870ad4" +xtend@^4.0.0, xtend@^4.0.1: + version "4.0.1" + resolved "https://registry.yarnpkg.com/xtend/-/xtend-4.0.1.tgz#a5c6d532be656e23db820efb943a1f04998d63af" + yallist@^2.1.2: version "2.1.2" resolved "https://registry.yarnpkg.com/yallist/-/yallist-2.1.2.tgz#1c11f9218f076089a47dd512f93c6699a6a81d52" From a1341458ab31a8aa457d833e48f9ccfd8ca8c519 Mon Sep 17 00:00:00 2001 From: Marcel Michau Date: Thu, 14 Dec 2017 18:01:43 +0200 Subject: [PATCH 36/92] Renamed 'redirect-to-url.md' to 'redirect-to-URL.md' to keep case consistent with other headings --- README.md | 2 +- snippets/redirect-to-url.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index ba2c3d8bd..bb4b99a85 100644 --- a/README.md +++ b/README.md @@ -69,7 +69,7 @@ * [Promisify](#promisify) * [Random integer in range](#random-integer-in-range) * [Random number in range](#random-number-in-range) -* [Redirect to url](#redirect-to-url) +* [Redirect to URL](#redirect-to-url) * [Reverse a string](#reverse-a-string) * [RGB to hexadecimal](#rgb-to-hexadecimal) * [Run promises in series](#run-promises-in-series) diff --git a/snippets/redirect-to-url.md b/snippets/redirect-to-url.md index dab1f775b..70356686f 100644 --- a/snippets/redirect-to-url.md +++ b/snippets/redirect-to-url.md @@ -5,6 +5,6 @@ Pass a second argument to simulate a link click (`true` - default) or an HTTP re ```js const redirect = (url, asLink = true) => - asLink ? window.location.href = url : window.location.replace(url); + asLink ? (window.location.href = url) : window.location.replace(url); // redirect('https://google.com') ``` From e4e8ea98dc509aee3e0938eb952e7a476d229382 Mon Sep 17 00:00:00 2001 From: Marcel Michau Date: Thu, 14 Dec 2017 18:07:29 +0200 Subject: [PATCH 37/92] Undo Prettier auto-formatting --- snippets/{redirect-to-url.md => redirect-to-URL.md} | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) rename snippets/{redirect-to-url.md => redirect-to-URL.md} (80%) diff --git a/snippets/redirect-to-url.md b/snippets/redirect-to-URL.md similarity index 80% rename from snippets/redirect-to-url.md rename to snippets/redirect-to-URL.md index 70356686f..dab1f775b 100644 --- a/snippets/redirect-to-url.md +++ b/snippets/redirect-to-URL.md @@ -5,6 +5,6 @@ Pass a second argument to simulate a link click (`true` - default) or an HTTP re ```js const redirect = (url, asLink = true) => - asLink ? (window.location.href = url) : window.location.replace(url); + asLink ? window.location.href = url : window.location.replace(url); // redirect('https://google.com') ``` From 06018e143aa086bba8081025aa4fdbcfa06955ee Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 18:24:49 +0200 Subject: [PATCH 38/92] Categorization --- README.md | 1425 +++++++++++++++++++++++--------------------- scripts/builder.js | 31 +- scripts/tagger.js | 9 +- 3 files changed, 785 insertions(+), 680 deletions(-) diff --git a/README.md b/README.md index 65a72b1a0..46fcf2e14 100644 --- a/README.md +++ b/README.md @@ -9,105 +9,103 @@ ## Table of Contents -* [Anagrams of string (with duplicates)](#anagrams-of-string-with-duplicates) +### Array * [Array concatenation](#array-concatenation) * [Array difference](#array-difference) * [Array intersection](#array-intersection) * [Array union](#array-union) * [Average of array of numbers](#average-of-array-of-numbers) -* [Bottom visible](#bottom-visible) -* [Capitalize first letter of every word](#capitalize-first-letter-of-every-word) -* [Capitalize first letter](#capitalize-first-letter) -* [Chain asynchronous functions](#chain-asynchronous-functions) -* [Check for palindrome](#check-for-palindrome) * [Chunk array](#chunk-array) -* [Collatz algorithm](#collatz-algorithm) * [Compact](#compact) * [Count occurrences of a value in array](#count-occurrences-of-a-value-in-array) -* [Current URL](#current-url) -* [Curry](#curry) * [Deep flatten array](#deep-flatten-array) -* [Distance between two points](#distance-between-two-points) -* [Divisible by number](#divisible-by-number) * [Drop elements in array](#drop-elements-in-array) -* [Element is visible in viewport](#element-is-visible-in-viewport) -* [Escape regular expression](#escape-regular-expression) -* [Even or odd number](#even-or-odd-number) -* [Factorial](#factorial) -* [Fibonacci array generator](#fibonacci-array-generator) * [Fill array](#fill-array) * [Filter out non unique values in an array](#filter-out-non-unique-values-in-an-array) * [Flatten array up to depth](#flatten-array-up-to-depth) * [Flatten array](#flatten-array) * [Get max value from array](#get-max-value-from-array) * [Get min value from array](#get-min-value-from-array) -* [Get native type of value](#get-native-type-of-value) -* [Get scroll position](#get-scroll-position) -* [Greatest common divisor (GCD)](#greatest-common-divisor-gcd) * [Group by](#group-by) -* [Hamming distance](#hamming-distance) * [Head of list](#head-of-list) * [Initial of list](#initial-of-list) * [Initialize array with range](#initialize-array-with-range) * [Initialize array with values](#initialize-array-with-values) +* [Last of list](#last-of-list) +* [Median of array of numbers](#median-of-array-of-numbers) +* [Pick](#pick) +* [Shuffle array](#shuffle-array) +* [Similarity between arrays](#similarity-between-arrays) +* [Sum of array of numbers](#sum-of-array-of-numbers) +* [Tail of list](#tail-of-list) +* [Take](#take) +* [Unique values of array](#unique-values-of-array) + +### Browser +* [Bottom visible](#bottom-visible) +* [Current URL](#current-url) +* [Element is visible in viewport](#element-is-visible-in-viewport) +* [Get scroll position](#get-scroll-position) +* [Redirect to URL](#redirect-to-url) +* [Scroll to top](#scroll-to-top) + +### Function +* [Chain asynchronous functions](#chain-asynchronous-functions) +* [Curry](#curry) +* [Pipe](#pipe) +* [Promisify](#promisify) +* [Run promises in series](#run-promises-in-series) +* [Sleep](#sleep) + +### Math +* [Collatz algorithm](#collatz-algorithm) +* [Distance between two points](#distance-between-two-points) +* [Divisible by number](#divisible-by-number) +* [Even or odd number](#even-or-odd-number) +* [Factorial](#factorial) +* [Fibonacci array generator](#fibonacci-array-generator) +* [Greatest common divisor (GCD)](#greatest-common-divisor-gcd) +* [Hamming distance](#hamming-distance) +* [Percentile](#percentile) +* [Powerset](#powerset) +* [Standard deviation](#standard-deviation) + +### Object +* [Object from key value pairs](#object-from-key-value-pairs) +* [Object to key value pairs](#object-to-key-value-pairs) + +### String +* [Anagrams of string (with duplicates)](#anagrams-of-string-with-duplicates) +* [Capitalize first letter of every word](#capitalize-first-letter-of-every-word) +* [Capitalize first letter](#capitalize-first-letter) +* [Check for palindrome](#check-for-palindrome) +* [Reverse a string](#reverse-a-string) +* [Sort characters in string (alphabetical)](#sort-characters-in-string-alphabetical) +* [Truncate a string](#truncate-a-string) + +### Utility +* [Escape regular expression](#escape-regular-expression) +* [Get native type of value](#get-native-type-of-value) * [Is array](#is-array) * [Is boolean](#is-boolean) * [Is function](#is-function) * [Is number](#is-number) * [Is string](#is-string) * [Is symbol](#is-symbol) -* [Last of list](#last-of-list) * [Measure time taken by function](#measure-time-taken-by-function) -* [Median of array of numbers](#median-of-array-of-numbers) -* [Object from key value pairs](#object-from-key-value-pairs) -* [Object to key value pairs](#object-to-key-value-pairs) * [Ordinal suffix of number](#ordinal-suffix-of-number) -* [Percentile](#percentile) -* [Pick](#pick) -* [Pipe](#pipe) -* [Powerset](#powerset) -* [Promisify](#promisify) * [Random integer in range](#random-integer-in-range) * [Random number in range](#random-number-in-range) -* [Redirect to URL](#redirect-to-url) -* [Reverse a string](#reverse-a-string) * [RGB to hexadecimal](#rgb-to-hexadecimal) -* [Run promises in series](#run-promises-in-series) -* [Scroll to top](#scroll-to-top) -* [Shuffle array](#shuffle-array) -* [Similarity between arrays](#similarity-between-arrays) -* [Sleep](#sleep) -* [Sort characters in string (alphabetical)](#sort-characters-in-string-alphabetical) -* [Standard deviation](#standard-deviation) -* [Sum of array of numbers](#sum-of-array-of-numbers) * [Swap values of two variables](#swap-values-of-two-variables) -* [Tail of list](#tail-of-list) -* [Take](#take) -* [Truncate a string](#truncate-a-string) -* [Unique values of array](#unique-values-of-array) * [URL parameters](#url-parameters) * [UUID generator](#uuid-generator) * [Validate email](#validate-email) * [Validate number](#validate-number) * [Value or default](#value-or-default) -### Anagrams of string (with duplicates) +## Array -Use recursion. -For each letter in the given string, create all the partial anagrams for the rest of its letters. -Use `Array.map()` to combine the letter with each partial anagram, then `Array.reduce()` to combine all anagrams in one array. -Base cases are for string `length` equal to `2` or `1`. - -```js -const anagrams = str => { - if (str.length <= 2) return str.length === 2 ? [str, str[1] + str[0]] : [str]; - return str.split('').reduce((acc, letter, i) => - acc.concat(anagrams(str.slice(0, i) + str.slice(i + 1)).map(val => letter + val)), []); -}; -// anagrams('abc') -> ['abc','acb','bac','bca','cab','cba'] -``` - -[⬆ back to top](#table-of-contents) ### Array concatenation Use `Array.concat()` to concatenate and array with any additional arrays and/or values, specified in `args`. @@ -118,6 +116,7 @@ const arrayConcat = (arr, ...args) => arr.concat(...args); ``` [⬆ back to top](#table-of-contents) + ### Array difference Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values not contained in `b`. @@ -128,6 +127,7 @@ const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has ``` [⬆ back to top](#table-of-contents) + ### Array intersection Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values contained in `b`. @@ -138,6 +138,7 @@ const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.ha ``` [⬆ back to top](#table-of-contents) + ### Array union Create a `Set` with all values of `a` and `b` and convert to an array. @@ -148,6 +149,7 @@ const union = (a, b) => Array.from(new Set([...a, ...b])) ``` [⬆ back to top](#table-of-contents) + ### Average of array of numbers Use `Array.reduce()` to add each value to an accumulator, initialized with a value of `0`, divide by the `length` of the array. @@ -158,69 +160,7 @@ const average = arr => arr.reduce((acc, val) => acc + val, 0) / arr.length; ``` [⬆ back to top](#table-of-contents) -### Bottom visible -Use `scrollY`, `scrollHeight` and `clientHeight` to determine if the bottom of the page is visible. - -```js -const bottomVisible = _ => - document.documentElement.clientHeight + window.scrollY >= document.documentElement.scrollHeight || document.documentElement.clientHeight; -// bottomVisible() -> true -``` - -[⬆ back to top](#table-of-contents) -### Capitalize first letter of every word - -Use `replace()` to match the first character of each word and `toUpperCase()` to capitalize it. - -```js -const capitalizeEveryWord = str => str.replace(/\b[a-z]/g, char => char.toUpperCase()); -// capitalizeEveryWord('hello world!') -> 'Hello World!' -``` - -[⬆ back to top](#table-of-contents) -### Capitalize first letter - -Use `slice(0,1)` and `toUpperCase()` to capitalize first letter, `slice(1)` to get the rest of the string. -Omit the `lowerRest` parameter to keep the rest of the string intact, or set it to `true` to convert to lower case. - -```js -const capitalize = (str, lowerRest = false) => - str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); -// capitalize('myName', true) -> 'Myname' -``` - -[⬆ back to top](#table-of-contents) -### Chain asynchronous functions - -Loop through an array of functions containing asynchronous events, calling `next` when each asynchronous event has completed. - -```js -const chainAsync = fns => { let curr = 0; const next = () => fns[curr++](next); next(); }; -/* -chainAsync([ - next => { console.log('0 seconds'); setTimeout(next, 1000); }, - next => { console.log('1 second'); setTimeout(next, 1000); }, - next => { console.log('2 seconds'); } -]) -*/ -``` - -[⬆ back to top](#table-of-contents) -### Check for palindrome - -Convert string `toLowerCase()` and use `replace()` to remove non-alphanumeric characters from it. -Then, `split('')` into individual characters, `reverse()`, `join('')` and compare to the original, unreversed string, after converting it `tolowerCase()`. - -```js -const palindrome = str => { - const s = str.toLowerCase().replace(/[\W_]/g,''); - return s === s.split('').reverse().join(''); -} -// palindrome('taco cat') -> true - ``` - -[⬆ back to top](#table-of-contents) ### Chunk array Use `Array.from()` to create a new array, that fits the number of chunks that will be produced. @@ -234,17 +174,7 @@ const chunk = (arr, size) => ``` [⬆ back to top](#table-of-contents) -### Collatz algorithm -If `n` is even, return `n/2`. Otherwise return `3n+1`. - -```js -const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); -// collatz(8) --> 4 -// collatz(5) --> 16 -``` - -[⬆ back to top](#table-of-contents) ### Compact Use `Array.filter()` to filter out falsey values (`false`, `null`, `0`, `""`, `undefined`, and `NaN`). @@ -255,6 +185,7 @@ const compact = (arr) => arr.filter(v => v); ``` [⬆ back to top](#table-of-contents) + ### Count occurrences of a value in array Use `Array.reduce()` to increment a counter each time you encounter the specific value inside the array. @@ -265,36 +196,7 @@ const countOccurrences = (arr, value) => arr.reduce((a, v) => v === value ? a + ``` [⬆ back to top](#table-of-contents) -### Current URL -Use `window.location.href` to get current URL. - -```js -const currentUrl = _ => window.location.href; -// currentUrl() -> 'https://google.com' -``` - -[⬆ back to top](#table-of-contents) -### Curry - -Use recursion. -If the number of provided arguments (`args`) is sufficient, call the passed function `f`. -Otherwise return a curried function `f` that expects the rest of the arguments. -If you want to curry a function that accepts a variable number of arguments (a variadic function, e.g. `Math.min()`), you can optionally pass the number of arguments to the second parameter `arity`. - -```js -const curry = (f, arity = f.length, next) => - (next = prevArgs => - nextArg => { - const args = [ ...prevArgs, nextArg ]; - return args.length >= arity ? f(...args) : next(args); - } - )([]); -// curry(Math.pow)(2)(10) -> 1024 -// curry(Math.min, 3)(10)(50)(2) -> 2 -``` - -[⬆ back to top](#table-of-contents) ### Deep flatten array Use recursion. @@ -307,26 +209,7 @@ const deepFlatten = arr => ``` [⬆ back to top](#table-of-contents) -### Distance between two points -Use `Math.hypot()` to calculate the Euclidean distance between two points. - -```js -const distance = (x0, y0, x1, y1) => Math.hypot(x1 - x0, y1 - y0); -// distance(1,1, 2,3) -> 2.23606797749979 -``` - -[⬆ back to top](#table-of-contents) -### Divisible by number - -Use the modulo operator (`%`) to check if the remainder is equal to `0`. - -```js -const isDivisible = (dividend, divisor) => dividend % divisor === 0; -// isDivisible(6,3) -> true -``` - -[⬆ back to top](#table-of-contents) ### Drop elements in array Loop through the array, using `Array.shift()` to drop the first element of the array until the returned value from the function is `true`. @@ -341,6 +224,274 @@ const dropElements = (arr,func) => { ``` [⬆ back to top](#table-of-contents) + +### Fill array + +Use `Array.map()` to map values between `start` (inclusive) and `end` (exclusive) to `value`. +Omit `start` to start at the first element and/or `end` to finish at the last. + +```js +const fillArray = (arr, value, start = 0, end = arr.length) => + arr.map((v,i) => i>=start && i [1,'8','8',4] +``` + +[⬆ back to top](#table-of-contents) + +### Filter out non-unique values in an array + +Use `Array.filter()` for an array containing only the unique values. + +```js +const filterNonUnique = arr => arr.filter(i => arr.indexOf(i) === arr.lastIndexOf(i)); +// filterNonUnique([1,2,2,3,4,4,5]) -> [1,3,5] +``` + +[⬆ back to top](#table-of-contents) + +### Flatten array up to depth + +Use recursion, decrementing `depth` by 1 for each level of depth. +Use `Array.reduce()` and `Array.concat()` to merge elements or arrays. +Base case, for `depth` equal to `1` stops recursion. +Omit the second element, `depth` to flatten only to a depth of `1` (single flatten). + +```js +const flattenDepth = (arr, depth = 1) => + depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth (v, depth-1) : v), []) + : arr.reduce((a,v) => a.concat(v),[]); +// flattenDepth([1,[2],[[[3],4],5]], 2) -> [1,2,[3],4,5] +``` + +[⬆ back to top](#table-of-contents) + +### Flatten array + +Use `Array.reduce()` to get all elements inside the array and `concat()` to flatten them. + +```js +const flatten = arr => arr.reduce((a, v) => a.concat(v), []); +// flatten([1,[2],3,4]) -> [1,2,3,4] +``` + +[⬆ back to top](#table-of-contents) + +### Get max value from array + +Use `Math.max()` combined with the spread operator (`...`) to get the maximum value in the array. + +```js +const arrayMax = arr => Math.max(...arr); +// arrayMax([10, 1, 5]) -> 10 +``` + +[⬆ back to top](#table-of-contents) + +### Get min value from array + +Use `Math.min()` combined with the spread operator (`...`) to get the minimum value in the array. + +```js +const arrayMin = arr => Math.min(...arr); +// arrayMin([10, 1, 5]) -> 1 +``` + +[⬆ back to top](#table-of-contents) + +### Group by + +Use `Array.map()` to map the values of an array to a function or property name. +Use `Array.reduce()` to create an object, where the keys are produced from the mapped results. + +```js +const groupBy = (arr, func) => + arr.map(typeof func === 'function' ? func : val => val[func]) + .reduce((acc, val, i) => { acc[val] = (acc[val] || []).concat(arr[i]); return acc; }, {}); +// groupBy([6.1, 4.2, 6.3], Math.floor) -> {4: [4.2], 6: [6.1, 6.3]} +// groupBy(['one', 'two', 'three'], 'length') -> {3: ['one', 'two'], 5: ['three']} +``` + +[⬆ back to top](#table-of-contents) + +### Head of list + +Use `arr[0]` to return the first element of the passed array. + +```js +const head = arr => arr[0]; +// head([1,2,3]) -> 1 +``` + +[⬆ back to top](#table-of-contents) + +### Initial of list + +Use `arr.slice(0,-1)`to return all but the last element of the array. + +```js +const initial = arr => arr.slice(0, -1); +// initial([1,2,3]) -> [1,2] +``` + +[⬆ back to top](#table-of-contents) + +### Initialize array with range + +Use `Array(end-start)` to create an array of the desired length, `Array.map()` to fill with the desired values in a range. +You can omit `start` to use a default value of `0`. + +```js +const initializeArrayRange = (end, start = 0) => + Array.apply(null, Array(end - start)).map((v, i) => i + start); +// initializeArrayRange(5) -> [0,1,2,3,4] +``` + +[⬆ back to top](#table-of-contents) + +### Initialize array with values + +Use `Array(n)` to create an array of the desired length, `fill(v)` to fill it with the desired values. +You can omit `value` to use a default value of `0`. + +```js +const initializeArray = (n, value = 0) => Array(n).fill(value); +// initializeArray(5, 2) -> [2,2,2,2,2] +``` + +[⬆ back to top](#table-of-contents) + +### Last of list + +Use `arr.slice(-1)[0]` to get the last element of the given array. + +```js +const last = arr => arr.slice(-1)[0]; +// last([1,2,3]) -> 3 +``` + +[⬆ back to top](#table-of-contents) + +### Median of array of numbers + +Find the middle of the array, use `Array.sort()` to sort the values. +Return the number at the midpoint if `length` is odd, otherwise the average of the two middle numbers. + +```js +const median = arr => { + const mid = Math.floor(arr.length / 2), nums = arr.sort((a, b) => a - b); + return arr.length % 2 !== 0 ? nums[mid] : (nums[mid - 1] + nums[mid]) / 2; +}; +// median([5,6,50,1,-5]) -> 5 +// median([0,10,-2,7]) -> 3.5 +``` + +[⬆ back to top](#table-of-contents) + +### Pick + +Use `Array.reduce()` to convert the filtered/picked keys back to a object with the corresponding key:value pair if the key exist in the obj. + +```js +const pick = (obj, arr) => + arr.reduce((acc, curr) => (curr in obj && (acc[curr] = obj[curr]), acc), {}); +// pick({ 'a': 1, 'b': '2', 'c': 3 }, ['a', 'c']) -> { 'a': 1, 'c': 3 } +// pick(object, ['a', 'c'])['a'] -> 1 +``` + +[⬆ back to top](#table-of-contents) + +### Shuffle array + +Use `Array.sort()` to reorder elements, using `Math.random()` in the comparator. + +```js +const shuffle = arr => arr.sort(() => Math.random() - 0.5); +// shuffle([1,2,3]) -> [2,3,1] +``` + +[⬆ back to top](#table-of-contents) + +### Similarity between arrays + +Use `filter()` to remove values that are not part of `values`, determined using `includes()`. + +```js +const similarity = (arr, values) => arr.filter(v => values.includes(v)); +// similarity([1,2,3], [1,2,4]) -> [1,2] +``` + +[⬆ back to top](#table-of-contents) + +### Sum of array of numbers + +Use `Array.reduce()` to add each value to an accumulator, initialized with a value of `0`. + +```js +const sum = arr => arr.reduce((acc, val) => acc + val, 0); +// sum([1,2,3,4]) -> 10 +``` + +[⬆ back to top](#table-of-contents) + +### Tail of list + +Return `arr.slice(1)` if the array's `length` is more than `1`, otherwise return the whole array. + +```js +const tail = arr => arr.length > 1 ? arr.slice(1) : arr; +// tail([1,2,3]) -> [2,3] +// tail([1]) -> [1] +``` + +[⬆ back to top](#table-of-contents) + +### Take + +Use `Array.slice()` to create a slice of the array with `n` elements taken from the beginning. + +```js +const take = (arr, n = 1) => arr.slice(0, n); +// take([1, 2, 3], 5) -> [1, 2, 3] +// take([1, 2, 3], 0) -> [] +``` + +[⬆ back to top](#table-of-contents) + +### Unique values of array + +Use ES6 `Set` and the `...rest` operator to discard all duplicated values. + +```js +const unique = arr => [...new Set(arr)]; +// unique([1,2,2,3,4,4,5]) -> [1,2,3,4,5] +``` + +[⬆ back to top](#table-of-contents) +## Browser + +### Bottom visible + +Use `scrollY`, `scrollHeight` and `clientHeight` to determine if the bottom of the page is visible. + +```js +const bottomVisible = _ => + document.documentElement.clientHeight + window.scrollY >= document.documentElement.scrollHeight || document.documentElement.clientHeight; +// bottomVisible() -> true +``` + +[⬆ back to top](#table-of-contents) + +### Current URL + +Use `window.location.href` to get current URL. + +```js +const currentUrl = _ => window.location.href; +// currentUrl() -> 'https://google.com' +``` + +[⬆ back to top](#table-of-contents) + ### Element is visible in viewport Use `Element.getBoundingClientRect()` and the `window.inner(Width|Height)` values @@ -362,129 +513,7 @@ const elementIsVisibleInViewport = (el, partiallyVisible = false) => { ``` [⬆ back to top](#table-of-contents) -### Escape regular expression -Use `replace()` to escape special characters. - -```js -const escapeRegExp = str => str.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'); -// escapeRegExp('(test)') -> \\(test\\) -``` - -[⬆ back to top](#table-of-contents) -### Even or odd number - -Checks whether a number is odd or even using the modulo (`%`) operator. -Returns `true` if the number is even, `false` if the number is odd. - -```js -const isEven = num => num % 2 === 0; -// isEven(3) -> false -``` - -[⬆ back to top](#table-of-contents) -### Factorial - -Use recursion. -If `n` is less than or equal to `1`, return `1`. -Otherwise, return the product of `n` and the factorial of `n - 1`. - -```js -const factorial = n => n <= 1 ? 1 : n * factorial(n - 1); -// factorial(6) -> 720 -``` - -[⬆ back to top](#table-of-contents) -### Fibonacci array generator - -Create an empty array of the specific length, initializing the first two values (`0` and `1`). -Use `Array.reduce()` to add values into the array, using the sum of the last two values, except for the first two. - -```js -const fibonacci = n => - Array(n).fill(0).reduce((acc, val, i) => acc.concat(i > 1 ? acc[i - 1] + acc[i - 2] : i), []); -// fibonacci(5) -> [0,1,1,2,3] -``` - -[⬆ back to top](#table-of-contents) -### Fill array - -Use `Array.map()` to map values between `start` (inclusive) and `end` (exclusive) to `value`. -Omit `start` to start at the first element and/or `end` to finish at the last. - -```js -const fillArray = (arr, value, start = 0, end = arr.length) => - arr.map((v,i) => i>=start && i [1,'8','8',4] -``` - -[⬆ back to top](#table-of-contents) -### Filter out non-unique values in an array - -Use `Array.filter()` for an array containing only the unique values. - -```js -const filterNonUnique = arr => arr.filter(i => arr.indexOf(i) === arr.lastIndexOf(i)); -// filterNonUnique([1,2,2,3,4,4,5]) -> [1,3,5] -``` - -[⬆ back to top](#table-of-contents) -### Flatten array up to depth - -Use recursion, decrementing `depth` by 1 for each level of depth. -Use `Array.reduce()` and `Array.concat()` to merge elements or arrays. -Base case, for `depth` equal to `1` stops recursion. -Omit the second element, `depth` to flatten only to a depth of `1` (single flatten). - -```js -const flattenDepth = (arr, depth = 1) => - depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth (v, depth-1) : v), []) - : arr.reduce((a,v) => a.concat(v),[]); -// flattenDepth([1,[2],[[[3],4],5]], 2) -> [1,2,[3],4,5] -``` - -[⬆ back to top](#table-of-contents) -### Flatten array - -Use `Array.reduce()` to get all elements inside the array and `concat()` to flatten them. - -```js -const flatten = arr => arr.reduce((a, v) => a.concat(v), []); -// flatten([1,[2],3,4]) -> [1,2,3,4] -``` - -[⬆ back to top](#table-of-contents) -### Get max value from array - -Use `Math.max()` combined with the spread operator (`...`) to get the maximum value in the array. - -```js -const arrayMax = arr => Math.max(...arr); -// arrayMax([10, 1, 5]) -> 10 -``` - -[⬆ back to top](#table-of-contents) -### Get min value from array - -Use `Math.min()` combined with the spread operator (`...`) to get the minimum value in the array. - -```js -const arrayMin = arr => Math.min(...arr); -// arrayMin([10, 1, 5]) -> 1 -``` - -[⬆ back to top](#table-of-contents) -### Get native type of value - -Returns lower-cased constructor name of value, "undefined" or "null" if value is undefined or null - -```js -const getType = v => - v === undefined ? 'undefined' : v === null ? 'null' : v.constructor.name.toLowerCase(); -// getType(new Set([1,2,3])) -> "set" -``` - -[⬆ back to top](#table-of-contents) ### Get scroll position Use `pageXOffset` and `pageYOffset` if they are defined, otherwise `scrollLeft` and `scrollTop`. @@ -498,254 +527,67 @@ const getScrollPos = (el = window) => ``` [⬆ back to top](#table-of-contents) -### Greatest common divisor (GCD) + +undefined +[⬆ back to top](#table-of-contents) + +### Scroll to top + +Get distance from top using `document.documentElement.scrollTop` or `document.body.scrollTop`. +Scroll by a fraction of the distance from top. Use `window.requestAnimationFrame()` to animate the scrolling. + +```js +const scrollToTop = _ => { + const c = document.documentElement.scrollTop || document.body.scrollTop; + if (c > 0) { + window.requestAnimationFrame(scrollToTop); + window.scrollTo(0, c - c / 8); + } +}; +// scrollToTop() +``` + +[⬆ back to top](#table-of-contents) +## Function + +### Chain asynchronous functions + +Loop through an array of functions containing asynchronous events, calling `next` when each asynchronous event has completed. + +```js +const chainAsync = fns => { let curr = 0; const next = () => fns[curr++](next); next(); }; +/* +chainAsync([ + next => { console.log('0 seconds'); setTimeout(next, 1000); }, + next => { console.log('1 second'); setTimeout(next, 1000); }, + next => { console.log('2 seconds'); } +]) +*/ +``` + +[⬆ back to top](#table-of-contents) + +### Curry Use recursion. -Base case is when `y` equals `0`. In this case, return `x`. -Otherwise, return the GCD of `y` and the remainder of the division `x/y`. +If the number of provided arguments (`args`) is sufficient, call the passed function `f`. +Otherwise return a curried function `f` that expects the rest of the arguments. +If you want to curry a function that accepts a variable number of arguments (a variadic function, e.g. `Math.min()`), you can optionally pass the number of arguments to the second parameter `arity`. ```js -const gcd = (x, y) => !y ? x : gcd(y, x % y); -// gcd (8, 36) -> 4 +const curry = (f, arity = f.length, next) => + (next = prevArgs => + nextArg => { + const args = [ ...prevArgs, nextArg ]; + return args.length >= arity ? f(...args) : next(args); + } + )([]); +// curry(Math.pow)(2)(10) -> 1024 +// curry(Math.min, 3)(10)(50)(2) -> 2 ``` [⬆ back to top](#table-of-contents) -### Group by -Use `Array.map()` to map the values of an array to a function or property name. -Use `Array.reduce()` to create an object, where the keys are produced from the mapped results. - -```js -const groupBy = (arr, func) => - arr.map(typeof func === 'function' ? func : val => val[func]) - .reduce((acc, val, i) => { acc[val] = (acc[val] || []).concat(arr[i]); return acc; }, {}); -// groupBy([6.1, 4.2, 6.3], Math.floor) -> {4: [4.2], 6: [6.1, 6.3]} -// groupBy(['one', 'two', 'three'], 'length') -> {3: ['one', 'two'], 5: ['three']} -``` - -[⬆ back to top](#table-of-contents) -### Hamming distance - -Use XOR operator (`^`) to find the bit difference between the two numbers, convert to binary string using `toString(2)`. -Count and return the number of `1`s in the string, using `match(/1/g)`. - -```js -const hammingDistance = (num1, num2) => - ((num1 ^ num2).toString(2).match(/1/g) || '').length; -// hammingDistance(2,3) -> 1 -``` - -[⬆ back to top](#table-of-contents) -### Head of list - -Use `arr[0]` to return the first element of the passed array. - -```js -const head = arr => arr[0]; -// head([1,2,3]) -> 1 -``` - -[⬆ back to top](#table-of-contents) -### Initial of list - -Use `arr.slice(0,-1)`to return all but the last element of the array. - -```js -const initial = arr => arr.slice(0, -1); -// initial([1,2,3]) -> [1,2] -``` - -[⬆ back to top](#table-of-contents) -### Initialize array with range - -Use `Array(end-start)` to create an array of the desired length, `Array.map()` to fill with the desired values in a range. -You can omit `start` to use a default value of `0`. - -```js -const initializeArrayRange = (end, start = 0) => - Array.apply(null, Array(end - start)).map((v, i) => i + start); -// initializeArrayRange(5) -> [0,1,2,3,4] -``` - -[⬆ back to top](#table-of-contents) -### Initialize array with values - -Use `Array(n)` to create an array of the desired length, `fill(v)` to fill it with the desired values. -You can omit `value` to use a default value of `0`. - -```js -const initializeArray = (n, value = 0) => Array(n).fill(value); -// initializeArray(5, 2) -> [2,2,2,2,2] -``` - -[⬆ back to top](#table-of-contents) -### Is array - -Use `Array.isArray()` to check if a value is classified as an array. - -```js -const isArray = val => val && Array.isArray(val); -// isArray(null) -> false -// isArray([1]) -> true -``` - -[⬆ back to top](#table-of-contents) -### Is boolean - -Use `typeof` to check if a value is classified as a boolean primitive. - -```js -const isBoolean = val => typeof val === 'boolean'; -// isBoolean(null) -> false -// isBoolean(false) -> true -``` - -[⬆ back to top](#table-of-contents) -### Is function - -Use `typeof` to check if a value is classified as a function primitive. - -```js -const isFunction = val => val && typeof val === 'function'; -// isFunction('x') -> false -// isFunction(x => x) -> true -``` - -[⬆ back to top](#table-of-contents) -### Is number - -Use `typeof` to check if a value is classified as a number primitive. - -```js -const isNumber = val => typeof val === 'number'; -// isNumber('1') -> false -// isNumber(1) -> true -``` - -[⬆ back to top](#table-of-contents) -### Is string - -Use `typeof` to check if a value is classified as a string primitive. - -```js -const isString = val => typeof val === 'string'; -// isString(10) -> false -// isString('10') -> true -``` - -[⬆ back to top](#table-of-contents) -### Is symbol - -Use `typeof` to check if a value is classified as a symbol primitive. - -```js -const isSymbol = val => typeof val === 'symbol'; -// isSymbol('x') -> false -// isSymbol(Symbol('x')) -> true -``` - -[⬆ back to top](#table-of-contents) -### Last of list - -Use `arr.slice(-1)[0]` to get the last element of the given array. - -```js -const last = arr => arr.slice(-1)[0]; -// last([1,2,3]) -> 3 -``` - -[⬆ back to top](#table-of-contents) -### Measure time taken by function - -Use `performance.now()` to get start and end time for the function, `console.log()` the time taken. -Pass a callback function as the argument. - -```js -const timeTaken = callback => { - const t0 = performance.now(), r = callback(); - console.log(performance.now() - t0); - return r; -}; -// timeTaken(() => Math.pow(2, 10)) -> 1024 (0.010000000009313226 logged in console) -``` - -[⬆ back to top](#table-of-contents) -### Median of array of numbers - -Find the middle of the array, use `Array.sort()` to sort the values. -Return the number at the midpoint if `length` is odd, otherwise the average of the two middle numbers. - -```js -const median = arr => { - const mid = Math.floor(arr.length / 2), nums = arr.sort((a, b) => a - b); - return arr.length % 2 !== 0 ? nums[mid] : (nums[mid - 1] + nums[mid]) / 2; -}; -// median([5,6,50,1,-5]) -> 5 -// median([0,10,-2,7]) -> 3.5 -``` - -[⬆ back to top](#table-of-contents) -### Object from key-value pairs - -Use `Array.reduce()` to create and combine key-value pairs. - -```js -const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); -// objectFromPairs([['a',1],['b',2]]) -> {a: 1, b: 2} -``` - -[⬆ back to top](#table-of-contents) -### Object to key-value pairs - -Use `Object.keys()` and `Array.map()` to iterate over the object's keys and produce an array with key-value pairs. - -```js -const objectToPairs = obj => Object.keys(obj).map(k => [k, obj[k]]); -// objectToPairs({a: 1, b: 2}) -> [['a',1],['b',2]]) -``` - -[⬆ back to top](#table-of-contents) -### Ordinal suffix of number - -Use the modulo operator (`%`) to find values of single and tens digits. -Find which ordinal pattern digits match. -If digit is found in teens pattern, use teens ordinal. - -```js -const toOrdinalSuffix = num => { - const int = parseInt(num), digits = [(int % 10), (int % 100)], - ordinals = ["st", "nd", "rd", "th"], oPattern = [1,2,3,4], - tPattern = [11, 12, 13, 14, 15, 16, 17, 18, 19] - return oPattern.includes(digits[0]) && !tPattern.includes(digits[1]) ? int + ordinals[digits[0]-1] : int + ordinals[3]; -} -// toOrdinalSuffix("123") -> "123rd" -``` - -[⬆ back to top](#table-of-contents) -### Percentile - -Use `Array.reduce()` to calculate how many numbers are below the value and how many are the same value and -apply the percentile formula. - -```js -const percentile = (arr, val) => - 100 * arr.reduce((acc,v) => acc + (v < val ? 1 : 0) + (v === val ? 0.5 : 0), 0) / arr.length; -// percentile([1,2,3,4,5,6,7,8,9,10], 6) -> 55 - ``` - -[⬆ back to top](#table-of-contents) -### Pick - -Use `Array.reduce()` to convert the filtered/picked keys back to a object with the corresponding key:value pair if the key exist in the obj. - -```js -const pick = (obj, arr) => - arr.reduce((acc, curr) => (curr in obj && (acc[curr] = obj[curr]), acc), {}); -// pick({ 'a': 1, 'b': '2', 'c': 3 }, ['a', 'c']) -> { 'a': 1, 'c': 3 } -// pick(object, ['a', 'c'])['a'] -> 1 -``` - -[⬆ back to top](#table-of-contents) ### Pipe Use `Array.reduce()` to pass value through functions. @@ -756,17 +598,7 @@ const pipe = (...funcs) => arg => funcs.reduce((acc, func) => func(acc), arg); ``` [⬆ back to top](#table-of-contents) -### Powerset -Use `Array.reduce()` combined with `Array.map()` to iterate over elements and combine into an array containing all combinations. - -```js -const powerset = arr => - arr.reduce((a, v) => a.concat(a.map(r => [v].concat(r))), [[]]); -// powerset([1,2]) -> [[], [1], [2], [2,1]] -``` - -[⬆ back to top](#table-of-contents) ### Promisify Use currying to return a function returning a `Promise` that calls the original function. @@ -786,59 +618,7 @@ const promisify = func => ``` [⬆ back to top](#table-of-contents) -### Random integer in range -Use `Math.random()` to generate a random number and map it to the desired range, using `Math.floor()` to make it an integer. - -```js -const randomIntegerInRange = (min, max) => Math.floor(Math.random() * (max - min + 1)) + min; -// randomIntegerInRange(0, 5) -> 2 -``` - -[⬆ back to top](#table-of-contents) -### Random number in range - -Use `Math.random()` to generate a random value, map it to the desired range using multiplication. - -```js -const randomInRange = (min, max) => Math.random() * (max - min) + min; -// randomInRange(2,10) -> 6.0211363285087005 -``` - -[⬆ back to top](#table-of-contents) -### Redirect to URL - -Use `window.location.href` or `window.location.replace()` to redirect to `url`. -Pass a second argument to simulate a link click (`true` - default) or an HTTP redirect (`false`). - -```js -const redirect = (url, asLink = true) => - asLink ? window.location.href = url : window.location.replace(url); -// redirect('https://google.com') -``` - -[⬆ back to top](#table-of-contents) -### Reverse a string - -Use array destructuring and `Array.reverse()` to reverse the order of the characters in the string. -Combine characters to get a string using `join('')`. - -```js -const reverseString = str => [...str].reverse().join(''); -// reverseString('foobar') -> 'raboof' -``` - -[⬆ back to top](#table-of-contents) -### RGB to hexadecimal - -Convert given RGB parameters to hexadecimal string using bitwise left-shift operator (`<<`) and `toString(16)`, then `padStart(6,'0')` to get a 6-digit hexadecimal value. - -```js -const rgbToHex = (r, g, b) => ((r << 16) + (g << 8) + b).toString(16).padStart(6, '0'); -// rgbToHex(255, 165, 1) -> 'ffa501' -``` - -[⬆ back to top](#table-of-contents) ### Run promises in series Run an array of promises in series using `Array.reduce()` by creating a promise chain, where each promise returns the next promise when resolved. @@ -850,43 +630,7 @@ const series = ps => ps.reduce((p, next) => p.then(next), Promise.resolve()); ``` [⬆ back to top](#table-of-contents) -### Scroll to top -Get distance from top using `document.documentElement.scrollTop` or `document.body.scrollTop`. -Scroll by a fraction of the distance from top. Use `window.requestAnimationFrame()` to animate the scrolling. - -```js -const scrollToTop = _ => { - const c = document.documentElement.scrollTop || document.body.scrollTop; - if (c > 0) { - window.requestAnimationFrame(scrollToTop); - window.scrollTo(0, c - c / 8); - } -}; -// scrollToTop() -``` - -[⬆ back to top](#table-of-contents) -### Shuffle array - -Use `Array.sort()` to reorder elements, using `Math.random()` in the comparator. - -```js -const shuffle = arr => arr.sort(() => Math.random() - 0.5); -// shuffle([1,2,3]) -> [2,3,1] -``` - -[⬆ back to top](#table-of-contents) -### Similarity between arrays - -Use `filter()` to remove values that are not part of `values`, determined using `includes()`. - -```js -const similarity = (arr, values) => arr.filter(v => values.includes(v)); -// similarity([1,2,3], [1,2,4]) -> [1,2] -``` - -[⬆ back to top](#table-of-contents) ### Sleep Delay executing part of an `async` function, by putting it to sleep, returning a `Promise`. @@ -903,17 +647,131 @@ async function sleepyWork() { ``` [⬆ back to top](#table-of-contents) -### Sort characters in string (alphabetical) +## Math -Split the string using `split('')`, `Array.sort()` utilizing `localeCompare()`, recombine using `join('')`. +### Collatz algorithm + +If `n` is even, return `n/2`. Otherwise return `3n+1`. ```js -const sortCharactersInString = str => - str.split('').sort((a, b) => a.localeCompare(b)).join(''); -// sortCharactersInString('cabbage') -> 'aabbceg' +const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); +// collatz(8) --> 4 +// collatz(5) --> 16 ``` [⬆ back to top](#table-of-contents) + +### Distance between two points + +Use `Math.hypot()` to calculate the Euclidean distance between two points. + +```js +const distance = (x0, y0, x1, y1) => Math.hypot(x1 - x0, y1 - y0); +// distance(1,1, 2,3) -> 2.23606797749979 +``` + +[⬆ back to top](#table-of-contents) + +### Divisible by number + +Use the modulo operator (`%`) to check if the remainder is equal to `0`. + +```js +const isDivisible = (dividend, divisor) => dividend % divisor === 0; +// isDivisible(6,3) -> true +``` + +[⬆ back to top](#table-of-contents) + +### Even or odd number + +Checks whether a number is odd or even using the modulo (`%`) operator. +Returns `true` if the number is even, `false` if the number is odd. + +```js +const isEven = num => num % 2 === 0; +// isEven(3) -> false +``` + +[⬆ back to top](#table-of-contents) + +### Factorial + +Use recursion. +If `n` is less than or equal to `1`, return `1`. +Otherwise, return the product of `n` and the factorial of `n - 1`. + +```js +const factorial = n => n <= 1 ? 1 : n * factorial(n - 1); +// factorial(6) -> 720 +``` + +[⬆ back to top](#table-of-contents) + +### Fibonacci array generator + +Create an empty array of the specific length, initializing the first two values (`0` and `1`). +Use `Array.reduce()` to add values into the array, using the sum of the last two values, except for the first two. + +```js +const fibonacci = n => + Array(n).fill(0).reduce((acc, val, i) => acc.concat(i > 1 ? acc[i - 1] + acc[i - 2] : i), []); +// fibonacci(5) -> [0,1,1,2,3] +``` + +[⬆ back to top](#table-of-contents) + +### Greatest common divisor (GCD) + +Use recursion. +Base case is when `y` equals `0`. In this case, return `x`. +Otherwise, return the GCD of `y` and the remainder of the division `x/y`. + +```js +const gcd = (x, y) => !y ? x : gcd(y, x % y); +// gcd (8, 36) -> 4 +``` + +[⬆ back to top](#table-of-contents) + +### Hamming distance + +Use XOR operator (`^`) to find the bit difference between the two numbers, convert to binary string using `toString(2)`. +Count and return the number of `1`s in the string, using `match(/1/g)`. + +```js +const hammingDistance = (num1, num2) => + ((num1 ^ num2).toString(2).match(/1/g) || '').length; +// hammingDistance(2,3) -> 1 +``` + +[⬆ back to top](#table-of-contents) + +### Percentile + +Use `Array.reduce()` to calculate how many numbers are below the value and how many are the same value and +apply the percentile formula. + +```js +const percentile = (arr, val) => + 100 * arr.reduce((acc,v) => acc + (v < val ? 1 : 0) + (v === val ? 0.5 : 0), 0) / arr.length; +// percentile([1,2,3,4,5,6,7,8,9,10], 6) -> 55 + ``` + +[⬆ back to top](#table-of-contents) + +### Powerset + +Use `Array.reduce()` combined with `Array.map()` to iterate over elements and combine into an array containing all combinations. + +```js +const powerset = arr => + arr.reduce((a, v) => a.concat(a.map(r => [v].concat(r))), [[]]); +// powerset([1,2]) -> [[], [1], [2], [2,1]] +``` + +[⬆ back to top](#table-of-contents) + ### Standard deviation Use `Array.reduce()` to calculate the mean, variance and the sum of the variance of the values, the variance of the values, then @@ -933,49 +791,112 @@ const standardDeviation = (arr, usePopulation = false) => { ``` [⬆ back to top](#table-of-contents) -### Sum of array of numbers +## Object -Use `Array.reduce()` to add each value to an accumulator, initialized with a value of `0`. +### Object from key-value pairs + +Use `Array.reduce()` to create and combine key-value pairs. ```js -const sum = arr => arr.reduce((acc, val) => acc + val, 0); -// sum([1,2,3,4]) -> 10 +const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); +// objectFromPairs([['a',1],['b',2]]) -> {a: 1, b: 2} ``` [⬆ back to top](#table-of-contents) -### Swap values of two variables -Use array destructuring to swap values between two variables. +### Object to key-value pairs + +Use `Object.keys()` and `Array.map()` to iterate over the object's keys and produce an array with key-value pairs. ```js -[varA, varB] = [varB, varA]; -// [x, y] = [y, x] +const objectToPairs = obj => Object.keys(obj).map(k => [k, obj[k]]); +// objectToPairs({a: 1, b: 2}) -> [['a',1],['b',2]]) ``` [⬆ back to top](#table-of-contents) -### Tail of list +## String -Return `arr.slice(1)` if the array's `length` is more than `1`, otherwise return the whole array. +### Anagrams of string (with duplicates) + +Use recursion. +For each letter in the given string, create all the partial anagrams for the rest of its letters. +Use `Array.map()` to combine the letter with each partial anagram, then `Array.reduce()` to combine all anagrams in one array. +Base cases are for string `length` equal to `2` or `1`. ```js -const tail = arr => arr.length > 1 ? arr.slice(1) : arr; -// tail([1,2,3]) -> [2,3] -// tail([1]) -> [1] +const anagrams = str => { + if (str.length <= 2) return str.length === 2 ? [str, str[1] + str[0]] : [str]; + return str.split('').reduce((acc, letter, i) => + acc.concat(anagrams(str.slice(0, i) + str.slice(i + 1)).map(val => letter + val)), []); +}; +// anagrams('abc') -> ['abc','acb','bac','bca','cab','cba'] ``` [⬆ back to top](#table-of-contents) -### Take -Use `Array.slice()` to create a slice of the array with `n` elements taken from the beginning. +### Capitalize first letter of every word + +Use `replace()` to match the first character of each word and `toUpperCase()` to capitalize it. ```js -const take = (arr, n = 1) => arr.slice(0, n); - -// take([1, 2, 3], 5) -> [1, 2, 3] -// take([1, 2, 3], 0) -> [] +const capitalizeEveryWord = str => str.replace(/\b[a-z]/g, char => char.toUpperCase()); +// capitalizeEveryWord('hello world!') -> 'Hello World!' ``` [⬆ back to top](#table-of-contents) + +### Capitalize first letter + +Use `slice(0,1)` and `toUpperCase()` to capitalize first letter, `slice(1)` to get the rest of the string. +Omit the `lowerRest` parameter to keep the rest of the string intact, or set it to `true` to convert to lower case. + +```js +const capitalize = (str, lowerRest = false) => + str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); +// capitalize('myName', true) -> 'Myname' +``` + +[⬆ back to top](#table-of-contents) + +### Check for palindrome + +Convert string `toLowerCase()` and use `replace()` to remove non-alphanumeric characters from it. +Then, `split('')` into individual characters, `reverse()`, `join('')` and compare to the original, unreversed string, after converting it `tolowerCase()`. + +```js +const palindrome = str => { + const s = str.toLowerCase().replace(/[\W_]/g,''); + return s === s.split('').reverse().join(''); +} +// palindrome('taco cat') -> true + ``` + +[⬆ back to top](#table-of-contents) + +### Reverse a string + +Use array destructuring and `Array.reverse()` to reverse the order of the characters in the string. +Combine characters to get a string using `join('')`. + +```js +const reverseString = str => [...str].reverse().join(''); +// reverseString('foobar') -> 'raboof' +``` + +[⬆ back to top](#table-of-contents) + +### Sort characters in string (alphabetical) + +Split the string using `split('')`, `Array.sort()` utilizing `localeCompare()`, recombine using `join('')`. + +```js +const sortCharactersInString = str => + str.split('').sort((a, b) => a.localeCompare(b)).join(''); +// sortCharactersInString('cabbage') -> 'aabbceg' +``` + +[⬆ back to top](#table-of-contents) + ### Truncate a String Determine if the string's `length` is greater than `num`. @@ -988,16 +909,181 @@ const truncate = (str, num) => ``` [⬆ back to top](#table-of-contents) -### Unique values of array +## Utility -Use ES6 `Set` and the `...rest` operator to discard all duplicated values. +### Escape regular expression + +Use `replace()` to escape special characters. ```js -const unique = arr => [...new Set(arr)]; -// unique([1,2,2,3,4,4,5]) -> [1,2,3,4,5] +const escapeRegExp = str => str.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'); +// escapeRegExp('(test)') -> \\(test\\) ``` [⬆ back to top](#table-of-contents) + +### Get native type of value + +Returns lower-cased constructor name of value, "undefined" or "null" if value is undefined or null + +```js +const getType = v => + v === undefined ? 'undefined' : v === null ? 'null' : v.constructor.name.toLowerCase(); +// getType(new Set([1,2,3])) -> "set" +``` + +[⬆ back to top](#table-of-contents) + +### Is array + +Use `Array.isArray()` to check if a value is classified as an array. + +```js +const isArray = val => val && Array.isArray(val); +// isArray(null) -> false +// isArray([1]) -> true +``` + +[⬆ back to top](#table-of-contents) + +### Is boolean + +Use `typeof` to check if a value is classified as a boolean primitive. + +```js +const isBoolean = val => typeof val === 'boolean'; +// isBoolean(null) -> false +// isBoolean(false) -> true +``` + +[⬆ back to top](#table-of-contents) + +### Is function + +Use `typeof` to check if a value is classified as a function primitive. + +```js +const isFunction = val => val && typeof val === 'function'; +// isFunction('x') -> false +// isFunction(x => x) -> true +``` + +[⬆ back to top](#table-of-contents) + +### Is number + +Use `typeof` to check if a value is classified as a number primitive. + +```js +const isNumber = val => typeof val === 'number'; +// isNumber('1') -> false +// isNumber(1) -> true +``` + +[⬆ back to top](#table-of-contents) + +### Is string + +Use `typeof` to check if a value is classified as a string primitive. + +```js +const isString = val => typeof val === 'string'; +// isString(10) -> false +// isString('10') -> true +``` + +[⬆ back to top](#table-of-contents) + +### Is symbol + +Use `typeof` to check if a value is classified as a symbol primitive. + +```js +const isSymbol = val => typeof val === 'symbol'; +// isSymbol('x') -> false +// isSymbol(Symbol('x')) -> true +``` + +[⬆ back to top](#table-of-contents) + +### Measure time taken by function + +Use `performance.now()` to get start and end time for the function, `console.log()` the time taken. +Pass a callback function as the argument. + +```js +const timeTaken = callback => { + const t0 = performance.now(), r = callback(); + console.log(performance.now() - t0); + return r; +}; +// timeTaken(() => Math.pow(2, 10)) -> 1024 (0.010000000009313226 logged in console) +``` + +[⬆ back to top](#table-of-contents) + +### Ordinal suffix of number + +Use the modulo operator (`%`) to find values of single and tens digits. +Find which ordinal pattern digits match. +If digit is found in teens pattern, use teens ordinal. + +```js +const toOrdinalSuffix = num => { + const int = parseInt(num), digits = [(int % 10), (int % 100)], + ordinals = ["st", "nd", "rd", "th"], oPattern = [1,2,3,4], + tPattern = [11, 12, 13, 14, 15, 16, 17, 18, 19] + return oPattern.includes(digits[0]) && !tPattern.includes(digits[1]) ? int + ordinals[digits[0]-1] : int + ordinals[3]; +} +// toOrdinalSuffix("123") -> "123rd" +``` + +[⬆ back to top](#table-of-contents) + +### Random integer in range + +Use `Math.random()` to generate a random number and map it to the desired range, using `Math.floor()` to make it an integer. + +```js +const randomIntegerInRange = (min, max) => Math.floor(Math.random() * (max - min + 1)) + min; +// randomIntegerInRange(0, 5) -> 2 +``` + +[⬆ back to top](#table-of-contents) + +### Random number in range + +Use `Math.random()` to generate a random value, map it to the desired range using multiplication. + +```js +const randomInRange = (min, max) => Math.random() * (max - min) + min; +// randomInRange(2,10) -> 6.0211363285087005 +``` + +[⬆ back to top](#table-of-contents) + +### RGB to hexadecimal + +Convert given RGB parameters to hexadecimal string using bitwise left-shift operator (`<<`) and `toString(16)`, then `padStart(6,'0')` to get a 6-digit hexadecimal value. + +```js +const rgbToHex = (r, g, b) => ((r << 16) + (g << 8) + b).toString(16).padStart(6, '0'); +// rgbToHex(255, 165, 1) -> 'ffa501' +``` + +[⬆ back to top](#table-of-contents) + +### Swap values of two variables + +Use array destructuring to swap values between two variables. + +```js +[varA, varB] = [varB, varA]; +// [x, y] = [y, x] +``` + +[⬆ back to top](#table-of-contents) + ### URL parameters Use `match()` with an appropriate regular expression to get all key-value pairs, `Array.reduce()` to map and combine them into a single object. @@ -1012,6 +1098,7 @@ const getUrlParameters = url => ``` [⬆ back to top](#table-of-contents) + ### UUID generator Use `crypto` API to generate a UUID, compliant with [RFC4122](https://www.ietf.org/rfc/rfc4122.txt) version 4. @@ -1025,6 +1112,7 @@ const uuid = _ => ``` [⬆ back to top](#table-of-contents) + ### Validate email Use a regular experssion to check if the email is valid. @@ -1037,6 +1125,7 @@ const validateEmail = str => ``` [⬆ back to top](#table-of-contents) + ### Validate number Use `!isNaN` in combination with `parseFloat()` to check if the argument is a number. @@ -1049,6 +1138,7 @@ const validateNumber = n => !isNaN(parseFloat(n)) && isFinite(n) && Number(n) == ``` [⬆ back to top](#table-of-contents) + ### Value or default Returns value, or default value if passed value is `falsy`. @@ -1059,6 +1149,7 @@ const valueOrDefault = (value, d) => value || d; ``` [⬆ back to top](#table-of-contents) + ## Credits *Icons made by [Smashicons](https://www.flaticon.com/authors/smashicons) from [www.flaticon.com](https://www.flaticon.com/) is licensed by [CC 3.0 BY](http://creativecommons.org/licenses/by/3.0/).* diff --git a/scripts/builder.js b/scripts/builder.js index 220469705..6a15e53a7 100644 --- a/scripts/builder.js +++ b/scripts/builder.js @@ -4,7 +4,10 @@ var path = require('path'); var snippetsPath = './snippets'; var staticPartsPath = './static-parts'; -var snippets = {}, startPart = '', endPart = '', output = ''; +var snippets = {}, startPart = '', endPart = '', output = '', tagDbData = {}; + +const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); +const capitalize = (str, lowerRest = false) => str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); console.time('Builder'); @@ -39,14 +42,28 @@ catch (err){ process.exit(1); } +try { + tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').slice(0,-1).map(v => v.split(':').slice(0,2))); +} +catch (err){ + console.log('Error during tag database loading: '+err); + process.exit(1); +} + try { output += `${startPart+'\n'}`; - for(var snippet of Object.entries(snippets)) - output += `* [${snippet[0][0].toUpperCase() + snippet[0].replace(/-/g,' ').slice(1,snippet[0].length-3)}](#${snippet[0].slice(0,snippet[0].length-3).replace(/\(/g,'').replace(/\)/g,'').toLowerCase()})\n` - output += '\n'; - for(var snippet of Object.entries(snippets)) - output += `${snippet[1]+'\n[⬆ back to top](#table-of-contents)\n'}`; - output += `${endPart+'\n'}`; + for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].sort((a,b) => a.localeCompare(b))){ + output +=`### ${capitalize(tag, true)}\n`; + for(var taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) + output += `* [${taggedSnippet[0][0].toUpperCase() + taggedSnippet[0].replace(/-/g,' ').slice(1)}](#${taggedSnippet[0].replace(/\(/g,'').replace(/\)/g,'').toLowerCase()})\n` + output += '\n'; + } + for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].sort((a,b) => a.localeCompare(b))){ + output +=`## ${capitalize(tag, true)}\n`; + for(var taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) + output += `\n${snippets[taggedSnippet[0]+'.md']+'\n[⬆ back to top](#table-of-contents)\n'}`; + } + output += `\n${endPart+'\n'}`; fs.writeFileSync('README.md', output); } catch (err){ diff --git a/scripts/tagger.js b/scripts/tagger.js index 6e2329e28..ecebce50f 100644 --- a/scripts/tagger.js +++ b/scripts/tagger.js @@ -35,11 +35,8 @@ catch (err){ } try { - tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').map(v => v.split(':').slice(0,2))); - // for(var tag of [...new Set(Object.entries(tagDbData).map(x => x[1]))]) - // tagDbStats[tag] = Object.values(tagDbData).filter(v => v === tag); - // console.log(tagDbStats); - tagDbStats = Object.entries(tagDbData).reduce((acc, val) => {acc.hasOwnProperty(val[1]) ? acc[val[1]]++ : acc[val[1]] = 1; return acc;}, {}); + tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').slice(0,-1).map(v => v.split(':').slice(0,2))); + tagDbStats = Object.entries(tagDbData).sort((a,b) => a[1].localeCompare(b[1])).reduce((acc, val) => {acc.hasOwnProperty(val[1]) ? acc[val[1]]++ : acc[val[1]] = 1; return acc;}, {}); } catch (err){ console.log('Error during tag database loading: '+err); @@ -61,7 +58,7 @@ catch (err){ console.log('Error during README generation: '+err); process.exit(1); } -console.log(`\n===Tag database statistics===`) +console.log(`\n=== TAG STATS ===`) for(var tagData of Object.entries(tagDbStats).filter(v => v[0] !== 'undefined')){ console.log(`${chalk.green(tagData[0])}: ${tagData[1]} snippets`); } From 0ab7ee90e29022a3eb9ecb51398a3a0f8b81f4a6 Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Thu, 14 Dec 2017 22:26:08 +0530 Subject: [PATCH 39/92] Create Speech_synthesis.md Hey, I think this is the coolest one I found! Hope this snippet gets attraction --- snippets/Speech_synthesis.md | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100644 snippets/Speech_synthesis.md diff --git a/snippets/Speech_synthesis.md b/snippets/Speech_synthesis.md new file mode 100644 index 000000000..664decc73 --- /dev/null +++ b/snippets/Speech_synthesis.md @@ -0,0 +1,16 @@ +### Speech synthesis + +Currently The SpeechSynthesisUtterance interface of the Web Speech API represents a speech request. +It contains the content the speech service should read and information about how to read it (e.g. language, pitch and volume.) + +To know more - https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance + +``` +function speak (message) { + var msg = new SpeechSynthesisUtterance(message) + var voices = window.speechSynthesis.getVoices() + msg.voice = voices[0] + window.speechSynthesis.speak(msg) +} +speak('Hello, world') +``` From cd4d6ba9e850ebd38cf038cfea940be7154ee133 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 19:02:15 +0200 Subject: [PATCH 40/92] Fixed build script to exclude untagged snippets --- README.md | 14 ++++++++++++-- scripts/builder.js | 4 ++-- tag_database | 2 +- 3 files changed, 15 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 46fcf2e14..ba9eb3cfd 100644 --- a/README.md +++ b/README.md @@ -46,7 +46,7 @@ * [Current URL](#current-url) * [Element is visible in viewport](#element-is-visible-in-viewport) * [Get scroll position](#get-scroll-position) -* [Redirect to URL](#redirect-to-url) +* [Redirect to url](#redirect-to-url) * [Scroll to top](#scroll-to-top) ### Function @@ -528,7 +528,17 @@ const getScrollPos = (el = window) => [⬆ back to top](#table-of-contents) -undefined +### Redirect to URL + +Use `window.location.href` or `window.location.replace()` to redirect to `url`. +Pass a second argument to simulate a link click (`true` - default) or an HTTP redirect (`false`). + +```js +const redirect = (url, asLink = true) => + asLink ? window.location.href = url : window.location.replace(url); +// redirect('https://google.com') +``` + [⬆ back to top](#table-of-contents) ### Scroll to top diff --git a/scripts/builder.js b/scripts/builder.js index 6a15e53a7..ba345e67f 100644 --- a/scripts/builder.js +++ b/scripts/builder.js @@ -52,13 +52,13 @@ catch (err){ try { output += `${startPart+'\n'}`; - for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].sort((a,b) => a.localeCompare(b))){ + for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].filter(v => v).sort((a,b) => a.localeCompare(b))){ output +=`### ${capitalize(tag, true)}\n`; for(var taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) output += `* [${taggedSnippet[0][0].toUpperCase() + taggedSnippet[0].replace(/-/g,' ').slice(1)}](#${taggedSnippet[0].replace(/\(/g,'').replace(/\)/g,'').toLowerCase()})\n` output += '\n'; } - for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].sort((a,b) => a.localeCompare(b))){ + for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].filter(v => v).sort((a,b) => a.localeCompare(b))){ output +=`## ${capitalize(tag, true)}\n`; for(var taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) output += `\n${snippets[taggedSnippet[0]+'.md']+'\n[⬆ back to top](#table-of-contents)\n'}`; diff --git a/tag_database b/tag_database index 5619a0369..ef62da213 100644 --- a/tag_database +++ b/tag_database @@ -58,7 +58,7 @@ powerset:math promisify:function random-integer-in-range:utility random-number-in-range:utility -redirect-to-URL:browser +redirect-to-url:browser reverse-a-string:string RGB-to-hexadecimal:utility run-promises-in-series:function From 2350460ed666c7ead54780ecf7f23c0b9925e664 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 19:05:14 +0200 Subject: [PATCH 41/92] Tag and build README --- README.md | 2 +- tag_database | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index e80f512da..190b57a2e 100644 --- a/README.md +++ b/README.md @@ -46,7 +46,7 @@ * [Current URL](#current-url) * [Element is visible in viewport](#element-is-visible-in-viewport) * [Get scroll position](#get-scroll-position) -* [Redirect to url](#redirect-to-url) +* [Redirect to URL](#redirect-to-url) * [Scroll to top](#scroll-to-top) ### Function diff --git a/tag_database b/tag_database index ef62da213..5619a0369 100644 --- a/tag_database +++ b/tag_database @@ -58,7 +58,7 @@ powerset:math promisify:function random-integer-in-range:utility random-number-in-range:utility -redirect-to-url:browser +redirect-to-URL:browser reverse-a-string:string RGB-to-hexadecimal:utility run-promises-in-series:function From 530e4e411abb8340b828cdf59bd327a34b14acda Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Thu, 14 Dec 2017 22:39:24 +0530 Subject: [PATCH 42/92] Update Speech_synthesis.md used es6 approach acc. to contributing guidelines --- snippets/Speech_synthesis.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/snippets/Speech_synthesis.md b/snippets/Speech_synthesis.md index 664decc73..781f20d55 100644 --- a/snippets/Speech_synthesis.md +++ b/snippets/Speech_synthesis.md @@ -6,11 +6,11 @@ It contains the content the speech service should read and information about how To know more - https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance ``` -function speak (message) { +speak = message => { var msg = new SpeechSynthesisUtterance(message) var voices = window.speechSynthesis.getVoices() msg.voice = voices[0] window.speechSynthesis.speak(msg) -} -speak('Hello, world') + } +speak('Hello, World') ``` From 8af4dfaa738029c001fb15522b0d6570e155673e Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Thu, 14 Dec 2017 22:43:10 +0530 Subject: [PATCH 43/92] Update Speech_synthesis.md --- snippets/Speech_synthesis.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/snippets/Speech_synthesis.md b/snippets/Speech_synthesis.md index 781f20d55..db1e084cd 100644 --- a/snippets/Speech_synthesis.md +++ b/snippets/Speech_synthesis.md @@ -7,8 +7,8 @@ To know more - https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisU ``` speak = message => { - var msg = new SpeechSynthesisUtterance(message) - var voices = window.speechSynthesis.getVoices() + const msg = new SpeechSynthesisUtterance(message) + const voices = window.speechSynthesis.getVoices() msg.voice = voices[0] window.speechSynthesis.speak(msg) } From 0a2175e00ef3b4ed145c0af36b582c550c1c7542 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 19:24:17 +0200 Subject: [PATCH 44/92] Consistency for tools --- CONTRIBUTING.md | 3 +- package.json | 6 +- scripts/build-script.js | 79 ++++++++++++++++++++++ scripts/builder.js | 74 -------------------- scripts/{lintSnippet.js => lint-script.js} | 0 scripts/tag-script.js | 67 ++++++++++++++++++ scripts/tagger.js | 67 ------------------ 7 files changed, 151 insertions(+), 145 deletions(-) create mode 100644 scripts/build-script.js delete mode 100644 scripts/builder.js rename scripts/{lintSnippet.js => lint-script.js} (100%) create mode 100644 scripts/tag-script.js delete mode 100644 scripts/tagger.js diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index d2bdbf7e1..4a1dc9e66 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -7,7 +7,8 @@ Here's what you can do to help: - [Open issues](https://github.com/Chalarangelo/30-seconds-of-code/issues/new) for things you want to see added or modified. - Be part of the discussion by helping out with [existing issues](https://github.com/Chalarangelo/30-seconds-of-code/issues) or talking on our [gitter channel](https://gitter.im/30-seconds-of-code/Lobby). - Submit [pull requests](https://github.com/Chalarangelo/30-seconds-of-code/pulls) with snippets you have created (see below for guidelines). -- Fix typos in existing snippets or run `npm run lint "snippet-name.md"` on unlinted snippets (yes, this is something we actually want help with). +- Fix typos in existing snippets or run `npm run linter "snippet-name.md"` on unlinted snippets (yes, this is something we actually want help with). +- Tag untagged snippets by running `npm run tagger` and adding the appropriate tag next to the script name in `tag_database`. ### Snippet submission and Pull request guidelines diff --git a/package.json b/package.json index 2e12c8aac..4c6d5f82e 100644 --- a/package.json +++ b/package.json @@ -15,9 +15,9 @@ "chalk": "^2.3.0" }, "scripts": { - "build-list": "node ./scripts/builder.js", - "lint": "node ./scripts/lintSnippet.js", - "tag": "node ./scripts/tagger.js", + "builder": "node ./scripts/build-script.js", + "linter": "node ./scripts/lint-script.js", + "tagger": "node ./scripts/tag-script.js", "start": "concurrently --kill-others \"nodemon -e js,md -i README.md -x \\\"npm run build-list\\\"\" \"live-server ./build\"" }, "repository": { diff --git a/scripts/build-script.js b/scripts/build-script.js new file mode 100644 index 000000000..05514ae78 --- /dev/null +++ b/scripts/build-script.js @@ -0,0 +1,79 @@ +/* + This is the builder script that generates the README file. + Run using `npm run builder`. +*/ +// Load modules +const fs = require('fs-extra'), path = require('path'), chalk = require('chalk'); +// Set variables for paths +const snippetsPath = './snippets', staticPartsPath = './static-parts'; +// Set variables for script +let snippets = {}, startPart = '', endPart = '', output = '', tagDbData = {}; +// Load helper functions (these are from existing snippets in 30 seconds of code!) +const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); +const capitalize = (str, lowerRest = false) => str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); +// Start the timer of the script +console.time('Builder'); +// Synchronously read all snippets and sort them as necessary (case-insensitive) +try { + let snippetFilenames = fs.readdirSync(snippetsPath); + snippetFilenames.sort((a, b) => { + a = a.toLowerCase(); + b = b.toLowerCase(); + if (a < b) return -1; + if (a > b) return 1; + return 0; + }); + // Store the data read from each snippet in the appropriate object + for(let snippet of snippetFilenames) snippets[snippet] = fs.readFileSync(path.join(snippetsPath,snippet),'utf8'); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During snippet loading: ${err}`); + process.exit(1); +} +// Load static parts for the README file +try { + startPart = fs.readFileSync(path.join(staticPartsPath,'README-start.md'),'utf8'); + endPart = fs.readFileSync(path.join(staticPartsPath,'README-end.md'),'utf8'); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During static part loading: ${err}`); + process.exit(1); +} +// Load tag data from the database +try { + tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').slice(0,-1).map(v => v.split(':').slice(0,2))); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During tag database loading: ${err}`); + process.exit(1); +} +// Create the output for the README file +try { + // Add the start static part + output += `${startPart+'\n'}`; + // Loop over tags and snippets to create the table of contents + for(let tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].filter(v => v).sort((a,b) => a.localeCompare(b))){ + output +=`### ${capitalize(tag, true)}\n`; + for(let taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) + output += `* [${taggedSnippet[0][0].toUpperCase() + taggedSnippet[0].replace(/-/g,' ').slice(1)}](#${taggedSnippet[0].replace(/\(/g,'').replace(/\)/g,'').toLowerCase()})\n` + output += '\n'; + } + // Loop over tags and snippets to create the list of snippets + for(let tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].filter(v => v).sort((a,b) => a.localeCompare(b))){ + output +=`## ${capitalize(tag, true)}\n`; + for(let taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) + output += `\n${snippets[taggedSnippet[0]+'.md']+'\n[⬆ back to top](#table-of-contents)\n'}`; + } + // Add the ending static part + output += `\n${endPart+'\n'}`; + // Write to the README file + fs.writeFileSync('README.md', output); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During README generation: ${err}`); + process.exit(1); +} +// Log a success message +console.log(`${chalk.green('SUCCESS!')} README file generated!`); +// Log the time taken +console.timeEnd('Builder'); diff --git a/scripts/builder.js b/scripts/builder.js deleted file mode 100644 index ba345e67f..000000000 --- a/scripts/builder.js +++ /dev/null @@ -1,74 +0,0 @@ -var fs = require('fs-extra'); -var path = require('path'); - -var snippetsPath = './snippets'; -var staticPartsPath = './static-parts'; - -var snippets = {}, startPart = '', endPart = '', output = '', tagDbData = {}; - -const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); -const capitalize = (str, lowerRest = false) => str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); - -console.time('Builder'); - -try { - var snippetFilenames = fs.readdirSync(snippetsPath); - snippetFilenames.sort((a, b) => { - a = a.toLowerCase(); - b = b.toLowerCase(); - if (a < b) { - return -1; - } - if (a > b) { - return 1; - } - return 0; - }); - for(var snippet of snippetFilenames){ - snippets[snippet] = fs.readFileSync(path.join(snippetsPath,snippet),'utf8'); - } -} -catch (err){ - console.log('Error during snippet loading: '+err); - process.exit(1); -} - -try { - startPart = fs.readFileSync(path.join(staticPartsPath,'README-start.md'),'utf8'); - endPart = fs.readFileSync(path.join(staticPartsPath,'README-end.md'),'utf8'); -} -catch (err){ - console.log('Error during static part loading: '+err); - process.exit(1); -} - -try { - tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').slice(0,-1).map(v => v.split(':').slice(0,2))); -} -catch (err){ - console.log('Error during tag database loading: '+err); - process.exit(1); -} - -try { - output += `${startPart+'\n'}`; - for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].filter(v => v).sort((a,b) => a.localeCompare(b))){ - output +=`### ${capitalize(tag, true)}\n`; - for(var taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) - output += `* [${taggedSnippet[0][0].toUpperCase() + taggedSnippet[0].replace(/-/g,' ').slice(1)}](#${taggedSnippet[0].replace(/\(/g,'').replace(/\)/g,'').toLowerCase()})\n` - output += '\n'; - } - for(var tag of [...new Set(Object.entries(tagDbData).map(t => t[1]))].filter(v => v).sort((a,b) => a.localeCompare(b))){ - output +=`## ${capitalize(tag, true)}\n`; - for(var taggedSnippet of Object.entries(tagDbData).filter(v => v[1] === tag)) - output += `\n${snippets[taggedSnippet[0]+'.md']+'\n[⬆ back to top](#table-of-contents)\n'}`; - } - output += `\n${endPart+'\n'}`; - fs.writeFileSync('README.md', output); -} -catch (err){ - console.log('Error during README generation: '+err); - process.exit(1); -} - -console.timeEnd('Builder'); diff --git a/scripts/lintSnippet.js b/scripts/lint-script.js similarity index 100% rename from scripts/lintSnippet.js rename to scripts/lint-script.js diff --git a/scripts/tag-script.js b/scripts/tag-script.js new file mode 100644 index 000000000..8537b3009 --- /dev/null +++ b/scripts/tag-script.js @@ -0,0 +1,67 @@ +/* + This is the tagger script that updates the tag_databse file and logs stats for snippet tags. + Run using `npm run tagger`. +*/ +// Load modules +const fs = require('fs-extra'), path = require('path'), chalk = require('chalk'); +// Set variables for paths +const snippetsPath = './snippets'; +// Set variables for script +let snippets = {}, output = '', tagDbData = {}, missingTags = 0, tagDbStats = {}; +// Load helper functions (these are from existing snippets in 30 seconds of code!) +const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); +const countOccurrences = (arr, value) => arr.reduce((a, v) => v === value ? a + 1 : a + 0, 0); +// Start the timer of the script +console.time('Tagger'); +// Synchronously read all snippets and sort them as necessary (case-insensitive) +try { + let snippetFilenames = fs.readdirSync(snippetsPath); + snippetFilenames.sort((a, b) => { + a = a.toLowerCase(); + b = b.toLowerCase(); + if (a < b) return -1; + if (a > b) return 1; + return 0; + }); + // Store the data read from each snippet in the appropriate object + for(let snippet of snippetFilenames) snippets[snippet] = fs.readFileSync(path.join(snippetsPath,snippet),'utf8'); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During snippet loading: ${err}`); + process.exit(1); +} +// Load tag data from the database +try { + tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').slice(0,-1).map(v => v.split(':').slice(0,2))); + tagDbStats = Object.entries(tagDbData).sort((a,b) => a[1].localeCompare(b[1])).reduce((acc, val) => {acc.hasOwnProperty(val[1]) ? acc[val[1]]++ : acc[val[1]] = 1; return acc;}, {}); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During tag database loading: ${err}`); + process.exit(1); +} +// Update the listing of snippets in tag_database and log the statistics, along with missing scripts +try { + for(let snippet of Object.entries(snippets)) + if(tagDbData.hasOwnProperty(snippet[0].slice(0,-3)) && tagDbData[snippet[0].slice(0,-3)].trim()) + output += `${snippet[0].slice(0,-3)}:${tagDbData[snippet[0].slice(0,-3)].trim()}\n`; + else { + output += `${snippet[0].slice(0,-3)}:\n`; + missingTags++; + console.log(`${chalk.yellow('Tag missing:')} ${snippet[0].slice(0,-3)}`); + } + // Write to tag_database + fs.writeFileSync('tag_database', output); +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During tag_database generation: ${err}`); + process.exit(1); +} +// Log statistics for the tag_database file +console.log(`\n${chalk.bgWhite(chalk.black('=== TAG STATS ==='))}`) +for(let tagData of Object.entries(tagDbStats).filter(v => v[0] !== 'undefined')) + console.log(`${chalk.green(tagData[0])}: ${tagData[1]} snippets`); +console.log(`${chalk.blue('Untagged snippets:')} ${missingTags}\n`); +// Log a success message +console.log(`${chalk.green('SUCCESS!')} tag_database file updated!`); +// Log the time taken +console.timeEnd('Tagger'); diff --git a/scripts/tagger.js b/scripts/tagger.js deleted file mode 100644 index ecebce50f..000000000 --- a/scripts/tagger.js +++ /dev/null @@ -1,67 +0,0 @@ -var fs = require('fs-extra'); -var path = require('path'); -var chalk = require('chalk'); - -var snippetsPath = './snippets'; - -var snippets = {}, output = '', tagDbData = {}, missingTags = 0, tagDbStats = {}; - -const objectFromPairs = arr => arr.reduce((a, v) => (a[v[0]] = v[1], a), {}); -const countOccurrences = (arr, value) => arr.reduce((a, v) => v === value ? a + 1 : a + 0, 0); - - -console.time('Tagger'); - -try { - var snippetFilenames = fs.readdirSync(snippetsPath); - snippetFilenames.sort((a, b) => { - a = a.toLowerCase(); - b = b.toLowerCase(); - if (a < b) { - return -1; - } - if (a > b) { - return 1; - } - return 0; - }); - for(var snippet of snippetFilenames){ - snippets[snippet] = fs.readFileSync(path.join(snippetsPath,snippet),'utf8'); - } -} -catch (err){ - console.log('Error during snippet loading: '+err); - process.exit(1); -} - -try { - tagDbData = objectFromPairs(fs.readFileSync('tag_database','utf8').split('\n').slice(0,-1).map(v => v.split(':').slice(0,2))); - tagDbStats = Object.entries(tagDbData).sort((a,b) => a[1].localeCompare(b[1])).reduce((acc, val) => {acc.hasOwnProperty(val[1]) ? acc[val[1]]++ : acc[val[1]] = 1; return acc;}, {}); -} -catch (err){ - console.log('Error during tag database loading: '+err); - process.exit(1); -} - -try { - for(var snippet of Object.entries(snippets)) - if(tagDbData.hasOwnProperty(snippet[0].slice(0,-3)) && tagDbData[snippet[0].slice(0,-3)].trim()) - output += `${snippet[0].slice(0,-3)}:${tagDbData[snippet[0].slice(0,-3)].trim()}\n`; - else { - output += `${snippet[0].slice(0,-3)}:\n`; - missingTags++; - console.log(`${chalk.red('Tag missing:')} ${snippet[0].slice(0,-3)}`); - } - fs.writeFileSync('tag_database', output); -} -catch (err){ - console.log('Error during README generation: '+err); - process.exit(1); -} -console.log(`\n=== TAG STATS ===`) -for(var tagData of Object.entries(tagDbStats).filter(v => v[0] !== 'undefined')){ - console.log(`${chalk.green(tagData[0])}: ${tagData[1]} snippets`); -} -console.log(`${chalk.blue('Untagged snippets:')} ${missingTags}\n`); - -console.timeEnd('Tagger'); From 20e8633917beb99531e3a3628c6a63dd16ffb4ad Mon Sep 17 00:00:00 2001 From: Meet Zaveri Date: Thu, 14 Dec 2017 23:02:18 +0530 Subject: [PATCH 45/92] Update Speech_synthesis.md --- snippets/Speech_synthesis.md | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/snippets/Speech_synthesis.md b/snippets/Speech_synthesis.md index db1e084cd..022601472 100644 --- a/snippets/Speech_synthesis.md +++ b/snippets/Speech_synthesis.md @@ -6,11 +6,10 @@ It contains the content the speech service should read and information about how To know more - https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance ``` -speak = message => { - const msg = new SpeechSynthesisUtterance(message) - const voices = window.speechSynthesis.getVoices() - msg.voice = voices[0] - window.speechSynthesis.speak(msg) - } +const speak = message => { + const msg = new SpeechSynthesisUtterance(message); + msg.voice = window.speechSynthesis.getVoices()[0]; + window.speechSynthesis.speak(msg); +} speak('Hello, World') ``` From e0693339b40a4252b2ca972621202c6ed4f5dab0 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 19:38:11 +0200 Subject: [PATCH 46/92] Updated tools, proper linting, build README --- CONTRIBUTING.md | 2 +- README.md | 34 +++++------ scripts/lint-script.js | 65 +++++++++++++--------- snippets/array-difference.md | 2 +- snippets/array-intersection.md | 2 +- snippets/array-union.md | 2 +- snippets/collatz-algorithm.md | 2 +- snippets/drop-elements-in-array.md | 6 +- snippets/element-is-visible-in-viewport.md | 2 +- snippets/fill-array.md | 4 +- snippets/flatten-array-up-to-depth.md | 4 +- snippets/ordinal-suffix-of-number.md | 8 +-- snippets/standard-deviation.md | 2 +- 13 files changed, 74 insertions(+), 61 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 4a1dc9e66..618a99b1a 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -7,8 +7,8 @@ Here's what you can do to help: - [Open issues](https://github.com/Chalarangelo/30-seconds-of-code/issues/new) for things you want to see added or modified. - Be part of the discussion by helping out with [existing issues](https://github.com/Chalarangelo/30-seconds-of-code/issues) or talking on our [gitter channel](https://gitter.im/30-seconds-of-code/Lobby). - Submit [pull requests](https://github.com/Chalarangelo/30-seconds-of-code/pulls) with snippets you have created (see below for guidelines). -- Fix typos in existing snippets or run `npm run linter "snippet-name.md"` on unlinted snippets (yes, this is something we actually want help with). - Tag untagged snippets by running `npm run tagger` and adding the appropriate tag next to the script name in `tag_database`. +- Fix typos in existing snippets or run `npm run linter` to lint unlinted snippets (yes, this is something we actually want help with, as this can take quite a while to run). ### Snippet submission and Pull request guidelines diff --git a/README.md b/README.md index 190b57a2e..ead95c6f1 100644 --- a/README.md +++ b/README.md @@ -122,7 +122,7 @@ const arrayConcat = (arr, ...args) => arr.concat(...args); Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values not contained in `b`. ```js -const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has(x)); } +const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has(x)); }; // difference([1,2,3], [1,2]) -> [3] ``` @@ -133,7 +133,7 @@ const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values contained in `b`. ```js -const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.has(x)); } +const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.has(x)); }; // intersection([1,2,3], [4,3,2]) -> [2,3] ``` @@ -144,7 +144,7 @@ const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.ha Create a `Set` with all values of `a` and `b` and convert to an array. ```js -const union = (a, b) => Array.from(new Set([...a, ...b])) +const union = (a, b) => Array.from(new Set([...a, ...b])); // union([1,2,3], [4,3,2]) -> [1,2,3,4] ``` @@ -216,10 +216,10 @@ Loop through the array, using `Array.shift()` to drop the first element of the a Returns the remaining elements. ```js -const dropElements = (arr,func) => { - while(arr.length > 0 && !func(arr[0])) arr.shift(); +const dropElements = (arr, func) => { + while (arr.length > 0 && !func(arr[0])) arr.shift(); return arr; -} +}; // dropElements([1, 2, 3, 4], n => n >= 3) -> [3,4] ``` @@ -231,8 +231,8 @@ Use `Array.map()` to map values between `start` (inclusive) and `end` (exclusive Omit `start` to start at the first element and/or `end` to finish at the last. ```js -const fillArray = (arr, value, start = 0, end = arr.length) => - arr.map((v,i) => i>=start && i + arr.map((v, i) => i >= start && i < end ? value : v); // fillArray([1,2,3,4],'8',1,3) -> [1,'8','8',4] ``` @@ -258,8 +258,8 @@ Omit the second element, `depth` to flatten only to a depth of `1` (single flatt ```js const flattenDepth = (arr, depth = 1) => - depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth (v, depth-1) : v), []) - : arr.reduce((a,v) => a.concat(v),[]); + depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth(v, depth - 1) : v), []) + : arr.reduce((a, v) => a.concat(v), []); // flattenDepth([1,[2],[[[3],4],5]], 2) -> [1,2,[3],4,5] ``` @@ -506,7 +506,7 @@ const elementIsVisibleInViewport = (el, partiallyVisible = false) => { ? ((top > 0 && top < innerHeight) || (bottom > 0 && bottom < innerHeight)) && ((left > 0 && left < innerWidth) || (right > 0 && right < innerWidth)) : top >= 0 && left >= 0 && bottom <= innerHeight && right <= innerWidth; -} +}; // e.g. 100x100 viewport and a 10x10px element at position {top: -1, left: 0, bottom: 9, right: 10} // elementIsVisibleInViewport(el) -> false (not fully visible) // elementIsVisibleInViewport(el, true) -> true (partially visible) @@ -664,7 +664,7 @@ async function sleepyWork() { If `n` is even, return `n/2`. Otherwise return `3n+1`. ```js -const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); +const collatz = n => (n % 2 == 0) ? (n / 2) : (3 * n + 1); // collatz(8) --> 4 // collatz(5) --> 16 ``` @@ -795,7 +795,7 @@ const standardDeviation = (arr, usePopulation = false) => { arr.reduce((acc, val) => acc.concat(Math.pow(val - mean, 2)), []) .reduce((acc, val) => acc + val, 0) / (arr.length - (usePopulation ? 0 : 1)) ); - } +}; // standardDeviation([10,2,38,23,38,23,21]) -> 13.284434142114991 (sample) // standardDeviation([10,2,38,23,38,23,21], true) -> 12.29899614287479 (population) ``` @@ -1041,10 +1041,10 @@ If digit is found in teens pattern, use teens ordinal. ```js const toOrdinalSuffix = num => { const int = parseInt(num), digits = [(int % 10), (int % 100)], - ordinals = ["st", "nd", "rd", "th"], oPattern = [1,2,3,4], - tPattern = [11, 12, 13, 14, 15, 16, 17, 18, 19] - return oPattern.includes(digits[0]) && !tPattern.includes(digits[1]) ? int + ordinals[digits[0]-1] : int + ordinals[3]; -} + ordinals = ['st', 'nd', 'rd', 'th'], oPattern = [1, 2, 3, 4], + tPattern = [11, 12, 13, 14, 15, 16, 17, 18, 19]; + return oPattern.includes(digits[0]) && !tPattern.includes(digits[1]) ? int + ordinals[digits[0] - 1] : int + ordinals[3]; +}; // toOrdinalSuffix("123") -> "123rd" ``` diff --git a/scripts/lint-script.js b/scripts/lint-script.js index a53686ee5..3aba12d27 100644 --- a/scripts/lint-script.js +++ b/scripts/lint-script.js @@ -1,31 +1,44 @@ -var fs = require('fs-extra'); -var cp = require('child_process'); -var path = require('path'); - +/* + This is the linter script that lints snippets. + Run using `npm run linter`. +*/ +// Load modules +const fs = require('fs-extra'), cp = require('child_process'), path = require('path'); +// Set variables for paths var snippetsPath = './snippets'; -var snippetFilename = ''; - -console.time('Linter'); - -if(process.argv.length < 3){ - console.log('Please specify the filename of a snippet to be linted.'); - console.log('Example usage: npm run lint "snippet-file.md"'); - process.exit(0); -} -else { - snippetFilename = process.argv[2]; - let snippetData = fs.readFileSync(path.join(snippetsPath,snippetFilename),'utf8'); - try { +// Read files, lint each one individually and update +try { + let snippetFilenames = fs.readdirSync(snippetsPath); + snippetFilenames.sort((a, b) => { + a = a.toLowerCase(); + b = b.toLowerCase(); + if (a < b) return -1; + if (a > b) return 1; + return 0; + }); + // Read each file, get its code, write it to a temporary file, pass it through + // semistandard, get the output from the file, update the original file. + for(let snippet of snippetFilenames){ + // Start a timer for the file + console.time(`Linter (${snippet})`); + // Synchronously read data from the snippet, get the code, write it to a temporary file + let snippetData = fs.readFileSync(path.join(snippetsPath,snippet),'utf8'); let originalCode = snippetData.slice(snippetData.indexOf('```js')+5,snippetData.lastIndexOf('```')); - fs.writeFileSync('currentSnippet.js',`${originalCode}`); - cp.exec('semistandard "currentSnippet.js" --fix',{},(error, stdOut, stdErr) => { - let lintedCode = fs.readFileSync('currentSnippet.js','utf8'); - fs.writeFile(path.join(snippetsPath,snippetFilename), `${snippetData.slice(0, snippetData.indexOf('```js')+5)+lintedCode+'```\n'}`); - console.timeEnd('Linter'); + fs.writeFileSync(`${snippet}.temp.js`,`${originalCode}`); + // Run semistandard asynchronously (only way this manages to run), get linted code + // and write back to the original snippet file. Remove temporary file + cp.exec(`semistandard "${snippet}.temp.js" --fix`,{},(error, stdOut, stdErr) => { + let lintedCode = fs.readFileSync(`${snippet}.temp.js`,'utf8'); + fs.writeFile(path.join(snippetsPath,snippet), `${snippetData.slice(0, snippetData.indexOf('```js')+5)+lintedCode+'```\n'}`); + fs.unlink(`${snippet}.temp.js`); + // Log a success message + console.log(`${chalk.red('SUCCESS!')} Linted snippet: ${snippet}`); + // Log the time taken for the file + console.timeEnd(`Linter (${snippet})`); }); } - catch (err){ - console.log('Error during snippet loading: '+err); - process.exit(1); - } +} +catch (err){ // Handle errors (hopefully not!) + console.log(`${chalk.red('ERROR!')} During linting: ${err}`); + process.exit(1); } diff --git a/snippets/array-difference.md b/snippets/array-difference.md index 46469b1d6..208cb811e 100644 --- a/snippets/array-difference.md +++ b/snippets/array-difference.md @@ -3,6 +3,6 @@ Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values not contained in `b`. ```js -const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has(x)); } +const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has(x)); }; // difference([1,2,3], [1,2]) -> [3] ``` diff --git a/snippets/array-intersection.md b/snippets/array-intersection.md index 87c42378b..780ab1d85 100644 --- a/snippets/array-intersection.md +++ b/snippets/array-intersection.md @@ -3,6 +3,6 @@ Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values contained in `b`. ```js -const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.has(x)); } +const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.has(x)); }; // intersection([1,2,3], [4,3,2]) -> [2,3] ``` diff --git a/snippets/array-union.md b/snippets/array-union.md index b417dcce7..6224227d1 100644 --- a/snippets/array-union.md +++ b/snippets/array-union.md @@ -3,6 +3,6 @@ Create a `Set` with all values of `a` and `b` and convert to an array. ```js -const union = (a, b) => Array.from(new Set([...a, ...b])) +const union = (a, b) => Array.from(new Set([...a, ...b])); // union([1,2,3], [4,3,2]) -> [1,2,3,4] ``` diff --git a/snippets/collatz-algorithm.md b/snippets/collatz-algorithm.md index 730bdd9e3..61614e5e0 100644 --- a/snippets/collatz-algorithm.md +++ b/snippets/collatz-algorithm.md @@ -3,7 +3,7 @@ If `n` is even, return `n/2`. Otherwise return `3n+1`. ```js -const collatz = n => (n % 2 == 0) ? (n/2) : (3*n+1); +const collatz = n => (n % 2 == 0) ? (n / 2) : (3 * n + 1); // collatz(8) --> 4 // collatz(5) --> 16 ``` diff --git a/snippets/drop-elements-in-array.md b/snippets/drop-elements-in-array.md index 0ad2ab5e9..236c5ab56 100644 --- a/snippets/drop-elements-in-array.md +++ b/snippets/drop-elements-in-array.md @@ -4,9 +4,9 @@ Loop through the array, using `Array.shift()` to drop the first element of the a Returns the remaining elements. ```js -const dropElements = (arr,func) => { - while(arr.length > 0 && !func(arr[0])) arr.shift(); +const dropElements = (arr, func) => { + while (arr.length > 0 && !func(arr[0])) arr.shift(); return arr; -} +}; // dropElements([1, 2, 3, 4], n => n >= 3) -> [3,4] ``` diff --git a/snippets/element-is-visible-in-viewport.md b/snippets/element-is-visible-in-viewport.md index 70ff83134..514aea5e6 100644 --- a/snippets/element-is-visible-in-viewport.md +++ b/snippets/element-is-visible-in-viewport.md @@ -12,7 +12,7 @@ const elementIsVisibleInViewport = (el, partiallyVisible = false) => { ? ((top > 0 && top < innerHeight) || (bottom > 0 && bottom < innerHeight)) && ((left > 0 && left < innerWidth) || (right > 0 && right < innerWidth)) : top >= 0 && left >= 0 && bottom <= innerHeight && right <= innerWidth; -} +}; // e.g. 100x100 viewport and a 10x10px element at position {top: -1, left: 0, bottom: 9, right: 10} // elementIsVisibleInViewport(el) -> false (not fully visible) // elementIsVisibleInViewport(el, true) -> true (partially visible) diff --git a/snippets/fill-array.md b/snippets/fill-array.md index a08c4362e..a5da15483 100644 --- a/snippets/fill-array.md +++ b/snippets/fill-array.md @@ -4,7 +4,7 @@ Use `Array.map()` to map values between `start` (inclusive) and `end` (exclusive Omit `start` to start at the first element and/or `end` to finish at the last. ```js -const fillArray = (arr, value, start = 0, end = arr.length) => - arr.map((v,i) => i>=start && i + arr.map((v, i) => i >= start && i < end ? value : v); // fillArray([1,2,3,4],'8',1,3) -> [1,'8','8',4] ``` diff --git a/snippets/flatten-array-up-to-depth.md b/snippets/flatten-array-up-to-depth.md index d28af98fb..b6e3805b6 100644 --- a/snippets/flatten-array-up-to-depth.md +++ b/snippets/flatten-array-up-to-depth.md @@ -7,7 +7,7 @@ Omit the second element, `depth` to flatten only to a depth of `1` (single flatt ```js const flattenDepth = (arr, depth = 1) => - depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth (v, depth-1) : v), []) - : arr.reduce((a,v) => a.concat(v),[]); + depth != 1 ? arr.reduce((a, v) => a.concat(Array.isArray(v) ? flattenDepth(v, depth - 1) : v), []) + : arr.reduce((a, v) => a.concat(v), []); // flattenDepth([1,[2],[[[3],4],5]], 2) -> [1,2,[3],4,5] ``` diff --git a/snippets/ordinal-suffix-of-number.md b/snippets/ordinal-suffix-of-number.md index 4e849eff7..d3166928b 100644 --- a/snippets/ordinal-suffix-of-number.md +++ b/snippets/ordinal-suffix-of-number.md @@ -7,9 +7,9 @@ If digit is found in teens pattern, use teens ordinal. ```js const toOrdinalSuffix = num => { const int = parseInt(num), digits = [(int % 10), (int % 100)], - ordinals = ["st", "nd", "rd", "th"], oPattern = [1,2,3,4], - tPattern = [11, 12, 13, 14, 15, 16, 17, 18, 19] - return oPattern.includes(digits[0]) && !tPattern.includes(digits[1]) ? int + ordinals[digits[0]-1] : int + ordinals[3]; -} + ordinals = ['st', 'nd', 'rd', 'th'], oPattern = [1, 2, 3, 4], + tPattern = [11, 12, 13, 14, 15, 16, 17, 18, 19]; + return oPattern.includes(digits[0]) && !tPattern.includes(digits[1]) ? int + ordinals[digits[0] - 1] : int + ordinals[3]; +}; // toOrdinalSuffix("123") -> "123rd" ``` diff --git a/snippets/standard-deviation.md b/snippets/standard-deviation.md index e559972bb..5819579ad 100644 --- a/snippets/standard-deviation.md +++ b/snippets/standard-deviation.md @@ -11,7 +11,7 @@ const standardDeviation = (arr, usePopulation = false) => { arr.reduce((acc, val) => acc.concat(Math.pow(val - mean, 2)), []) .reduce((acc, val) => acc + val, 0) / (arr.length - (usePopulation ? 0 : 1)) ); - } +}; // standardDeviation([10,2,38,23,38,23,21]) -> 13.284434142114991 (sample) // standardDeviation([10,2,38,23,38,23,21], true) -> 12.29899614287479 (population) ``` From 3549379bcb3a68a466092a8c390acdb3abe7e7a9 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:13:16 +0200 Subject: [PATCH 47/92] Build README --- README.md | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index ead95c6f1..5777cbc88 100644 --- a/README.md +++ b/README.md @@ -585,13 +585,10 @@ Otherwise return a curried function `f` that expects the rest of the arguments. If you want to curry a function that accepts a variable number of arguments (a variadic function, e.g. `Math.min()`), you can optionally pass the number of arguments to the second parameter `arity`. ```js -const curry = (f, arity = f.length, next) => - (next = prevArgs => - nextArg => { - const args = [ ...prevArgs, nextArg ]; - return args.length >= arity ? f(...args) : next(args); - } - )([]); +const curry = (fn, arity = fn.length, ...args) => + arity <= args.length + ? fn(...args) + : curry.bind(null, fn, arity, ...args) // curry(Math.pow)(2)(10) -> 1024 // curry(Math.min, 3)(10)(50)(2) -> 2 ``` From f81b49f9f5ad7fedce18d57538b7b51a5be01018 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:20:37 +0200 Subject: [PATCH 48/92] Resolve #111 --- snippets/is-array.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/is-array.md b/snippets/is-array.md index 7652f74c9..939cb086d 100644 --- a/snippets/is-array.md +++ b/snippets/is-array.md @@ -3,7 +3,7 @@ Use `Array.isArray()` to check if a value is classified as an array. ```js -const isArray = val => val && Array.isArray(val); +const isArray = val => !!val && Array.isArray(val); // isArray(null) -> false // isArray([1]) -> true ``` From 26c8055fa45f899478f773fef375d437a980b96e Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:21:26 +0200 Subject: [PATCH 49/92] Build README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 5777cbc88..b47ab9fce 100644 --- a/README.md +++ b/README.md @@ -946,7 +946,7 @@ const getType = v => Use `Array.isArray()` to check if a value is classified as an array. ```js -const isArray = val => val && Array.isArray(val); +const isArray = val => !!val && Array.isArray(val); // isArray(null) -> false // isArray([1]) -> true ``` From db4e2478cd503fe72885e618144711505448947f Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:24:12 +0200 Subject: [PATCH 50/92] Update get-days-difference-between-dates.md --- snippets/get-days-difference-between-dates.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/snippets/get-days-difference-between-dates.md b/snippets/get-days-difference-between-dates.md index 152cd7167..d97463adb 100644 --- a/snippets/get-days-difference-between-dates.md +++ b/snippets/get-days-difference-between-dates.md @@ -1,6 +1,6 @@ -### Get Days Difference Between Dates +### Get days difference between dates -Returns the number of days between two Dates. +Calculate the difference (in days) between to `Date` objects. ```js const getDaysDiffBetweenDates = (dateInitial, dateFinal) => (dateFinal - dateInitial) / (1000 * 3600 * 24); From 240eda38099986f93858e16c08fdaf14d780385f Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:26:20 +0200 Subject: [PATCH 51/92] Tag and build --- README.md | 15 +++++++++++++++ tag_database | 1 + 2 files changed, 16 insertions(+) diff --git a/README.md b/README.md index b47ab9fce..6c3c68b31 100644 --- a/README.md +++ b/README.md @@ -49,6 +49,9 @@ * [Redirect to URL](#redirect-to-url) * [Scroll to top](#scroll-to-top) +### Date +* [Get days difference between dates](#get-days-difference-between-dates) + ### Function * [Chain asynchronous functions](#chain-asynchronous-functions) * [Curry](#curry) @@ -557,6 +560,18 @@ const scrollToTop = _ => { // scrollToTop() ``` +[⬆ back to top](#table-of-contents) +## Date + +### Get days difference between dates + +Calculate the difference (in days) between to `Date` objects. + +```js +const getDaysDiffBetweenDates = (dateInitial, dateFinal) => (dateFinal - dateInitial) / (1000 * 3600 * 24); +//getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 +``` + [⬆ back to top](#table-of-contents) ## Function diff --git a/tag_database b/tag_database index 5619a0369..a8d4fa8dd 100644 --- a/tag_database +++ b/tag_database @@ -28,6 +28,7 @@ fill-array:array filter-out-non-unique-values-in-an-array:array flatten-array-up-to-depth:array flatten-array:array +get-days-difference-between-dates:date get-max-value-from-array:array get-min-value-from-array:array get-native-type-of-value:utility From 744c6f359dbbf4ad05f18f692e82049b4c92d3a2 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:47:23 +0200 Subject: [PATCH 52/92] Update and rename Speech_synthesis.md to speech_synthesis-(experimental).md --- snippets/Speech_synthesis.md | 15 --------------- snippets/speech_synthesis-(experimental).md | 15 +++++++++++++++ 2 files changed, 15 insertions(+), 15 deletions(-) delete mode 100644 snippets/Speech_synthesis.md create mode 100644 snippets/speech_synthesis-(experimental).md diff --git a/snippets/Speech_synthesis.md b/snippets/Speech_synthesis.md deleted file mode 100644 index 022601472..000000000 --- a/snippets/Speech_synthesis.md +++ /dev/null @@ -1,15 +0,0 @@ -### Speech synthesis - -Currently The SpeechSynthesisUtterance interface of the Web Speech API represents a speech request. -It contains the content the speech service should read and information about how to read it (e.g. language, pitch and volume.) - -To know more - https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance - -``` -const speak = message => { - const msg = new SpeechSynthesisUtterance(message); - msg.voice = window.speechSynthesis.getVoices()[0]; - window.speechSynthesis.speak(msg); -} -speak('Hello, World') -``` diff --git a/snippets/speech_synthesis-(experimental).md b/snippets/speech_synthesis-(experimental).md new file mode 100644 index 000000000..74cdcf161 --- /dev/null +++ b/snippets/speech_synthesis-(experimental).md @@ -0,0 +1,15 @@ +### Speech synthesis (experimental) + +Use `SpeechSynthesisUtterance.voice` and `indow.speechSynthesis.getVoices()` to convert a message to speech. +Use `window.speechSynthesis.speak()` to play the message. + +Learn more about the [SpeechSynthesisUtterance interface of the Web Speech API](https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance). + +```js +const speak = message => { + const msg = new SpeechSynthesisUtterance(message); + msg.voice = window.speechSynthesis.getVoices()[0]; + window.speechSynthesis.speak(msg); +} +// speak('Hello, World') -> plays the message +``` From 3f8ca8d615cf994a199d8f717147550acb5ab62b Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:49:06 +0200 Subject: [PATCH 53/92] Tag and build --- README.md | 22 ++++++++++++++++++++++ tag_database | 1 + 2 files changed, 23 insertions(+) diff --git a/README.md b/README.md index 6c3c68b31..3f3da1a6b 100644 --- a/README.md +++ b/README.md @@ -73,6 +73,9 @@ * [Powerset](#powerset) * [Standard deviation](#standard-deviation) +### Media +* [Speech_synthesis (experimental)](#speech_synthesis-experimental) + ### Object * [Object from key value pairs](#object-from-key-value-pairs) * [Object to key value pairs](#object-to-key-value-pairs) @@ -812,6 +815,25 @@ const standardDeviation = (arr, usePopulation = false) => { // standardDeviation([10,2,38,23,38,23,21], true) -> 12.29899614287479 (population) ``` +[⬆ back to top](#table-of-contents) +## Media + +### Speech synthesis (experimental) + +Use `SpeechSynthesisUtterance.voice` and `indow.speechSynthesis.getVoices()` to convert a message to speech. +Use `window.speechSynthesis.speak()` to play the message. + +Learn more about the [SpeechSynthesisUtterance interface of the Web Speech API](https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance). + +```js +const speak = message => { + const msg = new SpeechSynthesisUtterance(message); + msg.voice = window.speechSynthesis.getVoices()[0]; + window.speechSynthesis.speak(msg); +} +// speak('Hello, World') -> plays the message +``` + [⬆ back to top](#table-of-contents) ## Object diff --git a/tag_database b/tag_database index a8d4fa8dd..01c21bce9 100644 --- a/tag_database +++ b/tag_database @@ -68,6 +68,7 @@ shuffle-array:array similarity-between-arrays:array sleep:function sort-characters-in-string-(alphabetical):string +speech_synthesis-(experimental):media standard-deviation:math sum-of-array-of-numbers:array swap-values-of-two-variables:utility From 3fde98fc2e92f325c33c9b8217927a42bce5fff5 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:52:07 +0200 Subject: [PATCH 54/92] Lint and build --- .gitignore | 2 +- README.md | 6 +++--- scripts/lint-script.js | 4 ++-- snippets/curry.md | 2 +- snippets/get-days-difference-between-dates.md | 2 +- snippets/speech_synthesis-(experimental).md | 2 +- 6 files changed, 9 insertions(+), 9 deletions(-) diff --git a/.gitignore b/.gitignore index bc23f6a88..9fe5cb489 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,3 @@ node_modules/ - currentSnippet\.js +*.md.temp.js diff --git a/README.md b/README.md index 3f3da1a6b..142e14a79 100644 --- a/README.md +++ b/README.md @@ -572,7 +572,7 @@ Calculate the difference (in days) between to `Date` objects. ```js const getDaysDiffBetweenDates = (dateInitial, dateFinal) => (dateFinal - dateInitial) / (1000 * 3600 * 24); -//getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 +// getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 ``` [⬆ back to top](#table-of-contents) @@ -606,7 +606,7 @@ If you want to curry a function that accepts a variable number of arguments (a v const curry = (fn, arity = fn.length, ...args) => arity <= args.length ? fn(...args) - : curry.bind(null, fn, arity, ...args) + : curry.bind(null, fn, arity, ...args); // curry(Math.pow)(2)(10) -> 1024 // curry(Math.min, 3)(10)(50)(2) -> 2 ``` @@ -830,7 +830,7 @@ const speak = message => { const msg = new SpeechSynthesisUtterance(message); msg.voice = window.speechSynthesis.getVoices()[0]; window.speechSynthesis.speak(msg); -} +}; // speak('Hello, World') -> plays the message ``` diff --git a/scripts/lint-script.js b/scripts/lint-script.js index 3aba12d27..5d6d8721e 100644 --- a/scripts/lint-script.js +++ b/scripts/lint-script.js @@ -3,7 +3,7 @@ Run using `npm run linter`. */ // Load modules -const fs = require('fs-extra'), cp = require('child_process'), path = require('path'); +const fs = require('fs-extra'), cp = require('child_process'), path = require('path'), chalk = require('chalk'); // Set variables for paths var snippetsPath = './snippets'; // Read files, lint each one individually and update @@ -32,7 +32,7 @@ try { fs.writeFile(path.join(snippetsPath,snippet), `${snippetData.slice(0, snippetData.indexOf('```js')+5)+lintedCode+'```\n'}`); fs.unlink(`${snippet}.temp.js`); // Log a success message - console.log(`${chalk.red('SUCCESS!')} Linted snippet: ${snippet}`); + console.log(`${chalk.green('SUCCESS!')} Linted snippet: ${snippet}`); // Log the time taken for the file console.timeEnd(`Linter (${snippet})`); }); diff --git a/snippets/curry.md b/snippets/curry.md index b47492721..bbee4086c 100644 --- a/snippets/curry.md +++ b/snippets/curry.md @@ -9,7 +9,7 @@ If you want to curry a function that accepts a variable number of arguments (a v const curry = (fn, arity = fn.length, ...args) => arity <= args.length ? fn(...args) - : curry.bind(null, fn, arity, ...args) + : curry.bind(null, fn, arity, ...args); // curry(Math.pow)(2)(10) -> 1024 // curry(Math.min, 3)(10)(50)(2) -> 2 ``` diff --git a/snippets/get-days-difference-between-dates.md b/snippets/get-days-difference-between-dates.md index d97463adb..ae93ce79d 100644 --- a/snippets/get-days-difference-between-dates.md +++ b/snippets/get-days-difference-between-dates.md @@ -4,5 +4,5 @@ Calculate the difference (in days) between to `Date` objects. ```js const getDaysDiffBetweenDates = (dateInitial, dateFinal) => (dateFinal - dateInitial) / (1000 * 3600 * 24); -//getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 +// getDaysDiffBetweenDates(new Date("2017-12-13"), new Date("2017-12-22")) -> 9 ``` diff --git a/snippets/speech_synthesis-(experimental).md b/snippets/speech_synthesis-(experimental).md index 74cdcf161..c9e6a288c 100644 --- a/snippets/speech_synthesis-(experimental).md +++ b/snippets/speech_synthesis-(experimental).md @@ -10,6 +10,6 @@ const speak = message => { const msg = new SpeechSynthesisUtterance(message); msg.voice = window.speechSynthesis.getVoices()[0]; window.speechSynthesis.speak(msg); -} +}; // speak('Hello, World') -> plays the message ``` From d15ef2afa989d7f4477bb27e1e0494aae06e5505 Mon Sep 17 00:00:00 2001 From: Arjun Mahishi Date: Fri, 15 Dec 2017 00:23:10 +0530 Subject: [PATCH 55/92] Added snippet to convert number to array of digits --- snippets/number-to-array-of-digits.md | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 snippets/number-to-array-of-digits.md diff --git a/snippets/number-to-array-of-digits.md b/snippets/number-to-array-of-digits.md new file mode 100644 index 000000000..710540762 --- /dev/null +++ b/snippets/number-to-array-of-digits.md @@ -0,0 +1,17 @@ +### Number to array to digits + +use `parseInt()` to get only the integer part of the quotient. +use `Array.reverse()` to return the array in the same order as the number. + +```js +const num2array = (n) =>{ + let arr = []; + while (n>0) { + arr.push(n%10); + n = parseInt(n/10); + } + return arr.reverse(); +} + +// num2array(2334) -> [2, 3, 3, 4] +``` \ No newline at end of file From a14f144436aef18eb28664630a9c5a30bbd0b877 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 20:53:53 +0200 Subject: [PATCH 56/92] Fix filename --- README.md | 17 +---------------- ...l).md => speech-synthesis-(experimental).md} | 0 2 files changed, 1 insertion(+), 16 deletions(-) rename snippets/{speech_synthesis-(experimental).md => speech-synthesis-(experimental).md} (100%) diff --git a/README.md b/README.md index 142e14a79..f15c1af45 100644 --- a/README.md +++ b/README.md @@ -818,22 +818,7 @@ const standardDeviation = (arr, usePopulation = false) => { [⬆ back to top](#table-of-contents) ## Media -### Speech synthesis (experimental) - -Use `SpeechSynthesisUtterance.voice` and `indow.speechSynthesis.getVoices()` to convert a message to speech. -Use `window.speechSynthesis.speak()` to play the message. - -Learn more about the [SpeechSynthesisUtterance interface of the Web Speech API](https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance). - -```js -const speak = message => { - const msg = new SpeechSynthesisUtterance(message); - msg.voice = window.speechSynthesis.getVoices()[0]; - window.speechSynthesis.speak(msg); -}; -// speak('Hello, World') -> plays the message -``` - +undefined [⬆ back to top](#table-of-contents) ## Object diff --git a/snippets/speech_synthesis-(experimental).md b/snippets/speech-synthesis-(experimental).md similarity index 100% rename from snippets/speech_synthesis-(experimental).md rename to snippets/speech-synthesis-(experimental).md From 655584d0ed8d6dc91c0a805c40a8a581da41bdc3 Mon Sep 17 00:00:00 2001 From: Arjun Mahishi Date: Fri, 15 Dec 2017 00:25:46 +0530 Subject: [PATCH 57/92] Fixed typo --- snippets/number-to-array-of-digits.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/number-to-array-of-digits.md b/snippets/number-to-array-of-digits.md index 710540762..aa4652fa7 100644 --- a/snippets/number-to-array-of-digits.md +++ b/snippets/number-to-array-of-digits.md @@ -1,4 +1,4 @@ -### Number to array to digits +### Number to array of digits use `parseInt()` to get only the integer part of the quotient. use `Array.reverse()` to return the array in the same order as the number. From 6ef96cc3a616f599517bc32801a177bc66538608 Mon Sep 17 00:00:00 2001 From: Arjun Mahishi Date: Fri, 15 Dec 2017 00:37:32 +0530 Subject: [PATCH 58/92] updated changes --- snippets/number-to-array-of-digits.md | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/snippets/number-to-array-of-digits.md b/snippets/number-to-array-of-digits.md index aa4652fa7..63fe6c907 100644 --- a/snippets/number-to-array-of-digits.md +++ b/snippets/number-to-array-of-digits.md @@ -5,12 +5,9 @@ use `Array.reverse()` to return the array in the same order as the number. ```js const num2array = (n) =>{ - let arr = []; - while (n>0) { - arr.push(n%10); - n = parseInt(n/10); - } - return arr.reverse(); + return (''+n).split('').map((i) =>{ + return parseInt(i); + }) } // num2array(2334) -> [2, 3, 3, 4] From f827f0d1090bf77f8940f59727a4cca0027d3456 Mon Sep 17 00:00:00 2001 From: Arjun Mahishi Date: Fri, 15 Dec 2017 00:44:39 +0530 Subject: [PATCH 59/92] updated changes --- snippets/number-to-array-of-digits.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/snippets/number-to-array-of-digits.md b/snippets/number-to-array-of-digits.md index 63fe6c907..9493c279f 100644 --- a/snippets/number-to-array-of-digits.md +++ b/snippets/number-to-array-of-digits.md @@ -1,7 +1,7 @@ ### Number to array of digits -use `parseInt()` to get only the integer part of the quotient. -use `Array.reverse()` to return the array in the same order as the number. +Convert the number to a string, split the string using `split()`. +use `parseInt()` to convert every element back to integer. ```js const num2array = (n) =>{ From 69b3e2b97fa775cfae4e35462303e3e7b7856c59 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 22:53:42 +0200 Subject: [PATCH 60/92] Update number-to-array-of-digits.md --- snippets/number-to-array-of-digits.md | 15 +++++---------- 1 file changed, 5 insertions(+), 10 deletions(-) diff --git a/snippets/number-to-array-of-digits.md b/snippets/number-to-array-of-digits.md index 9493c279f..f00a62b75 100644 --- a/snippets/number-to-array-of-digits.md +++ b/snippets/number-to-array-of-digits.md @@ -1,14 +1,9 @@ ### Number to array of digits -Convert the number to a string, split the string using `split()`. -use `parseInt()` to convert every element back to integer. +Convert the number to a string, use `split()` to convert build an array. +Use `Array.map()` and `parseInt()` to transform each value to an integer. ```js -const num2array = (n) =>{ - return (''+n).split('').map((i) =>{ - return parseInt(i); - }) -} - -// num2array(2334) -> [2, 3, 3, 4] -``` \ No newline at end of file +const digitize = n => (''+n).split('').map(i => parseInt(i)); +// digitize(2334) -> [2, 3, 3, 4] +``` From aafeaaabdac18d330ea3e62f1318cca0571fac92 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 23:00:38 +0200 Subject: [PATCH 61/92] Tag, lint, build --- README.md | 32 ++++++++++++++++++++++++++++++-- tag_database | 3 ++- 2 files changed, 32 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index f15c1af45..90e814bc8 100644 --- a/README.md +++ b/README.md @@ -74,7 +74,7 @@ * [Standard deviation](#standard-deviation) ### Media -* [Speech_synthesis (experimental)](#speech_synthesis-experimental) +* [Speech synthesis (experimental)](#speech-synthesis-experimental) ### Object * [Object from key value pairs](#object-from-key-value-pairs) @@ -99,6 +99,7 @@ * [Is string](#is-string) * [Is symbol](#is-symbol) * [Measure time taken by function](#measure-time-taken-by-function) +* [Number to array of digits](#number-to-array-of-digits) * [Ordinal suffix of number](#ordinal-suffix-of-number) * [Random integer in range](#random-integer-in-range) * [Random number in range](#random-number-in-range) @@ -818,7 +819,22 @@ const standardDeviation = (arr, usePopulation = false) => { [⬆ back to top](#table-of-contents) ## Media -undefined +### Speech synthesis (experimental) + +Use `SpeechSynthesisUtterance.voice` and `indow.speechSynthesis.getVoices()` to convert a message to speech. +Use `window.speechSynthesis.speak()` to play the message. + +Learn more about the [SpeechSynthesisUtterance interface of the Web Speech API](https://developer.mozilla.org/en-US/docs/Web/API/SpeechSynthesisUtterance). + +```js +const speak = message => { + const msg = new SpeechSynthesisUtterance(message); + msg.voice = window.speechSynthesis.getVoices()[0]; + window.speechSynthesis.speak(msg); +}; +// speak('Hello, World') -> plays the message +``` + [⬆ back to top](#table-of-contents) ## Object @@ -1051,6 +1067,18 @@ const timeTaken = callback => { [⬆ back to top](#table-of-contents) +### Number to array of digits + +Convert the number to a string, use `split()` to convert build an array. +Use `Array.map()` and `parseInt()` to transform each value to an integer. + +```js +const digitize = n => (''+n).split('').map(i => parseInt(i)); +// digitize(2334) -> [2, 3, 3, 4] +``` + +[⬆ back to top](#table-of-contents) + ### Ordinal suffix of number Use the modulo operator (`%`) to find values of single and tens digits. diff --git a/tag_database b/tag_database index 01c21bce9..7f81cbec1 100644 --- a/tag_database +++ b/tag_database @@ -49,6 +49,7 @@ is-symbol:utility last-of-list:array measure-time-taken-by-function:utility median-of-array-of-numbers:array +number-to-array-of-digits:utility object-from-key-value-pairs:object object-to-key-value-pairs:object ordinal-suffix-of-number:utility @@ -68,7 +69,7 @@ shuffle-array:array similarity-between-arrays:array sleep:function sort-characters-in-string-(alphabetical):string -speech_synthesis-(experimental):media +speech-synthesis-(experimental):media standard-deviation:math sum-of-array-of-numbers:array swap-values-of-two-variables:utility From d9821bfafdfe3cbcde5fb32fda9eb94736f762d1 Mon Sep 17 00:00:00 2001 From: Eric Wyne Date: Thu, 14 Dec 2017 13:09:08 -0800 Subject: [PATCH 62/92] round number to n digits --- snippets/round-number-to-n-digits.md | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 snippets/round-number-to-n-digits.md diff --git a/snippets/round-number-to-n-digits.md b/snippets/round-number-to-n-digits.md new file mode 100644 index 000000000..0c33b5b4f --- /dev/null +++ b/snippets/round-number-to-n-digits.md @@ -0,0 +1,9 @@ +### Round number to n digits + +Correctly rounds a number to the specified number of digits. + +```js +const round = (n, decimals = 0) => + Number(`${Math.round(`${n}e${decimals}`)}e-${decimals}`) +// round(1.005, 2) -> 1.01 +``` From 9d29636e43b84721ca02b34f9bfe6719e770b546 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 23:11:52 +0200 Subject: [PATCH 63/92] Create nth-element-of-array.md --- snippets/nth-element-of-array.md | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 snippets/nth-element-of-array.md diff --git a/snippets/nth-element-of-array.md b/snippets/nth-element-of-array.md new file mode 100644 index 000000000..15552d071 --- /dev/null +++ b/snippets/nth-element-of-array.md @@ -0,0 +1,11 @@ +### Nth element of array + +Use `Array.slice()` to get an array containing the nth element at the first place. +If the index is out of bounds, return `[]`. +Omit the second argument, `n`, to get the first element of the array. + +```js +const nth = (arr, n=0) => (n>0? arr.slice(n,n+1) : arr.slice(n))[0]; +// nth(['a','b','c'],1) -> 'b' +// nth(['a','b','b']-2) -> 'a' +``` From cbe7d80ba573333103ea0cc1e26053f32a198842 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 23:15:34 +0200 Subject: [PATCH 64/92] Update round-number-to-n-digits.md --- snippets/round-number-to-n-digits.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/snippets/round-number-to-n-digits.md b/snippets/round-number-to-n-digits.md index 0c33b5b4f..a35308ce0 100644 --- a/snippets/round-number-to-n-digits.md +++ b/snippets/round-number-to-n-digits.md @@ -1,9 +1,9 @@ ### Round number to n digits -Correctly rounds a number to the specified number of digits. +Use `Math.round()` and template literals to round the number to the specified number of digits. +Omit the second argument, `decimals` to round to an integer. ```js -const round = (n, decimals = 0) => - Number(`${Math.round(`${n}e${decimals}`)}e-${decimals}`) +const round = (n, decimals=0) => Number(`${Math.round(`${n}e${decimals}`)}e-${decimals}`); // round(1.005, 2) -> 1.01 ``` From 6ced078936f9c30fdcac057610c9db16058bc800 Mon Sep 17 00:00:00 2001 From: atomiks Date: Fri, 15 Dec 2017 08:17:21 +1100 Subject: [PATCH 65/92] Create shallow-clone-object.md We need a deep clone too but that's a different animal. `JSON.parse(JSON.stringify(obj))` is not very good because it strips functions, etc. --- snippets/shallow-clone-object.md | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 snippets/shallow-clone-object.md diff --git a/snippets/shallow-clone-object.md b/snippets/shallow-clone-object.md new file mode 100644 index 000000000..7993e8243 --- /dev/null +++ b/snippets/shallow-clone-object.md @@ -0,0 +1,12 @@ +### Shallow clone object + +Use the object spread operator to spread the properties of the target object into the clone. + +```js +const shallowClone = obj => ({ ...obj }); +/* +const a = { x: true, y: 1 }; +const b = shallowClone(a); +a === b -> false +*/ +``` From db097c03f266393ee384b4633c1077d7e84defb9 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 23:27:27 +0200 Subject: [PATCH 66/92] Update shallow-clone-object.md --- snippets/shallow-clone-object.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/shallow-clone-object.md b/snippets/shallow-clone-object.md index 7993e8243..c6873c0d8 100644 --- a/snippets/shallow-clone-object.md +++ b/snippets/shallow-clone-object.md @@ -1,6 +1,6 @@ ### Shallow clone object -Use the object spread operator to spread the properties of the target object into the clone. +Use the object `...spread` operator to spread the properties of the target object into the clone. ```js const shallowClone = obj => ({ ...obj }); From 6074aa67545312b18d84336b8a31f408d3dcd029 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 23:29:12 +0200 Subject: [PATCH 67/92] Tag, lint, build --- README.md | 44 ++++++++++++++++++++++++++++++++++++++++++++ tag_database | 3 +++ 2 files changed, 47 insertions(+) diff --git a/README.md b/README.md index 90e814bc8..367898d9e 100644 --- a/README.md +++ b/README.md @@ -33,6 +33,7 @@ * [Initialize array with values](#initialize-array-with-values) * [Last of list](#last-of-list) * [Median of array of numbers](#median-of-array-of-numbers) +* [Nth element of array](#nth-element-of-array) * [Pick](#pick) * [Shuffle array](#shuffle-array) * [Similarity between arrays](#similarity-between-arrays) @@ -71,6 +72,7 @@ * [Hamming distance](#hamming-distance) * [Percentile](#percentile) * [Powerset](#powerset) +* [Round number to n digits](#round-number-to-n-digits) * [Standard deviation](#standard-deviation) ### Media @@ -79,6 +81,7 @@ ### Object * [Object from key value pairs](#object-from-key-value-pairs) * [Object to key value pairs](#object-to-key-value-pairs) +* [Shallow clone object](#shallow-clone-object) ### String * [Anagrams of string (with duplicates)](#anagrams-of-string-with-duplicates) @@ -394,6 +397,20 @@ const median = arr => { [⬆ back to top](#table-of-contents) +### Nth element of array + +Use `Array.slice()` to get an array containing the nth element at the first place. +If the index is out of bounds, return `[]`. +Omit the second argument, `n`, to get the first element of the array. + +```js +const nth = (arr, n=0) => (n>0? arr.slice(n,n+1) : arr.slice(n))[0]; +// nth(['a','b','c'],1) -> 'b' +// nth(['a','b','b']-2) -> 'a' +``` + +[⬆ back to top](#table-of-contents) + ### Pick Use `Array.reduce()` to convert the filtered/picked keys back to a object with the corresponding key:value pair if the key exist in the obj. @@ -798,6 +815,18 @@ const powerset = arr => [⬆ back to top](#table-of-contents) +### Round number to n digits + +Use `Math.round()` and template literals to round the number to the specified number of digits. +Omit the second argument, `decimals` to round to an integer. + +```js +const round = (n, decimals=0) => Number(`${Math.round(`${n}e${decimals}`)}e-${decimals}`); +// round(1.005, 2) -> 1.01 +``` + +[⬆ back to top](#table-of-contents) + ### Standard deviation Use `Array.reduce()` to calculate the mean, variance and the sum of the variance of the values, the variance of the values, then @@ -858,6 +887,21 @@ const objectToPairs = obj => Object.keys(obj).map(k => [k, obj[k]]); // objectToPairs({a: 1, b: 2}) -> [['a',1],['b',2]]) ``` +[⬆ back to top](#table-of-contents) + +### Shallow clone object + +Use the object `...spread` operator to spread the properties of the target object into the clone. + +```js +const shallowClone = obj => ({ ...obj }); +/* +const a = { x: true, y: 1 }; +const b = shallowClone(a); +a === b -> false +*/ +``` + [⬆ back to top](#table-of-contents) ## String diff --git a/tag_database b/tag_database index 7f81cbec1..b2535a484 100644 --- a/tag_database +++ b/tag_database @@ -49,6 +49,7 @@ is-symbol:utility last-of-list:array measure-time-taken-by-function:utility median-of-array-of-numbers:array +nth-element-of-array:array number-to-array-of-digits:utility object-from-key-value-pairs:object object-to-key-value-pairs:object @@ -63,8 +64,10 @@ random-number-in-range:utility redirect-to-URL:browser reverse-a-string:string RGB-to-hexadecimal:utility +round-number-to-n-digits:math run-promises-in-series:function scroll-to-top:browser +shallow-clone-object:object shuffle-array:array similarity-between-arrays:array sleep:function From 94799c46d91efd79c319e8b59a80c3b63a4b7549 Mon Sep 17 00:00:00 2001 From: atomiks Date: Fri, 15 Dec 2017 08:43:47 +1100 Subject: [PATCH 68/92] Update measure-time-taken-by-function.md --- snippets/measure-time-taken-by-function.md | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/snippets/measure-time-taken-by-function.md b/snippets/measure-time-taken-by-function.md index 44e099d7e..ca476ac71 100644 --- a/snippets/measure-time-taken-by-function.md +++ b/snippets/measure-time-taken-by-function.md @@ -1,13 +1,14 @@ ### Measure time taken by function -Use `performance.now()` to get start and end time for the function, `console.log()` the time taken. -Pass a callback function as the argument. +Use `console.time()` and `console.timeEnd()` to measure the difference between the start and end times to determine how long the callback took to execute. ```js const timeTaken = callback => { - const t0 = performance.now(), r = callback(); - console.log(performance.now() - t0); + console.time('timeTaken'); + const r = callback(); + console.timeEnd('timeTaken'); return r; }; -// timeTaken(() => Math.pow(2, 10)) -> 1024 (0.010000000009313226 logged in console) +// timeTaken(() => Math.pow(2, 10)) -> 1024 +// (logged): timeTaken: 0.02099609375ms ``` From ddbcf684560e19b4449b37ffeb06f3a46a2067b6 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Thu, 14 Dec 2017 23:47:46 +0200 Subject: [PATCH 69/92] Build README --- README.md | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 367898d9e..7160b9afb 100644 --- a/README.md +++ b/README.md @@ -1097,16 +1097,17 @@ const isSymbol = val => typeof val === 'symbol'; ### Measure time taken by function -Use `performance.now()` to get start and end time for the function, `console.log()` the time taken. -Pass a callback function as the argument. +Use `console.time()` and `console.timeEnd()` to measure the difference between the start and end times to determine how long the callback took to execute. ```js const timeTaken = callback => { - const t0 = performance.now(), r = callback(); - console.log(performance.now() - t0); + console.time('timeTaken'); + const r = callback(); + console.timeEnd('timeTaken'); return r; }; -// timeTaken(() => Math.pow(2, 10)) -> 1024 (0.010000000009313226 logged in console) +// timeTaken(() => Math.pow(2, 10)) -> 1024 +// (logged): timeTaken: 0.02099609375ms ``` [⬆ back to top](#table-of-contents) From 671ea5a330d181d789f6143222b6468356855a81 Mon Sep 17 00:00:00 2001 From: Justin Lee Date: Thu, 14 Dec 2017 14:44:38 -0800 Subject: [PATCH 70/92] Rewrote pipe such that the first function may have any arity. --- snippets/pipe.md | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/snippets/pipe.md b/snippets/pipe.md index c61ec042c..11803210c 100644 --- a/snippets/pipe.md +++ b/snippets/pipe.md @@ -1,8 +1,18 @@ ### Pipe -Use `Array.reduce()` to pass value through functions. +Use `Array.reduce()` to perform left-to-right function composition. The first (leftmost) function can accept one or more arguments; the remaining functions must be unary. ```js -const pipe = (...funcs) => arg => funcs.reduce((acc, func) => func(acc), arg); -// pipe(btoa, x => x.toUpperCase())("Test") -> "VGVZDA==" +const pipe = (...fns) => fns.reduce((f, g) => (...args) => g(f(...args))) +/* +const add5 = (x) => x + 5 +const multiply = (x, y) => x * y + +const multiplyAndAdd5 = pipe( + multiply, + add5 +) + +multiplyAndAdd5(5, 2) -> 15 +*/ ``` From 89cb11bccc1c6cc73cd4e4115e4fb237fad06d28 Mon Sep 17 00:00:00 2001 From: Justin Lee Date: Thu, 14 Dec 2017 14:52:25 -0800 Subject: [PATCH 71/92] removed unnecessary brackets around one parameter function --- snippets/pipe.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/pipe.md b/snippets/pipe.md index 11803210c..9c13f5e27 100644 --- a/snippets/pipe.md +++ b/snippets/pipe.md @@ -5,7 +5,7 @@ Use `Array.reduce()` to perform left-to-right function composition. The first (l ```js const pipe = (...fns) => fns.reduce((f, g) => (...args) => g(f(...args))) /* -const add5 = (x) => x + 5 +const add5 = x => x + 5 const multiply = (x, y) => x * y const multiplyAndAdd5 = pipe( From 0925f657da016ee9ee739a10d7532aef94cb5f6d Mon Sep 17 00:00:00 2001 From: Justin Lee Date: Thu, 14 Dec 2017 14:53:20 -0800 Subject: [PATCH 72/92] Placed parameters of pipe on one line for better readability --- snippets/pipe.md | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/snippets/pipe.md b/snippets/pipe.md index 9c13f5e27..f46a32148 100644 --- a/snippets/pipe.md +++ b/snippets/pipe.md @@ -8,10 +8,7 @@ const pipe = (...fns) => fns.reduce((f, g) => (...args) => g(f(...args))) const add5 = x => x + 5 const multiply = (x, y) => x * y -const multiplyAndAdd5 = pipe( - multiply, - add5 -) +const multiplyAndAdd5 = pipe(multiply, add5) multiplyAndAdd5(5, 2) -> 15 */ From ffb917e72dbbffb983e7745c137e800d290a95b9 Mon Sep 17 00:00:00 2001 From: taltmann42 Date: Thu, 14 Dec 2017 23:54:55 +0100 Subject: [PATCH 73/92] Array zip Zip method from https://lodash.com/docs/4.17.4#zip --- snippets/array-zip.md | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 snippets/array-zip.md diff --git a/snippets/array-zip.md b/snippets/array-zip.md new file mode 100644 index 000000000..d63f79b15 --- /dev/null +++ b/snippets/array-zip.md @@ -0,0 +1,17 @@ +### Array zip + +Use `Math.max.apply` to get the longest array in the arguments. +Creates an array with that length as return value and use `Array.from` with a map-function to create an array of grouped elements. +If lengths of the argument-arrays vary, `undefined` is used where no value could be found. + +```js +const zip = (...arrays) => { + const maxLength = Math.max.apply(null, arrays.map(a => a.length)); + return Array.from({length: maxLength}).map((_, i) => { + return Array.from({length: arrays.length}, (_, k) => arrays[k][i]) + }) +} + +//zip(['a', 'b'], [1, 2], [true, false]); -> [['a', 1, true], ['b', 2, false]] +zip(['a'], [1, 2], [true, false]); -> [['a', 1, true], [undefined, 2, false]] +``` From 74b5a78f2b5def73bb759544c35810b1a6c4fe2e Mon Sep 17 00:00:00 2001 From: taltmann42 Date: Thu, 14 Dec 2017 23:56:51 +0100 Subject: [PATCH 74/92] Update array-zip.md --- snippets/array-zip.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/array-zip.md b/snippets/array-zip.md index d63f79b15..08c40ed68 100644 --- a/snippets/array-zip.md +++ b/snippets/array-zip.md @@ -13,5 +13,5 @@ const zip = (...arrays) => { } //zip(['a', 'b'], [1, 2], [true, false]); -> [['a', 1, true], ['b', 2, false]] -zip(['a'], [1, 2], [true, false]); -> [['a', 1, true], [undefined, 2, false]] +//zip(['a'], [1, 2], [true, false]); -> [['a', 1, true], [undefined, 2, false]] ``` From e96393019c10ac004c96743fc9aa909042ceea16 Mon Sep 17 00:00:00 2001 From: taltmann42 Date: Fri, 15 Dec 2017 00:23:10 +0100 Subject: [PATCH 75/92] Create array-without.md --- snippets/array-without.md | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 snippets/array-without.md diff --git a/snippets/array-without.md b/snippets/array-without.md new file mode 100644 index 000000000..353d1308e --- /dev/null +++ b/snippets/array-without.md @@ -0,0 +1,9 @@ +### Array without + +Filters out array elements if they are included in the given `values` arguments + +```js +const without = ((arr, ...values) => arr.filter(x => !values.includes(x))) + +//without([2, 1, 2, 3], 1, 2); -> [3] +``` From fc5e66a141d51d11e9c8815abcb4a7a3338b1bb4 Mon Sep 17 00:00:00 2001 From: taltmann42 Date: Fri, 15 Dec 2017 00:30:18 +0100 Subject: [PATCH 76/92] Delete array-without.md --- snippets/array-without.md | 9 --------- 1 file changed, 9 deletions(-) delete mode 100644 snippets/array-without.md diff --git a/snippets/array-without.md b/snippets/array-without.md deleted file mode 100644 index 353d1308e..000000000 --- a/snippets/array-without.md +++ /dev/null @@ -1,9 +0,0 @@ -### Array without - -Filters out array elements if they are included in the given `values` arguments - -```js -const without = ((arr, ...values) => arr.filter(x => !values.includes(x))) - -//without([2, 1, 2, 3], 1, 2); -> [3] -``` From d79ffc0f24c7c0c8977dc4fc4625bfa12141c90a Mon Sep 17 00:00:00 2001 From: King Date: Thu, 14 Dec 2017 19:00:10 -0500 Subject: [PATCH 77/92] add takeRight --- snippets/takeRight.md | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 snippets/takeRight.md diff --git a/snippets/takeRight.md b/snippets/takeRight.md new file mode 100644 index 000000000..03fc634fa --- /dev/null +++ b/snippets/takeRight.md @@ -0,0 +1,10 @@ +### takeRight + +Use `Array.slice()` to create a slice of the array with `n` elements taken from the end. + +```js +const takeRight = (arr, n = 1) => arr.slice(arr.length - n, arr.length); +// takeRight([1, 2, 3], 2) -> [ 2, 3 ] +// takeRight([1, 2, 3]) -> [3] +// takeRight([1, 2, 3]) -> [] +``` \ No newline at end of file From dca2f9ec077cf028455af150b78c4bbfbd4e2f5d Mon Sep 17 00:00:00 2001 From: King Date: Thu, 14 Dec 2017 19:03:20 -0500 Subject: [PATCH 78/92] ran npm run tagger & add array tag for takeRight --- tag_database | 1 + 1 file changed, 1 insertion(+) diff --git a/tag_database b/tag_database index b2535a484..a174c20c3 100644 --- a/tag_database +++ b/tag_database @@ -78,6 +78,7 @@ sum-of-array-of-numbers:array swap-values-of-two-variables:utility tail-of-list:array take:array +takeRight:array truncate-a-string:string unique-values-of-array:array URL-parameters:utility From 2c9486ae7f73cfdb514be1c136b3ca2783ef2d01 Mon Sep 17 00:00:00 2001 From: xaveyaguarez Date: Thu, 14 Dec 2017 22:34:10 -0800 Subject: [PATCH 79/92] deep flatten array without reduce --- snippets/deep-flatten-array.md | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/snippets/deep-flatten-array.md b/snippets/deep-flatten-array.md index c350d848c..1dffe860f 100644 --- a/snippets/deep-flatten-array.md +++ b/snippets/deep-flatten-array.md @@ -1,10 +1,9 @@ ### Deep flatten array Use recursion. -Use `Array.reduce()` to get all elements that are not arrays, flatten each element that is an array. +Use `[].concat()` and the spread operator `...` to flatten an array, and recursively flatten each element that is an array. ```js -const deepFlatten = arr => - arr.reduce((a, v) => a.concat(Array.isArray(v) ? deepFlatten(v) : v), []); +const deepFlatten = arr => [].concat(...arr.map(v => Array.isArray(v) ? deepFlatten(v) : v)); // deepFlatten([1,[2],[[3],4],5]) -> [1,2,3,4,5] ``` From 54e71191fcec908a8c32b980c17ba252c3deada4 Mon Sep 17 00:00:00 2001 From: King Date: Fri, 15 Dec 2017 02:35:30 -0500 Subject: [PATCH 80/92] add without.md --- snippets/without.md | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 snippets/without.md diff --git a/snippets/without.md b/snippets/without.md new file mode 100644 index 000000000..00876b5c9 --- /dev/null +++ b/snippets/without.md @@ -0,0 +1,12 @@ +### Without + +Use `Array.filter()` to create an array excluding all given values + +```js + +const without = (arr, ...args) => arr.filter(v => args.indexOf(v) === -1) + +// without[2, 1, 2, 3], 1, 2) -> [3] +// without([2, 1, 2, 3, 4, 5, 5, 5, 3, 2, 7, 7], 3, 1, 5, 2) -> [ 4, 7, 7 ] + +``` From 8b03f3d26d7d8a8fd891ad2419d39732e080c377 Mon Sep 17 00:00:00 2001 From: King Date: Fri, 15 Dec 2017 02:37:19 -0500 Subject: [PATCH 81/92] ran npm run tagger & add array tag to DB --- tag_database | 1 + 1 file changed, 1 insertion(+) diff --git a/tag_database b/tag_database index b2535a484..937676886 100644 --- a/tag_database +++ b/tag_database @@ -85,3 +85,4 @@ UUID-generator:utility validate-email:utility validate-number:utility value-or-default:utility +without:array From edd961abc719bd42abe5e6db57219d0ba1aae631 Mon Sep 17 00:00:00 2001 From: Arjun Mahishi Date: Fri, 15 Dec 2017 13:45:12 +0530 Subject: [PATCH 82/92] Added snippet to sample an array --- snippets/array-sample.md | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 snippets/array-sample.md diff --git a/snippets/array-sample.md b/snippets/array-sample.md new file mode 100644 index 000000000..d48f13840 --- /dev/null +++ b/snippets/array-sample.md @@ -0,0 +1,9 @@ +### Array sample + +Use `Math.random()` to generate a random number, multiply it with `Array.length` and round it of to the nearest whole number using `Math.floor()`. Works with strings too. + +```js +const sample = arr => arr[Math.floor(Math.random() * arr.length)]; + +// sample([3, 7, 9, 11]) -> 9 +``` \ No newline at end of file From 5398eaa4d73d230c5593304b0a305aa1274c2408 Mon Sep 17 00:00:00 2001 From: fpluquet Date: Fri, 15 Dec 2017 09:47:57 +0100 Subject: [PATCH 83/92] Update chunk-array.md Fix chunk array result --- snippets/chunk-array.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/chunk-array.md b/snippets/chunk-array.md index c14bf269d..ba3e5e42e 100644 --- a/snippets/chunk-array.md +++ b/snippets/chunk-array.md @@ -7,5 +7,5 @@ If the original array can't be split evenly, the final chunk will contain the re ```js const chunk = (arr, size) => Array.from({length: Math.ceil(arr.length / size)}, (v, i) => arr.slice(i * size, i * size + size)); -// chunk([1,2,3,4,5], 2) -> [[1,2],[3,4],5] +// chunk([1,2,3,4,5], 2) -> [[1,2],[3,4],[5]] ``` From bec3c5afa6d15160675d42145c904eb78132831c Mon Sep 17 00:00:00 2001 From: iamsoorena Date: Fri, 15 Dec 2017 12:56:13 +0330 Subject: [PATCH 84/92] removing unrelated file from "to merge" branch --- snippets/json-cleaner.md | 20 -------------------- 1 file changed, 20 deletions(-) delete mode 100644 snippets/json-cleaner.md diff --git a/snippets/json-cleaner.md b/snippets/json-cleaner.md deleted file mode 100644 index 46ef745dc..000000000 --- a/snippets/json-cleaner.md +++ /dev/null @@ -1,20 +0,0 @@ -### Clean Json objects - -Clean your json object from unwanted keys, deeply. -provide set of `keys` to keep and an indicator for `children` if there is any. - -```js -const cleanObj = (obj, keys = [], childIndicator) => { - Object.keys(obj).forEach(key => { - if (key === childIndicator) { - cleanObj(obj[key], keys, childIndicator) - } else if (!keys.includes(key)) { - delete obj[key] - } - }) -} -/* - dirtyObj = { a: 1, b: 2, children: {a: 1, b :2}} - let cleaned = cleanObj(dirtyObj, [a]) // { a: 1, children : { a: 1}} - */ -``` From 453026fe3b2ccaf246b4bf04f2e58b1db68ba9ca Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Fri, 15 Dec 2017 12:53:09 +0200 Subject: [PATCH 85/92] Tag, lint, build --- README.md | 79 +++++++++++++++++++++-- snippets/array-sample.md | 8 +-- snippets/{without.md => array-without.md} | 9 +-- snippets/array-zip.md | 7 +- snippets/deep-flatten-array.md | 3 +- snippets/pipe.md | 9 ++- snippets/{takeRight.md => take-right.md} | 5 +- tag_database | 6 +- 8 files changed, 94 insertions(+), 32 deletions(-) rename snippets/{without.md => array-without.md} (88%) rename snippets/{takeRight.md => take-right.md} (83%) diff --git a/README.md b/README.md index 7160b9afb..b8412a802 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,10 @@ * [Array concatenation](#array-concatenation) * [Array difference](#array-difference) * [Array intersection](#array-intersection) +* [Array sample](#array-sample) * [Array union](#array-union) +* [Array without](#array-without) +* [Array zip](#array-zip) * [Average of array of numbers](#average-of-array-of-numbers) * [Chunk array](#chunk-array) * [Compact](#compact) @@ -39,6 +42,7 @@ * [Similarity between arrays](#similarity-between-arrays) * [Sum of array of numbers](#sum-of-array-of-numbers) * [Tail of list](#tail-of-list) +* [Take right](#take-right) * [Take](#take) * [Unique values of array](#unique-values-of-array) @@ -149,6 +153,18 @@ const intersection = (a, b) => { const s = new Set(b); return a.filter(x => s.ha [⬆ back to top](#table-of-contents) +### Array sample + +Use `Math.random()` to generate a random number, multiply it with `length` and round it of to the nearest whole number using `Math.floor()`. +This method also works with strings. + +```js +const sample = arr => arr[Math.floor(Math.random() * arr.length)]; +// sample([3, 7, 9, 11]) -> 9 +``` + +[⬆ back to top](#table-of-contents) + ### Array union Create a `Set` with all values of `a` and `b` and convert to an array. @@ -160,6 +176,37 @@ const union = (a, b) => Array.from(new Set([...a, ...b])); [⬆ back to top](#table-of-contents) +### Array without + +Use `Array.filter()` to create an array excluding all given values. + +```js +const without = (arr, ...args) => arr.filter(v => args.indexOf(v) === -1); +// without[2, 1, 2, 3], 1, 2) -> [3] +// without([2, 1, 2, 3, 4, 5, 5, 5, 3, 2, 7, 7], 3, 1, 5, 2) -> [ 4, 7, 7 ] +``` + +[⬆ back to top](#table-of-contents) + +### Array zip + +Use `Math.max.apply()` to get the longest array in the arguments. +Creates an array with that length as return value and use `Array.from()` with a map-function to create an array of grouped elements. +If lengths of the argument-arrays vary, `undefined` is used where no value could be found. + +```js +const zip = (...arrays) => { + const maxLength = Math.max.apply(null, arrays.map(a => a.length)); + return Array.from({length: maxLength}).map((_, i) => { + return Array.from({length: arrays.length}, (_, k) => arrays[k][i]); + }) +} +//zip(['a', 'b'], [1, 2], [true, false]); -> [['a', 1, true], ['b', 2, false]] +//zip(['a'], [1, 2], [true, false]); -> [['a', 1, true], [undefined, 2, false]] +``` + +[⬆ back to top](#table-of-contents) + ### Average of array of numbers Use `Array.reduce()` to add each value to an accumulator, initialized with a value of `0`, divide by the `length` of the array. @@ -180,7 +227,7 @@ If the original array can't be split evenly, the final chunk will contain the re ```js const chunk = (arr, size) => Array.from({length: Math.ceil(arr.length / size)}, (v, i) => arr.slice(i * size, i * size + size)); -// chunk([1,2,3,4,5], 2) -> [[1,2],[3,4],5] +// chunk([1,2,3,4,5], 2) -> [[1,2],[3,4],[5]] ``` [⬆ back to top](#table-of-contents) @@ -210,11 +257,11 @@ const countOccurrences = (arr, value) => arr.reduce((a, v) => v === value ? a + ### Deep flatten array Use recursion. -Use `Array.reduce()` to get all elements that are not arrays, flatten each element that is an array. +Use `Array.concat()` with an empty array (`[]`) and the spread operator (`...`) to flatten an array. +Rrecursively flatten each element that is an array. ```js -const deepFlatten = arr => - arr.reduce((a, v) => a.concat(Array.isArray(v) ? deepFlatten(v) : v), []); +const deepFlatten = arr => [].concat(...arr.map(v => Array.isArray(v) ? deepFlatten(v) : v)); // deepFlatten([1,[2],[[3],4],5]) -> [1,2,3,4,5] ``` @@ -469,6 +516,18 @@ const tail = arr => arr.length > 1 ? arr.slice(1) : arr; [⬆ back to top](#table-of-contents) +### Take right + +Use `Array.slice()` to create a slice of the array with `n` elements taken from the end. + +```js +const takeRight = (arr, n = 1) => arr.slice(arr.length - n, arr.length); +// takeRight([1, 2, 3], 2) -> [ 2, 3 ] +// takeRight([1, 2, 3]) -> [3] +``` + +[⬆ back to top](#table-of-contents) + ### Take Use `Array.slice()` to create a slice of the array with `n` elements taken from the beginning. @@ -633,11 +692,17 @@ const curry = (fn, arity = fn.length, ...args) => ### Pipe -Use `Array.reduce()` to pass value through functions. +Use `Array.reduce()` to perform left-to-right function composition. +The first (leftmost) function can accept one or more arguments; the remaining functions must be unary. ```js -const pipe = (...funcs) => arg => funcs.reduce((acc, func) => func(acc), arg); -// pipe(btoa, x => x.toUpperCase())("Test") -> "VGVZDA==" +const pipe = (...fns) => fns.reduce((f, g) => (...args) => g(f(...args))); +/* +const add5 = x => x + 5 +const multiply = (x, y) => x * y +const multiplyAndAdd5 = pipe(multiply, add5) +multiplyAndAdd5(5, 2) -> 15 +*/ ``` [⬆ back to top](#table-of-contents) diff --git a/snippets/array-sample.md b/snippets/array-sample.md index d48f13840..9de5c5ae0 100644 --- a/snippets/array-sample.md +++ b/snippets/array-sample.md @@ -1,9 +1,9 @@ ### Array sample -Use `Math.random()` to generate a random number, multiply it with `Array.length` and round it of to the nearest whole number using `Math.floor()`. Works with strings too. +Use `Math.random()` to generate a random number, multiply it with `length` and round it of to the nearest whole number using `Math.floor()`. +This method also works with strings. ```js const sample = arr => arr[Math.floor(Math.random() * arr.length)]; - -// sample([3, 7, 9, 11]) -> 9 -``` \ No newline at end of file +// sample([3, 7, 9, 11]) -> 9 +``` diff --git a/snippets/without.md b/snippets/array-without.md similarity index 88% rename from snippets/without.md rename to snippets/array-without.md index 00876b5c9..dd657fe2a 100644 --- a/snippets/without.md +++ b/snippets/array-without.md @@ -1,12 +1,9 @@ -### Without +### Array without -Use `Array.filter()` to create an array excluding all given values +Use `Array.filter()` to create an array excluding all given values. ```js - -const without = (arr, ...args) => arr.filter(v => args.indexOf(v) === -1) - +const without = (arr, ...args) => arr.filter(v => args.indexOf(v) === -1); // without[2, 1, 2, 3], 1, 2) -> [3] // without([2, 1, 2, 3, 4, 5, 5, 5, 3, 2, 7, 7], 3, 1, 5, 2) -> [ 4, 7, 7 ] - ``` diff --git a/snippets/array-zip.md b/snippets/array-zip.md index 08c40ed68..6c9a2491b 100644 --- a/snippets/array-zip.md +++ b/snippets/array-zip.md @@ -1,17 +1,16 @@ ### Array zip -Use `Math.max.apply` to get the longest array in the arguments. -Creates an array with that length as return value and use `Array.from` with a map-function to create an array of grouped elements. +Use `Math.max.apply()` to get the longest array in the arguments. +Creates an array with that length as return value and use `Array.from()` with a map-function to create an array of grouped elements. If lengths of the argument-arrays vary, `undefined` is used where no value could be found. ```js const zip = (...arrays) => { const maxLength = Math.max.apply(null, arrays.map(a => a.length)); return Array.from({length: maxLength}).map((_, i) => { - return Array.from({length: arrays.length}, (_, k) => arrays[k][i]) + return Array.from({length: arrays.length}, (_, k) => arrays[k][i]); }) } - //zip(['a', 'b'], [1, 2], [true, false]); -> [['a', 1, true], ['b', 2, false]] //zip(['a'], [1, 2], [true, false]); -> [['a', 1, true], [undefined, 2, false]] ``` diff --git a/snippets/deep-flatten-array.md b/snippets/deep-flatten-array.md index 1dffe860f..d33ff7e25 100644 --- a/snippets/deep-flatten-array.md +++ b/snippets/deep-flatten-array.md @@ -1,7 +1,8 @@ ### Deep flatten array Use recursion. -Use `[].concat()` and the spread operator `...` to flatten an array, and recursively flatten each element that is an array. +Use `Array.concat()` with an empty array (`[]`) and the spread operator (`...`) to flatten an array. +Rrecursively flatten each element that is an array. ```js const deepFlatten = arr => [].concat(...arr.map(v => Array.isArray(v) ? deepFlatten(v) : v)); diff --git a/snippets/pipe.md b/snippets/pipe.md index f46a32148..e5136777b 100644 --- a/snippets/pipe.md +++ b/snippets/pipe.md @@ -1,15 +1,14 @@ ### Pipe -Use `Array.reduce()` to perform left-to-right function composition. The first (leftmost) function can accept one or more arguments; the remaining functions must be unary. +Use `Array.reduce()` to perform left-to-right function composition. +The first (leftmost) function can accept one or more arguments; the remaining functions must be unary. ```js -const pipe = (...fns) => fns.reduce((f, g) => (...args) => g(f(...args))) +const pipe = (...fns) => fns.reduce((f, g) => (...args) => g(f(...args))); /* const add5 = x => x + 5 -const multiply = (x, y) => x * y - +const multiply = (x, y) => x * y const multiplyAndAdd5 = pipe(multiply, add5) - multiplyAndAdd5(5, 2) -> 15 */ ``` diff --git a/snippets/takeRight.md b/snippets/take-right.md similarity index 83% rename from snippets/takeRight.md rename to snippets/take-right.md index 03fc634fa..1e7c55766 100644 --- a/snippets/takeRight.md +++ b/snippets/take-right.md @@ -1,4 +1,4 @@ -### takeRight +### Take right Use `Array.slice()` to create a slice of the array with `n` elements taken from the end. @@ -6,5 +6,4 @@ Use `Array.slice()` to create a slice of the array with `n` elements taken from const takeRight = (arr, n = 1) => arr.slice(arr.length - n, arr.length); // takeRight([1, 2, 3], 2) -> [ 2, 3 ] // takeRight([1, 2, 3]) -> [3] -// takeRight([1, 2, 3]) -> [] -``` \ No newline at end of file +``` diff --git a/tag_database b/tag_database index d1733c293..7e20b7516 100644 --- a/tag_database +++ b/tag_database @@ -2,7 +2,10 @@ anagrams-of-string-(with-duplicates):string array-concatenation:array array-difference:array array-intersection:array +array-sample:array array-union:array +array-without:array +array-zip:array average-of-array-of-numbers:array bottom-visible:browser capitalize-first-letter-of-every-word:string @@ -77,8 +80,8 @@ standard-deviation:math sum-of-array-of-numbers:array swap-values-of-two-variables:utility tail-of-list:array +take-right:array take:array -takeRight:array truncate-a-string:string unique-values-of-array:array URL-parameters:utility @@ -86,4 +89,3 @@ UUID-generator:utility validate-email:utility validate-number:utility value-or-default:utility -without:array From 2b4d7c6ee52adb792881f757043ef5102cb1981c Mon Sep 17 00:00:00 2001 From: Arjun Mahishi Date: Fri, 15 Dec 2017 16:30:12 +0530 Subject: [PATCH 86/92] Added snippet for array includes --- snippets/array-includes.md | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 snippets/array-includes.md diff --git a/snippets/array-includes.md b/snippets/array-includes.md new file mode 100644 index 000000000..c068d17b2 --- /dev/null +++ b/snippets/array-includes.md @@ -0,0 +1,10 @@ +### Array includes + +Use `slice()` to offset the array/string. `Array.indexOf()` returns `-1` if the sub-string/array dosen't contain the given `value`. + +```js +const includes = (collection, val, fromIndex=0) => collection.slice(fromIndex).indexOf(val) != -1; + +// includes("30-seconds-of-code", "code") -> true +// includes([1, 2, 3, 4], [1, 2], 1) -> false +``` \ No newline at end of file From e8293d89de4a515af9d02432254e1a858db16290 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Fri, 15 Dec 2017 13:06:53 +0200 Subject: [PATCH 87/92] Tag, lint, build --- README.md | 14 ++++++++++++++ snippets/array-includes.md | 6 +++--- tag_database | 1 + 3 files changed, 18 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index b8412a802..416266397 100644 --- a/README.md +++ b/README.md @@ -12,6 +12,7 @@ ### Array * [Array concatenation](#array-concatenation) * [Array difference](#array-difference) +* [Array includes](#array-includes) * [Array intersection](#array-intersection) * [Array sample](#array-sample) * [Array union](#array-union) @@ -142,6 +143,19 @@ const difference = (a, b) => { const s = new Set(b); return a.filter(x => !s.has [⬆ back to top](#table-of-contents) +### Array includes + +Use `slice()` to offset the array/string and `indexOf()` to check if the value is included. +Omit the last argument, `fromIndex`, to check the whole array/string. + +```js +const includes = (collection, val, fromIndex=0) => collection.slice(fromIndex).indexOf(val) != -1; +// includes("30-seconds-of-code", "code") -> true +// includes([1, 2, 3, 4], [1, 2], 1) -> false +``` + +[⬆ back to top](#table-of-contents) + ### Array intersection Create a `Set` from `b`, then use `Array.filter()` on `a` to only keep values contained in `b`. diff --git a/snippets/array-includes.md b/snippets/array-includes.md index c068d17b2..5ebcbc009 100644 --- a/snippets/array-includes.md +++ b/snippets/array-includes.md @@ -1,10 +1,10 @@ ### Array includes -Use `slice()` to offset the array/string. `Array.indexOf()` returns `-1` if the sub-string/array dosen't contain the given `value`. +Use `slice()` to offset the array/string and `indexOf()` to check if the value is included. +Omit the last argument, `fromIndex`, to check the whole array/string. ```js const includes = (collection, val, fromIndex=0) => collection.slice(fromIndex).indexOf(val) != -1; - // includes("30-seconds-of-code", "code") -> true // includes([1, 2, 3, 4], [1, 2], 1) -> false -``` \ No newline at end of file +``` diff --git a/tag_database b/tag_database index 7e20b7516..67bdedd3c 100644 --- a/tag_database +++ b/tag_database @@ -1,6 +1,7 @@ anagrams-of-string-(with-duplicates):string array-concatenation:array array-difference:array +array-includes:array array-intersection:array array-sample:array array-union:array From cb488b39742979d664e883f84246b7c4d2208c5d Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Fri, 15 Dec 2017 13:15:21 +0200 Subject: [PATCH 88/92] Update write-json-to-file.md --- snippets/write-json-to-file.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/snippets/write-json-to-file.md b/snippets/write-json-to-file.md index 6a0ae21a0..5cff72064 100644 --- a/snippets/write-json-to-file.md +++ b/snippets/write-json-to-file.md @@ -1,9 +1,9 @@ ### Write a JSON to a file -Write a `json` object to a `.json` file. -```js -const fs = require('fs') +Use `fs.writeFile()`, template literals and `JSON.stringify()` to write a `json` object to a `.json` file. -const jsonToFile = (obj, filename) => fs.writeFile(`${filename}.json`, JSON.stringify(obj, null, 4)) +```js +const fs = require('fs'); +const jsonToFile = (obj, filename) => fs.writeFile(`${filename}.json`, JSON.stringify(obj, null, 2)) // jsonToFile({test: "is passed"}, 'testJsonFile') ``` From 564486472469851e0ff92fb4045afbe795b7c991 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Fri, 15 Dec 2017 13:15:51 +0200 Subject: [PATCH 89/92] Update write-json-to-file.md --- snippets/write-json-to-file.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/snippets/write-json-to-file.md b/snippets/write-json-to-file.md index 5cff72064..17de5a44e 100644 --- a/snippets/write-json-to-file.md +++ b/snippets/write-json-to-file.md @@ -5,5 +5,5 @@ Use `fs.writeFile()`, template literals and `JSON.stringify()` to write a `json` ```js const fs = require('fs'); const jsonToFile = (obj, filename) => fs.writeFile(`${filename}.json`, JSON.stringify(obj, null, 2)) -// jsonToFile({test: "is passed"}, 'testJsonFile') +// jsonToFile({test: "is passed"}, 'testJsonFile') -> writes the object to 'testJsonFile.json' ``` From 6ff467c157238083adc5545b3e664f0e1750ff1f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Stefan=20Feje=C5=A1?= Date: Fri, 15 Dec 2017 12:29:05 +0100 Subject: [PATCH 90/92] Fix capitalize to use more modern ES6 approach --- snippets/capitalize-first-letter.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/snippets/capitalize-first-letter.md b/snippets/capitalize-first-letter.md index 61f73b6a7..edbb04b02 100644 --- a/snippets/capitalize-first-letter.md +++ b/snippets/capitalize-first-letter.md @@ -1,10 +1,11 @@ ### Capitalize first letter -Use `slice(0,1)` and `toUpperCase()` to capitalize first letter, `slice(1)` to get the rest of the string. +Use destructuring and `toUpperCase()` to capitalize first letter, `...rest` to get array of characters after first letter and then `Array.join('')` to make it a string again. Omit the `lowerRest` parameter to keep the rest of the string intact, or set it to `true` to convert to lower case. ```js -const capitalize = (str, lowerRest = false) => - str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); +const capitalize = ([first,...rest], lowerRest = false) => + first.toUpperCase() + (lowerRest ? rest.join('').toLowerCase() : rest.join('')); +// capitalize('myName') -> 'MyName' // capitalize('myName', true) -> 'Myname' ``` From 25984a700e36340d2a6912c6701f7b9cc297a3d6 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Fri, 15 Dec 2017 13:33:46 +0200 Subject: [PATCH 91/92] Update shallow clone, tag, build --- README.md | 20 ++++++++++++++++++-- snippets/shallow-clone-object.md | 4 ++-- tag_database | 1 + 3 files changed, 21 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 416266397..ace0e4e80 100644 --- a/README.md +++ b/README.md @@ -83,6 +83,9 @@ ### Media * [Speech synthesis (experimental)](#speech-synthesis-experimental) +### Node +* [Write json to file](#write-json-to-file) + ### Object * [Object from key value pairs](#object-from-key-value-pairs) * [Object to key value pairs](#object-to-key-value-pairs) @@ -943,6 +946,19 @@ const speak = message => { // speak('Hello, World') -> plays the message ``` +[⬆ back to top](#table-of-contents) +## Node + +### Write a JSON to a file + +Use `fs.writeFile()`, template literals and `JSON.stringify()` to write a `json` object to a `.json` file. + +```js +const fs = require('fs'); +const jsonToFile = (obj, filename) => fs.writeFile(`${filename}.json`, JSON.stringify(obj, null, 2)) +// jsonToFile({test: "is passed"}, 'testJsonFile') -> writes the object to 'testJsonFile.json' +``` + [⬆ back to top](#table-of-contents) ## Object @@ -970,10 +986,10 @@ const objectToPairs = obj => Object.keys(obj).map(k => [k, obj[k]]); ### Shallow clone object -Use the object `...spread` operator to spread the properties of the target object into the clone. +Use `Object.assign()` and an empty object (`{}`) to create a shallo clone of the original. ```js -const shallowClone = obj => ({ ...obj }); +const shallowClone = obj => Object.assign({}, obj); /* const a = { x: true, y: 1 }; const b = shallowClone(a); diff --git a/snippets/shallow-clone-object.md b/snippets/shallow-clone-object.md index c6873c0d8..f3536999f 100644 --- a/snippets/shallow-clone-object.md +++ b/snippets/shallow-clone-object.md @@ -1,9 +1,9 @@ ### Shallow clone object -Use the object `...spread` operator to spread the properties of the target object into the clone. +Use `Object.assign()` and an empty object (`{}`) to create a shallo clone of the original. ```js -const shallowClone = obj => ({ ...obj }); +const shallowClone = obj => Object.assign({}, obj); /* const a = { x: true, y: 1 }; const b = shallowClone(a); diff --git a/tag_database b/tag_database index 67bdedd3c..1a454936f 100644 --- a/tag_database +++ b/tag_database @@ -90,3 +90,4 @@ UUID-generator:utility validate-email:utility validate-number:utility value-or-default:utility +write-json-to-file:node From 5d11c699d56ca9615d927082a3a814fd30a7abc3 Mon Sep 17 00:00:00 2001 From: Angelos Chalaris Date: Fri, 15 Dec 2017 13:42:31 +0200 Subject: [PATCH 92/92] Build --- README.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index ace0e4e80..4e1b89453 100644 --- a/README.md +++ b/README.md @@ -1031,12 +1031,13 @@ const capitalizeEveryWord = str => str.replace(/\b[a-z]/g, char => char.toUpperC ### Capitalize first letter -Use `slice(0,1)` and `toUpperCase()` to capitalize first letter, `slice(1)` to get the rest of the string. +Use destructuring and `toUpperCase()` to capitalize first letter, `...rest` to get array of characters after first letter and then `Array.join('')` to make it a string again. Omit the `lowerRest` parameter to keep the rest of the string intact, or set it to `true` to convert to lower case. ```js -const capitalize = (str, lowerRest = false) => - str.slice(0, 1).toUpperCase() + (lowerRest ? str.slice(1).toLowerCase() : str.slice(1)); +const capitalize = ([first,...rest], lowerRest = false) => + first.toUpperCase() + (lowerRest ? rest.join('').toLowerCase() : rest.join('')); +// capitalize('myName') -> 'MyName' // capitalize('myName', true) -> 'Myname' ```