\n\n\nhttps://www.crockford.com/pp/functions.js\n function identity(x) {\n return x;\n }\n console.log(\"identity\", 3, identity(3));
\nslide10. The Rules If you have a question, you must ask it.\nI won’t debug your stuff.\nIf you need more time, let me know.
\nslide11. Quiz
\nslide12. What is x? function funky(o) {\n o = null;\n}\nlet x = [];\nfunky(x);\nconsole.log(x); A.null\nB.[]\nC.undefined\nD.throw
\nslide13. What is x? function funky(o) {\n o = null;\n}\nlet x = [];\nfunky(x);\nconsole.log(x); A.null\nB.[]\nC.undefined\nD.throw
\nslide14. function funky(o) {\n o = null;\n}\nlet x = [];\nfunky(x);\nconsole.log(x); global [ ]
\nslide15. function funky(o) {\n o = null;\n}\nlet x = [];\nfunky(x);\nconsole.log(x); global [ ] funky
\nslide16. function funky(o) {\n o = null;\n}\nlet x = [];\nfunky(x);\nconsole.log(x); global [ ] funky
\nslide17. What is x? function swap(a, b) {\n let temp = a;\n a = b;\n b = temp;\n}\nlet x = 1;\nlet y = 2;\nswap(x, y);\nconsole.log(x); A.1\nB.2\nC.undefined\nD.throw
\nslide18. What is x? function swap(a, b) {\n let temp = a;\n a = b;\n b = temp;\n}\nlet x = 1;\nlet y = 2;\nswap(x, y);\nconsole.log(x); A.1\nB.2\nC.undefined\nD.throw
\nslide19. function swap(a, b) {\n let temp = a;\n a = b;\n b = temp;\n}\nlet x = 1;\nlet y = 2;\nswap(x, y);\nconsole.log(x); global 1 2
\nslide20. function swap(a, b) {\n let temp = a;\n a = b;\n b = temp;\n}\nlet x = 1;\nlet y = 2;\nswap(x, y);\nconsole.log(x); global 1 2 swap
\nslide21. function swap(a, b) {\n let temp = a;\n a = b;\n b = temp;\n}\nlet x = 1;\nlet y = 2;\nswap(x, y);\nconsole.log(x); global 1 2 swap
\nslide22. Write three binary functions, add , sub, and mul, that take two numbers and return their sum, difference, and product. add(3, 4) // 7\nsub(3, 4) // -1\nmul(3, 4) // 12
\nslide23. function add(first, second) {\n return first + second;\n}\n\nfunction sub(first, second) {\n return first - second;\n}\n\nfunction mul(first, second) {\n return first * second;\n}
\nslide24. Write a function identityf that takes an argument and returns a function that returns that argument. const unity = identityf(1);\nunity() // 1
\nslide25. function identityf(x) {\n return function () {\n return x;\n };\n}
\nslide26. Write a function addf that \u000badds from two invocations. addf(3)(4) // 7
\nslide27. function addf(first) {\n return function (second) {\n return first + second;\n };\n}
\nslide28. Write a function curry that takes a binary function and an argument, and returns a function that can take a second argument. let add3 = curry(add, 3);\nadd3(4) // 7\n\ncurry(mul, 5)(6) // 30
\nslide29. function curry(binary, first) {\n return function (second) {\n return binary(first, second);\n };\n}
\nslide30. function curry(binary, first) {\n return function (second) {\n return binary(first, second);\n };\n}\n\nfunction curry(func, first) {\n return liftf(func)(first);\n} currying\n\nschönfinkelisation
\nslide31. function curry(func) {\n const slice = Array.prototype.slice;\n const args = slice.call(arguments, 1);\n return function () {\n return func.apply(\n null, \n args.concat(slice.call(arguments, 0))\n );\n };\n}\n\nfunction curry(func, ...first) {\n return function (...second) {\n return func(...first, ...second);\n };\n}
\nslide32. function curry(func) {\n const slice = Array.prototype.slice;\n const args = slice.call(arguments, 1);\n return function () {\n return func.apply(\n null, \n args.concat(slice.call(arguments, 0))\n );\n };\n}\n\nfunction curry(func, ...first) {\n return function (...second) {\n return func(...first, ...second);\n };\n}
\nslide33. Write a function curryr that takes a binary function and a second argument, and returns a function that can take a" }

Fun With Functions Block Scope { let a; { let

Published  . 0 views
↓ Download
Fun With Functions Block Scope { let a; { let
1 / 1
Fun With Functions Block Scope { let a; { let - slide 1 of 130 Fun With Functions Block Scope { let a; { let - slide 2 of 130 Fun With Functions Block Scope { let a; { let - slide 3 of 130 Fun With Functions Block Scope { let a; { let - slide 4 of 130 Fun With Functions Block Scope { let a; { let - slide 5 of 130 Fun With Functions Block Scope { let a; { let - slide 6 of 130 Fun With Functions Block Scope { let a; { let - slide 7 of 130 Fun With Functions Block Scope { let a; { let - slide 8 of 130 Fun With Functions Block Scope { let a; { let - slide 9 of 130 Fun With Functions Block Scope { let a; { let - slide 10 of 130 Fun With Functions Block Scope { let a; { let - slide 11 of 130 Fun With Functions Block Scope { let a; { let - slide 12 of 130 Fun With Functions Block Scope { let a; { let - slide 13 of 130 Fun With Functions Block Scope { let a; { let - slide 14 of 130 Fun With Functions Block Scope { let a; { let - slide 15 of 130 Fun With Functions Block Scope { let a; { let - slide 16 of 130 Fun With Functions Block Scope { let a; { let - slide 17 of 130 Fun With Functions Block Scope { let a; { let - slide 18 of 130 Fun With Functions Block Scope { let a; { let - slide 19 of 130 Fun With Functions Block Scope { let a; { let - slide 20 of 130 Fun With Functions Block Scope { let a; { let - slide 21 of 130 Fun With Functions Block Scope { let a; { let - slide 22 of 130 Fun With Functions Block Scope { let a; { let - slide 23 of 130 Fun With Functions Block Scope { let a; { let - slide 24 of 130 Fun With Functions Block Scope { let a; { let - slide 25 of 130 Fun With Functions Block Scope { let a; { let - slide 26 of 130 Fun With Functions Block Scope { let a; { let - slide 27 of 130 Fun With Functions Block Scope { let a; { let - slide 28 of 130 Fun With Functions Block Scope { let a; { let - slide 29 of 130 Fun With Functions Block Scope { let a; { let - slide 30 of 130 Fun With Functions Block Scope { let a; { let - slide 31 of 130 Fun With Functions Block Scope { let a; { let - slide 32 of 130 Fun With Functions Block Scope { let a; { let - slide 33 of 130 Fun With Functions Block Scope { let a; { let - slide 34 of 130 Fun With Functions Block Scope { let a; { let - slide 35 of 130 Fun With Functions Block Scope { let a; { let - slide 36 of 130 Fun With Functions Block Scope { let a; { let - slide 37 of 130 Fun With Functions Block Scope { let a; { let - slide 38 of 130 Fun With Functions Block Scope { let a; { let - slide 39 of 130 Fun With Functions Block Scope { let a; { let - slide 40 of 130 Fun With Functions Block Scope { let a; { let - slide 41 of 130 Fun With Functions Block Scope { let a; { let - slide 42 of 130 Fun With Functions Block Scope { let a; { let - slide 43 of 130 Fun With Functions Block Scope { let a; { let - slide 44 of 130 Fun With Functions Block Scope { let a; { let - slide 45 of 130 Fun With Functions Block Scope { let a; { let - slide 46 of 130 Fun With Functions Block Scope { let a; { let - slide 47 of 130 Fun With Functions Block Scope { let a; { let - slide 48 of 130 Fun With Functions Block Scope { let a; { let - slide 49 of 130 Fun With Functions Block Scope { let a; { let - slide 50 of 130 Fun With Functions Block Scope { let a; { let - slide 51 of 130 Fun With Functions Block Scope { let a; { let - slide 52 of 130 Fun With Functions Block Scope { let a; { let - slide 53 of 130 Fun With Functions Block Scope { let a; { let - slide 54 of 130 Fun With Functions Block Scope { let a; { let - slide 55 of 130 Fun With Functions Block Scope { let a; { let - slide 56 of 130 Fun With Functions Block Scope { let a; { let - slide 57 of 130 Fun With Functions Block Scope { let a; { let - slide 58 of 130 Fun With Functions Block Scope { let a; { let - slide 59 of 130 Fun With Functions Block Scope { let a; { let - slide 60 of 130 Fun With Functions Block Scope { let a; { let - slide 61 of 130 Fun With Functions Block Scope { let a; { let - slide 62 of 130 Fun With Functions Block Scope { let a; { let - slide 63 of 130 Fun With Functions Block Scope { let a; { let - slide 64 of 130 Fun With Functions Block Scope { let a; { let - slide 65 of 130 Fun With Functions Block Scope { let a; { let - slide 66 of 130 Fun With Functions Block Scope { let a; { let - slide 67 of 130 Fun With Functions Block Scope { let a; { let - slide 68 of 130 Fun With Functions Block Scope { let a; { let - slide 69 of 130 Fun With Functions Block Scope { let a; { let - slide 70 of 130 Fun With Functions Block Scope { let a; { let - slide 71 of 130 Fun With Functions Block Scope { let a; { let - slide 72 of 130 Fun With Functions Block Scope { let a; { let - slide 73 of 130 Fun With Functions Block Scope { let a; { let - slide 74 of 130 Fun With Functions Block Scope { let a; { let - slide 75 of 130 Fun With Functions Block Scope { let a; { let - slide 76 of 130 Fun With Functions Block Scope { let a; { let - slide 77 of 130 Fun With Functions Block Scope { let a; { let - slide 78 of 130 Fun With Functions Block Scope { let a; { let - slide 79 of 130 Fun With Functions Block Scope { let a; { let - slide 80 of 130 Fun With Functions Block Scope { let a; { let - slide 81 of 130 Fun With Functions Block Scope { let a; { let - slide 82 of 130 Fun With Functions Block Scope { let a; { let - slide 83 of 130 Fun With Functions Block Scope { let a; { let - slide 84 of 130 Fun With Functions Block Scope { let a; { let - slide 85 of 130 Fun With Functions Block Scope { let a; { let - slide 86 of 130 Fun With Functions Block Scope { let a; { let - slide 87 of 130 Fun With Functions Block Scope { let a; { let - slide 88 of 130 Fun With Functions Block Scope { let a; { let - slide 89 of 130 Fun With Functions Block Scope { let a; { let - slide 90 of 130 Fun With Functions Block Scope { let a; { let - slide 91 of 130 Fun With Functions Block Scope { let a; { let - slide 92 of 130 Fun With Functions Block Scope { let a; { let - slide 93 of 130 Fun With Functions Block Scope { let a; { let - slide 94 of 130 Fun With Functions Block Scope { let a; { let - slide 95 of 130 Fun With Functions Block Scope { let a; { let - slide 96 of 130 Fun With Functions Block Scope { let a; { let - slide 97 of 130 Fun With Functions Block Scope { let a; { let - slide 98 of 130 Fun With Functions Block Scope { let a; { let - slide 99 of 130 Fun With Functions Block Scope { let a; { let - slide 100 of 130 Fun With Functions Block Scope { let a; { let - slide 101 of 130 Fun With Functions Block Scope { let a; { let - slide 102 of 130 Fun With Functions Block Scope { let a; { let - slide 103 of 130 Fun With Functions Block Scope { let a; { let - slide 104 of 130 Fun With Functions Block Scope { let a; { let - slide 105 of 130 Fun With Functions Block Scope { let a; { let - slide 106 of 130 Fun With Functions Block Scope { let a; { let - slide 107 of 130 Fun With Functions Block Scope { let a; { let - slide 108 of 130 Fun With Functions Block Scope { let a; { let - slide 109 of 130 Fun With Functions Block Scope { let a; { let - slide 110 of 130 Fun With Functions Block Scope { let a; { let - slide 111 of 130 Fun With Functions Block Scope { let a; { let - slide 112 of 130 Fun With Functions Block Scope { let a; { let - slide 113 of 130 Fun With Functions Block Scope { let a; { let - slide 114 of 130 Fun With Functions Block Scope { let a; { let - slide 115 of 130 Fun With Functions Block Scope { let a; { let - slide 116 of 130 Fun With Functions Block Scope { let a; { let - slide 117 of 130 Fun With Functions Block Scope { let a; { let - slide 118 of 130 Fun With Functions Block Scope { let a; { let - slide 119 of 130 Fun With Functions Block Scope { let a; { let - slide 120 of 130 Fun With Functions Block Scope { let a; { let - slide 121 of 130 Fun With Functions Block Scope { let a; { let - slide 122 of 130 Fun With Functions Block Scope { let a; { let - slide 123 of 130 Fun With Functions Block Scope { let a; { let - slide 124 of 130 Fun With Functions Block Scope { let a; { let - slide 125 of 130 Fun With Functions Block Scope { let a; { let - slide 126 of 130 Fun With Functions Block Scope { let a; { let - slide 127 of 130 Fun With Functions Block Scope { let a; { let - slide 128 of 130 Fun With Functions Block Scope { let a; { let - slide 129 of 130 Fun With Functions Block Scope { let a; { let - slide 130 of 130
Description: Fun With Functions Block Scope let a; let b; a b a Function Scope function green() let a; function yellow() let b; a b a Function Scope function green() let a; function yellow() let b; a

Related Topics

Download Presentation

"Fun With Functions Block Scope { let a; { let" is the property of its rightful owner. Permission is granted to download and print the materials on this website for personal, non-commercial use only, and to display it on your personal computer provided you do not modify the materials and that you retain all copyright notices contained in the materials. By downloading content from our website, you accept the terms of this agreement.

Presentation Transcript

slide1. Fun With Functions<br>
slide2. Block Scope {
let a;
{
let b;
… a …
… b …
}
… a …
}<br>
slide3. Function Scope function green() {
let a;
function yellow() {
let b;
… a …
… b …
}
… a …
}<br>
slide4. Function Scope function green() {
let a;
function yellow() {
let b;
… a …
… b …
}
… a …
} a<br>
slide5. Closure function green() {
let a;
function yellow() {
let b;
… a …
… b …
}
… a …
} a b<br>
slide6. Inner survives the outer function green() {
let a;
return function yellow() {
let b;
… a …
… b …
};
… a …
}<br>
slide7. Write an identity function that takes an argument and returns that argument. identity(3) // 3<br>
slide8. function identity(x) {
return x;
}

const identity = function identity(x) {
return x;
};<br>
slide9. https://www.crockford.com/pp/fun.html
<!DOCTYPE html><html>
<head><meta charset="UTF-8"></head>
<body><script src="functions.js">
</script></body></html>

https://www.crockford.com/pp/functions.js
function identity(x) {
return x;
}
console.log("identity", 3, identity(3));<br>
slide10. The Rules If you have a question, you must ask it.
I won’t debug your stuff.
If you need more time, let me know.<br>
slide11. Quiz<br>
slide12. What is x? function funky(o) {
o = null;
}
let x = [];
funky(x);
console.log(x); A.null
B.[]
C.undefined
D.throw<br>
slide13. What is x? function funky(o) {
o = null;
}
let x = [];
funky(x);
console.log(x); A.null
B.[]
C.undefined
D.throw<br>
slide14. function funky(o) {
o = null;
}
let x = [];
funky(x);
console.log(x); global [ ]<br>
slide15. function funky(o) {
o = null;
}
let x = [];
funky(x);
console.log(x); global [ ] funky<br>
slide16. function funky(o) {
o = null;
}
let x = [];
funky(x);
console.log(x); global [ ] funky<br>
slide17. What is x? function swap(a, b) {
let temp = a;
a = b;
b = temp;
}
let x = 1;
let y = 2;
swap(x, y);
console.log(x); A.1
B.2
C.undefined
D.throw<br>
slide18. What is x? function swap(a, b) {
let temp = a;
a = b;
b = temp;
}
let x = 1;
let y = 2;
swap(x, y);
console.log(x); A.1
B.2
C.undefined
D.throw<br>
slide19. function swap(a, b) {
let temp = a;
a = b;
b = temp;
}
let x = 1;
let y = 2;
swap(x, y);
console.log(x); global 1 2<br>
slide20. function swap(a, b) {
let temp = a;
a = b;
b = temp;
}
let x = 1;
let y = 2;
swap(x, y);
console.log(x); global 1 2 swap<br>
slide21. function swap(a, b) {
let temp = a;
a = b;
b = temp;
}
let x = 1;
let y = 2;
swap(x, y);
console.log(x); global 1 2 swap<br>
slide22. Write three binary functions, add , sub, and mul, that take two numbers and return their sum, difference, and product. add(3, 4) // 7
sub(3, 4) // -1
mul(3, 4) // 12<br>
slide23. function add(first, second) {
return first + second;
}

function sub(first, second) {
return first - second;
}

function mul(first, second) {
return first * second;
}<br>
slide24. Write a function identityf that takes an argument and returns a function that returns that argument. const unity = identityf(1);
unity() // 1<br>
slide25. function identityf(x) {
return function () {
return x;
};
}<br>
slide26. Write a function addf that adds from two invocations. addf(3)(4) // 7<br>
slide27. function addf(first) {
return function (second) {
return first + second;
};
}<br>
slide28. Write a function curry that takes a binary function and an argument, and returns a function that can take a second argument. let add3 = curry(add, 3);
add3(4) // 7

curry(mul, 5)(6) // 30<br>
slide29. function curry(binary, first) {
return function (second) {
return binary(first, second);
};
}<br>
slide30. function curry(binary, first) {
return function (second) {
return binary(first, second);
};
}

function curry(func, first) {
return liftf(func)(first);
} currying

schönfinkelisation<br>
slide31. function curry(func) {
const slice = Array.prototype.slice;
const args = slice.call(arguments, 1);
return function () {
return func.apply(
null,
args.concat(slice.call(arguments, 0))
);
};
}

function curry(func, ...first) {
return function (...second) {
return func(...first, ...second);
};
}<br>
slide32. function curry(func) {
const slice = Array.prototype.slice;
const args = slice.call(arguments, 1);
return function () {
return func.apply(
null,
args.concat(slice.call(arguments, 0))
);
};
}

function curry(func, ...first) {
return function (...second) {
return func(...first, ...second);
};
}<br>
slide33. Write a function curryr that takes a binary function and a second argument, and returns a function that can take a first argument. let dec = curryr(sub, 1);
dec(7) // 6<br>
slide34. function curryr(binary, second) {
return function (first) {
return binary(first, second);
};
}<br>
slide35. Write a function liftf that takes a binary function, and makes it callable with two invocations. let addf = liftf(add);
addf(3)(4) // 7
liftf(mul)(5)(6) // 30<br>
slide36. function liftf(binary) {
return function (first) {
return function (second) {
return binary(first, second);
};
};
}

function liftf(binary) {
return function (first) {
return curry(binary, first);
};
}<br>
slide37. function liftf(binary) {
return function (first) {
return function (second) {
return binary(first, second);
};
};
}

function liftf(binary) {
return function (first) {
return curry(binary, first);
};
}<br>
slide38. Without writing any new functions, show four ways to create the inc function. let inc = _ _ _ ;
inc(5) // 6
inc(inc(5)) // 7<br>
slide39. 1. inc = addf(1);

2. inc = curry(add, 1);

3. inc = curryr(add, 1);

4. inc = liftf(add)(1);<br>
slide40. Write a function twice that takes a binary function and returns a unary function that passes its argument to the binary function twice. add(11, 11) // 22
let double = twice(add);
double(11) // 22
let square = twice(mul);
square(11) // 121<br>
slide41. function twice(binary) {
return function (a) {
return binary(a, a);
};
}<br>
slide42. Write reverse, a function that reverses the arguments of a binary function. let bus = reverse(sub);
bus(3, 2) // -1<br>
slide43. function reverse(binary) {
return function (first, second) {
return binary(second, first);
};
}

function reverse(any) {
return function (...args) {
return any(...args.reverse());
};
}<br>
slide44. Write a function composeu that takes two unary functions and returns a unary function that calls them both. composeu(double, square)(5) // 100<br>
slide45. function composeu(f, g) {
return function (a) {
return g(f(a));
};
}<br>
slide46. function composeu(...functions) {
return function (value) {
return functions.forEach(
function (func) {
value = func(value);
}
);
return value;
};
}<br>
slide47. Write a function composeb that takes two binary functions and returns a function that calls them both. composeb(add, mul)(2, 3, 7) // 35<br>
slide48. function composeb(f, g) {
return function (a, b, c) {
return g(f(a, b), c);
};
}<br>
slide49. Write a limit function that allows a function to be called a limited number of times. let add_ltd = limit(add, 1);
add_ltd(3, 4) // 7
add_ltd(3, 5) // undefined<br>
slide50. function limit(func, count) {
return function (...args) {
if (count >= 1) {
count -= 1;
return func(...args);
}
return undefined;
};
}<br>
slide51. Generators Generator factory:
A function that returns a generator function.

Generator function:
A function that returns a series of values.<br>
slide52. Write a from factory that produces a generator that will produce a series of values. let index = from(0);
index() // 0
index() // 1
index() // 2<br>
slide53. function from(start) {
return function from_generator() {
let next = start;
start += 1;
return next;
};
}<br>
slide54. Write a to factory that takes a generator and an end value, and returns a generator that will produce numbers up to but not including that limit. let index = to(from(2), 4);
index() // 2
index() // 3
index() // undefined<br>
slide55. function to(gen, end) {
return function to_generator() {
let value = gen();
if (value < end) {
return value;
}
};
}<br>
slide56. Write a fromTo factory that produces a generator that will produce values in a range. let index = fromTo(0, 3);
index() // 0
index() // 1
index() // 2
index() // undefined<br>
slide57. function fromTo(start, end) {
return to(from(start), end);
}<br>
slide58. Write an element factory that takes an array and a generator and returns a generator that will produce elements from the array. let ele = element(
["a", "b", "c", "d"],
fromTo(1, 3)
);
ele() // "b"
ele() // "c"
ele() // undefined<br>
slide59. function element(array, gen) {
return function element_generator() {
let value = gen();
if (value !== undefined) {
return array[value];
}
};
}<br>
slide60. Modify the element factory so that the generator argument is optional. If a generator is not provided, then each of the elements of the array will be produced. let ele = element(["a", "b", "c", "d"]);
ele() // "a"
ele() // "b"
ele() // "c"
ele() // "d"
ele() // undefined<br>
slide61. function element(
array,
gen = fromTo(0, array.length)
) {
return function element_generator() {
let value = gen();
if (value !== undefined) {
return array[value];
}
};
}<br>
slide62. Write a collect factory that takes a generator and an array and produces a generator that will collect the results in the array. let array = [];
let col = collect(fromTo(0, 2), array);
col() // 0
col() // 1
col() // undefined
array // [0, 1]<br>
slide63. function collect(gen, array) {
return function collect_generator() {
let value = gen();
if (value !== undefined) {
array.push(value);
}
return value;
};
}<br>
slide64. Write a filter factory that takes a generator and a predicate and produces a generator that produces only the values approved by the predicate. let fil = filter(
fromTo(0, 5),
function divisible_by_3(value) {
return (value % 3) === 0;
}
);
fil() // 0
fil() // 3
fil() // undefined<br>
slide65. function filter(gen, predicate) {
return function filter_generator() {
let value;
do {
value = gen();
} while (
value !== undefined
&& !predicate(value)
);
return value;
};
}<br>
slide66. function filter(gen, predicate) {
return function filter_generator() {
let value = gen();
if (
value === undefined
|| predicate(value)
) {
return value;
}
return filter_generator();
};
}<br>
slide67. Write a concat factory that takes two generators and produces a generator that combines the sequences. let con = concat(fromTo(0, 3), fromTo(0,2));
con() // 0
con() // 1
con() // 2
con() // 0
con() // 1
con() // undefined<br>
slide68. function concat(gen1, gen2) {
let gen = gen1;
return function concat_generator() {
let value = gen();
if (value !== undefined) {
return value;
}
gen = gen2;
return gen();
};
}<br>
slide69. function concat(...gens) {
let next = element(gens);
let gen = next();
return function concat_generator() {
if (gen !== undefined) {
let value = gen();
if (value !== undefined) {
return value;
}
gen = next();
return concat_generator();
}
};
}<br>
slide70. Write a repeat function that takes a generator and calls it until it returns undefined. let array = [];
repeat(collect(fromTo(0, 4), array));
log(array); // 0, 1, 2, 3<br>
slide71. function repeat(gen) {
let value;
do {
value = gen();
} while (value !== undefined);
}

function repeat(func) {
if (func() !== undefined) {
return repeat(func);
}
}<br>
slide72. function repeat(gen) {
let value;
do {
value = gen();
} while (value !== undefined);
}

function repeat(gen) {
if (gen() !== undefined) {
return repeat(gen);
}
}<br>
slide73. Write a map function that takes an array and a unary function, and returns an array containing the result of passing each element to the unary function. Use the repeat function. map([2, 1, 0], inc) // [3, 2, 1]<br>
slide74. function map(array, unary) {
const ele = element(array);
const result = [];
repeat(collect(
function () {
let value = ele();
if (value !== undefined) {
return unary(value);
}
},
result
));
return result;
}<br>
slide75. Write a reduce function that takes an array and a binary function, and returns a single value. Use the repeat function. reduce([], add) // undefined
reduce([2], add) // 2
reduce([2, 1, 0], add) // 3<br>
slide76. function reduce(array, binary) {
const ele = element(array);
let result;
repeat(function () {
let value = ele();
if (value !== undefined) {
result = (
result === undefined
? value
: binary(result, value)
);
}
return value;
});
return result;
}<br>
slide77. Make a gensymf factory that makes a unique symbol generator. let geng = gensymf("G");
let genh = gensymf("H");
geng() // "G1"
genh() // "H1"
geng() // "G2"
genh() // "H2"<br>
slide78. function gensymf(prefix) {
let gen = from(1);
return function gensym_generator() {
return prefix + gen();
};
}<br>
slide79. Write a gensymff factory factory that takes a factory function and a seed and returns a gensymf. let gensymf = gensymff(from, 1);
let geng = gensymf("G");
let genh = gensymf("H");
geng() // "G1"
genh() // "H1"
geng() // "G2"
genh() // "H2"<br>
slide80. function gensymff(factory, seed) {
return function (prefix) {
let gen = factory(seed);
return function generator() {
return prefix + gen();
};
};
} geng() // "G1"
genh() // "H1"
geng() // "G2"
genh() // "H2"<br>
slide81. function gensymff(factory, seed) {
let gen = factory(seed);
return function (prefix) {
return function generator() {
return prefix + gen();
};
};
} geng() // "G1"
genh() // "H2"
geng() // "G3"
genh() // "H4"<br>
slide82. Make a fibonaccif factory that returns a generator that will produce the fibonacci sequence. let fib = fibonaccif(0, 1);
fib() // 0
fib() // 1
fib() // 1
fib() // 2
fib() // 3
fib() // 5<br>
slide83. function fibonaccif(a, b) {
let i = 0;
return function () {
let next;
if (i === 0) {
i = 1;
return a;
}
if (i == 1) {
i = 2;
return b;
}
next = a + b;
a = b;
b = next;
return next;
};
}<br>
slide84. function fibonaccif(a, b) {
return function () {
let next = a;
a = b;
b += next;
return next;
};
}<br>
slide85. const single = composeu(identityf, curryr(limit, 1));

function fibonaccif(a, b) {
return concat(
concat(
single(a),
single(b)
),
function fibonacci() {
let next = a + b;
a = b;
b = next;
return next;
}
);
}<br>
slide86. function fibonaccif(a, b) {
return concat(
element([a, b]),
function fibonacci() {
let next = a + b;
a = b;
b = next;
return next;
}
);
}<br>
slide87. Write a counter constructor that returns an object containing two functions that implement an up/down counter, hiding the counter. let object = counter(10);
let up = object.up;
let down = object.down;
up() // 11
down() // 10
down() // 9
up() // 10<br>
slide88. function counter(value) {
return {
up: function () {
value += 1;
return value;
},
down: function () {
value -= 1;
return value;
}
};
}<br>
slide89. Make a revocable constructor that takes a function, and returns an object containing an invoke method that can invoke the function, and a revoke method that disables the invoke method. let rev = revocable(add);
let add_rev = rev.invoke;
add_rev(3, 4); // 7
rev.revoke();
add_rev(5, 7); // undefined<br>
slide90. function revocable(any) {
return {
invoke: function (...args) {
if (any !== undefined) {
return any(...args);
}
},
revoke: function () {
any = undefined;
}
};
}<br>
slide91. Write a function num that takes a value and an optional source string and returns them in an object. JSON.stringify(num(1))
// {"value": 1, "source": "1"}
JSON.stringify(num(Math.PI, "pi"))
// {"value": 3.14159…, "source": "pi"}<br>
slide92. https://www.crockford.com/pp/num.js

function num(value, source) {
return {
value,
source: (
typeof source === "string"
? source
: String(value)
)
};
}<br>
slide93. Write a function addnum that adds two num objects and returns an num object. JSON.stringify(addnum(num(3), num(4)))
// {"value": 7, "source": "(3+4)"}
JSON.stringify(addnum(num(1), num(Math.PI, "pi")))
// {"value": 4.14159…, "source": "(1+pi)"}<br>
slide94. function addnum(a, b) {
return num(
a.value + b.value,
"(" + a.source + "+" + b.source + ")"
);
}<br>
slide95. Write a function lifnutm that takes a binary function and a string and returns a function that acts on num objects. let addm = liftnum(add, "+");
JSON.stringify(addm(num(3), num(4)))
// {"value": 7, "source": "(3+4)"}
JSON.stringify(liftnum(mul, "*")(num(3), num(4)))
// {"value": 12, "source": "(3*4)"}<br>
slide96. function liftnum(binary, op) {
return function (a, b) {
return num(
binary(a.value, b.value),
"(" + a.source + op + b.source + ")"
);
};
}<br>
slide97. Modify function liftnum so that the functions it produces can accept arguments that are either numbers or m objects. let addnum = liftnum(add, "+");
JSON.stringify(addnum(3, 4))
// {"value": 7, "source": "(3+4)"}<br>
slide98. function liftnum(binary, op) {
return function (a, b) {
if (typeof a === "number") {
a = num(a);
}
if (typeof b === "number") {
b = num(b);
}
return num(
binary(a.value, b.value),
"(" + a.source + op +
b.source + ")"
);
};
}<br>
slide99. Write a function exp that evaluates simple array expressions. let sae = [mul, 5, 11];
exp(sae) // 55
exp(42) // 42<br>
slide100. function exp(value) {
return (
Array.isArray(value)
? value[0](value[1], value[2])
: value
);
}<br>
slide101. Modify exp to evaluate nested array expressions. let nae = [
Math.sqrt,
[
add,
[square, 3],
[square, 4]
]
];
exp(nae) // 5<br>
slide102. function exp(value) {
return (
Array.isArray(value)
? value[0](
exp(value[1]),
exp(value[2])
)
: value
);
}

// recursion: a function calls itself<br>
slide103. Write a function addg that adds from many invocations, until it sees an empty invocation. addg() // undefined
addg(2)() // 2
addg(2)(7)() // 9
addg(3)(0)(4)() // 7
addg(1)(2)(4)(8)() // 15<br>
slide104. function addg(first) {
function more(next) {
if (next === undefined) {
return first;
}
first += next;
return more;
}
if (first !== undefined) {
return more;
}
}

// retursion: a function returns itself<br>
slide105. Write a function liftg that will take a binary function and apply it to many invocations. liftg(mul)() // undefined
liftg(mul)(3)() // 3
liftg(mul)(3)(0)(4)() // 0
liftg(mul)(1)(2)(4)(8)() // 64<br>
slide106. function liftg(binary) {
return function (first) {
if (first === undefined) {
return first;
}
return function more(next) {
if (next === undefined) {
return first;
}
first = binary(first, next);
return more;
};
};
}<br>
slide107. Write a function arrayg that will build an array from many invocations. arrayg() // []
arrayg(3)() // [3]
arrayg(3)(4)(5)() // [3, 4, 5]<br>
slide108. function arrayg(first) {
let array = [];
function more(next) {
if (next === undefined) {
return array;
}
array.push(next);
return more;
}
return more(first);
}<br>
slide109. function arrayg(first) {
if (first === undefined) {
return [];
}
return liftg(
function (array, value) {
array.push(value);
return array;
}
)([first]);
}<br>
slide110. Make an objectify factory that takes an array of property names and returns a constructor that takes values and returns an object. let make = objectify("date", "marry", "kill");
JSON.stringify(make("butterfly", "unicorn", "monster"))
// {
// "date": "butterfly",
// "marry": "unicorn",
// "kill" : "monster"
// }<br>
slide111. function objectify(...names) {
return function objectify_constructor(...values) {
const object = Object.create(null);
names.forEach(function (name, name_nr) {
object[name] = values[name_nr];
});
return object;
};
}<br>
slide112. Make a join factory that takes a function and generators that provide arguments to the function. let fo = join(
objectify("number", "fibonacci"),
from(0),
fibonaccif(4, 5)
);
fo() // {"number": 0, "fibonacci": 4}
fo() // {"number": 1, "fibonacci": 5}
fo() // {"number": 2, "fibonacci": 9}<br>
slide113. function join(func, ...gens) {
return function join_generator() {
return func(...gens.map(function (gen) {
return gen();
}));
};
}<br>
slide114. Make a continuize factory that takes a function, and returns a function that takes a callback and an argument. let sqrtc = continuize(Math.sqrt);
sqrtc(console.log, 81);<br>
slide115. function continuize(any) {
return function (continuation, ...args) {
return continuation(any(...args));
};
}<br>
slide116. function constructor(spec) {
let {member} = spec;
const reuse = other_constructor(spec);
const method = function () {
// spec, member, reuse, method
};
return Object.freeze({
method,
goodness: reuse.goodness
});
}<br>
slide117. Make a vector constructor with methods get, store, and append, such that an attacker cannot get access to the private array. myvector = vector();
myvector.append(7);
myvector.store(1, 8);
myvector.get(0) // 7
myvector.get(1) // 8<br>
slide118. function vector() {
const array = [];

return {
get: function get(i) {
return array[i];
},
store: function store(i, v) {
array[i] = v;
},
append: function append(v) {
array.push(v);
}
};
}<br>
slide119. function vector() {
const array = [];

return {
get: function get(i) {
return array[i];
},
store: function store(i, v) {
array[i] = v;
},
append: function append(v) {
array.push(v);
}
}; let stash;
} myvector.store("push", function () {
stash = this;
});
myvector.append(); // stash is array<br>
slide120. function vector() {
const array = [];

return {
get: function (i) {
return array[i];
},
store: function store(i, v) {
array[Number(i)] = v;
},
append: function (v) {
array[array.length] = v;
}
};
}<br>
slide121. Make a function that makes a publish/subscribe object. It will reliably deliver all publications to all subscribers in the right order. my_pubsub = pubsub();
my_pubsub.subscribe(log);
my_pubsub.publish("It works!");
// log("It works!")<br>
slide122. function pubsub() {
const subscribers = [];
return {
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
let i;
const length = subscribers.length;
for (i = 0; i < length; i += 1) {
subscribers[i](publication);
}
}
};
}<br>
slide123. function pubsub() {
const subscribers = [];
return {
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
let i;
const length = subscribers.length;
for (i = 0; i < length; i += 1) {
subscribers[i](publication);
}
}
};
}

my_pubsub.subscribe();<br>
slide124. function pubsub() {
const subscribers = [];
return {
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
let i;
const length = subscribers.length;
for (i = 0; i < length; i += 1) {
try {
subscribers[i](publication);
} catch (ignore) {}
}
}
};
}<br>
slide125. function pubsub() {
const subscribers = [];
return {
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
let i;
const length = subscribers.length;
for (i = 0; i < length; i += 1) {
try {
subscribers[i](publication);
} catch (ignore) {}
}
}
};
} my_pubsub.publish = undefined;<br>
slide126. function pubsub() {
const subscribers = [];
return Object.freeze({
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
let i;
const length = subscribers.length;
for (i = 0; i < length; i += 1) {
try {
subscribers[i](publication);
} catch (ignore) {}
}
}
});
}<br>
slide127. function pubsub() {
const subscribers = [];
return Object.freeze({
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
let i;
const length = subscribers.length;
for (i = 0; i < length; i += 1) {
try {
subscribers[i](publication);
} catch (ignore) {}
}
}
}); my_pubsub.subscribe(function () {
} this.length = 0;
});<br>
slide128. function pubsub() {
const subscribers = [];
return Object.freeze({
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
subscribers.forEach(function (subscriber) {
try {
subscriber(publication);
} catch (ignore) {}
});
}
});
}<br>
slide129. function pubsub() {
const subscribers = [];
return Object.freeze({
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
subscribers.forEach(function (subscriber) {
try {
subscriber(publication);
} catch (ignore) {}
});
} my_pubsub.subscribe(limit(
}); function () {
} my_pubsub.publish("Out of order");
},
1
)); "<br>
slide130. function pubsub() {
const subscribers = [];
return Object.freeze({
subscribe: function (subscriber) {
subscribers.push(subscriber);
},
publish: function (publication) {
subscribers.forEach(function (subscriber) {
setTimeout(function () {
subscriber(publication);
}, 0);
});
}
});
}<br>