Skip to content

Instantly share code, notes, and snippets.

View briancavalier's full-sized avatar

Brian Cavalier briancavalier

  • Pittsburgh
View GitHub Profile
@briancavalier
briancavalier / serialize-function.js
Created February 10, 2015 18:34
Serializing / deserializing JavaScript functions *with free variables*
var a = 123, b = 'hello';
function test(x, y) {
console.log(this);
return a + x + b + y;
}
// Serialize a function *with its captured environment*
var sf = serialize(test, { a: a, b: b });
// Deserialize with captured environment
@briancavalier
briancavalier / simple-promise-retry.js
Created February 24, 2011 18:35
A few general patterns for retries using promises
function keepTrying(otherArgs, promise) {
promise = promise||new Promise();
// try doing the important thing
if(success) {
promise.resolve(result);
} else {
setTimeout(function() {
keepTrying(otherArgs, promise);
@briancavalier
briancavalier / promise-monad-proof.js
Created August 8, 2012 15:57
A proof that Promises/A is a Monad
//-------------------------------------------------------------
//
// Hypothesis:
//
// Promises/A is a Monad
//
// To be a Monad, it must provide at least:
// - A unit (aka return or mreturn) operation that creates a corresponding
// monadic value from a non-monadic value.
// - A bind operation that applies a function to a monadic value
@briancavalier
briancavalier / typescript-strongly-typed-variadic-2.md
Last active October 12, 2023 18:34
A technique for strongly-typed, heterogeneous variadic function types in Typescript

Simpler Variadic Function Types in TypeScript (part 2): Higher-order Variadic Functions

In part 1 we looked at a technique that allows expressing strongly-typed variadic functions in a way that solves problems with the current most common approach. It reduces code size and repetition, and it scales to any arity.

I mentioned that the technique can also be extended to higher-order variadic functions, such as the typical zipWith. Let’s explore how to do that.

ZipWith Example

As we did in part 1, let’s start with an example, a typical zipWith on arrays.

@briancavalier
briancavalier / typescript-strongly-typed-variadic-1.md
Last active October 12, 2023 18:34
A technique for strongly-typed, heterogeneous variadic function types in Typescript

Simpler Variadic Function Types in TypeScript (part 1)

Variadic functions, such as the common zip function on arrays, are convenient and remove the need for lots of specific arity-function variants, e.g., zip2, zip3, zip4, etc. However, they can be difficult and tedious to type correctly in TypeScript when the return type depends on the parameter types, and the parameter types are heterogeneous.

Zip Example

Given a typical zip on arrays:

const a: number[] = [1, 2, 3]
@briancavalier
briancavalier / example.js
Last active November 24, 2021 20:10
Infinite "lists" in es6 using generators and yield
// Requires traceur
import { iterate, take, map, foldl } from './list-out-of-yield';
// Sum of squares of integers 1..100
var values = take(100, iterate(x => x + 1, 1));
var result = foldl((x, y) => x + y, 0, map(x => x * x, values));
console.log(result);
@briancavalier
briancavalier / tiny closure Promise.js
Created February 7, 2011 12:55
A closure version of my mod (https://gist.github.com/814313) to unscriptable's tiny promise (https://gist.github.com/814052/)
function Promise() {
var callbacks = [],
promise = {
resolve: resolve,
reject: reject,
then: then,
safe: {
then: function safeThen(resolve, reject) {
promise.then(resolve, reject);
}
type Tuple<Iterables extends Iterable<any>[]> = {
[K in keyof Iterables]: Iterables[K] extends Iterable<infer A> ? A : never
}
export const product = <Iterables extends Iterable<any>[]>(...t: Iterables): Iterable<Tuple<Iterables>> =>
t.length === 0 ? [] : prod(t, [])
export function* prod<Iterables extends Iterable<any>[]>([h, ...t]: Iterables, r: any[]): Iterable<Tuple<Iterables>> {
if (t.length === 0) for (const a of h) yield [...r, a] as Tuple<Iterables>
else for (const a of h) yield* prod(t, [...r, a]) as Iterable<Tuple<Iterables>>
@briancavalier
briancavalier / 1-echo-console.ts
Created February 7, 2020 13:36
Two ways to use Env
import { co, unsafeRun, resumeLater, resumeNow, use, Resume, op } from '../src'
import { EOL } from 'os'
import { createInterface } from 'readline'
type Print = { print(s: string): Resume<void> }
const print = (s: string) => op<Print>(c => c.print(s))
type Read = { read(): Resume<string> }
const read = op<Read>(c => c.read())
@briancavalier
briancavalier / most-sample-promises.md
Last active November 19, 2019 16:47
Description of most.js sample+promises issue

This is an explanation of the extremely subtle problem in this most.js issue. This solution described isn't necessarily the best, or most rigorous solution. We're investigating other potential solutions, but wanted to record this information in case it's interesting to someone.

Background

One of the fastest ways to schedule a task in ES6 is to use a promise. They tend to use the fastest micro-tick scheduling option the platform provides. So, when a task is scheduled with scheduler.asap it doesn’t use setTimeout 0, it uses a promise to schedule itself, because that’s basically as close to zero-time as you can get in a platform independent way

given this: