add reader
This commit is contained in:
parent
6e2f725e7a
commit
1fec16c29c
5 changed files with 120 additions and 18 deletions
|
@ -1,5 +1,5 @@
|
||||||
import { liftF } from './fn.js'
|
import { liftF } from './fn.js'
|
||||||
import { Algebra, BaseSet, Comonad, Monad } from './index.js'
|
import { Algebra, BaseSet, Monad, Semigroupoid } from './index.js'
|
||||||
|
|
||||||
/** @import { InferredMorphism, Morphism } from './types.js' */
|
/** @import { InferredMorphism, Morphism } from './types.js' */
|
||||||
|
|
||||||
|
@ -8,7 +8,7 @@ import { Algebra, BaseSet, Comonad, Monad } from './index.js'
|
||||||
* @extends BaseSet
|
* @extends BaseSet
|
||||||
* @mixes Monad
|
* @mixes Monad
|
||||||
*/
|
*/
|
||||||
export class Suspend extends Algebra(Monad) {
|
export class Suspend extends Algebra(Semigroupoid, Monad) {
|
||||||
_value
|
_value
|
||||||
#fn
|
#fn
|
||||||
|
|
||||||
|
@ -55,6 +55,14 @@ export class Suspend extends Algebra(Monad) {
|
||||||
return this.map(g)
|
return this.map(g)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @template T
|
||||||
|
* @param {InferredMorphism<T>} other
|
||||||
|
*/
|
||||||
|
compose(other) {
|
||||||
|
return this.chain(() => other)
|
||||||
|
}
|
||||||
|
|
||||||
step() {
|
step() {
|
||||||
return this.#fn(this._value)
|
return this.#fn(this._value)
|
||||||
}
|
}
|
||||||
|
@ -65,7 +73,7 @@ export class Suspend extends Algebra(Monad) {
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @template T */
|
/** @template T */
|
||||||
export class Pure extends Algebra(Monad, Comonad) {
|
export class Pure extends Algebra(Monad) {
|
||||||
_value
|
_value
|
||||||
|
|
||||||
/** @param {T} value */
|
/** @param {T} value */
|
||||||
|
@ -95,7 +103,7 @@ export class Pure extends Algebra(Monad, Comonad) {
|
||||||
* @returns {Pure<U>}
|
* @returns {Pure<U>}
|
||||||
*/
|
*/
|
||||||
map(f) {
|
map(f) {
|
||||||
return this.chain(x => new Pure(f(x)))
|
return this.chain(x => pure(f(x)))
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -107,8 +115,12 @@ export class Pure extends Algebra(Monad, Comonad) {
|
||||||
return this.map(f)
|
return this.map(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
extract() {
|
/**
|
||||||
return this._value
|
* @template T
|
||||||
|
* @param {InferredMorphism<T>} other
|
||||||
|
*/
|
||||||
|
compose(other) {
|
||||||
|
return this.chain(() => pure(other))
|
||||||
}
|
}
|
||||||
|
|
||||||
step() {
|
step() {
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import { concat } from '../iter.js'
|
import { concat } from '../iter.js'
|
||||||
import { liftF } from './fn.js'
|
import { liftF } from './fn.js'
|
||||||
import { Pure, Suspend } from './free.js'
|
import { Pure, Suspend } from './free.js'
|
||||||
import { AlgebraWithBase, Comonad, Foldable } from './index.js'
|
import { AlgebraWithBase, Category, Comonad, Foldable, Monoid } from './index.js'
|
||||||
|
|
||||||
/** @import { InferredMorphism } from './types.js' */
|
/** @import { InferredMorphism } from './types.js' */
|
||||||
|
|
||||||
|
@ -11,7 +11,15 @@ const Nil = Symbol('Nil')
|
||||||
* @template T
|
* @template T
|
||||||
* @extends {Pure<T>}
|
* @extends {Pure<T>}
|
||||||
*/
|
*/
|
||||||
class ListPure extends AlgebraWithBase(Pure)(Foldable) {
|
class ListPure extends AlgebraWithBase(Pure)(Category, Foldable, Monoid) {
|
||||||
|
static empty() {
|
||||||
|
return List.empty()
|
||||||
|
}
|
||||||
|
|
||||||
|
static id() {
|
||||||
|
return List.empty()
|
||||||
|
}
|
||||||
|
|
||||||
head() {
|
head() {
|
||||||
return this._value
|
return this._value
|
||||||
}
|
}
|
||||||
|
@ -35,7 +43,7 @@ class ListPure extends AlgebraWithBase(Pure)(Foldable) {
|
||||||
* @template T
|
* @template T
|
||||||
* @extends {Suspend<T>}
|
* @extends {Suspend<T>}
|
||||||
*/
|
*/
|
||||||
class ListSuspend extends AlgebraWithBase(Suspend)(Foldable, Comonad) {
|
class ListSuspend extends AlgebraWithBase(Suspend)(Foldable, Monoid, Comonad) {
|
||||||
/**
|
/**
|
||||||
* @param {Iterator<T>} iter
|
* @param {Iterator<T>} iter
|
||||||
*/
|
*/
|
||||||
|
@ -79,6 +87,10 @@ class ListSuspend extends AlgebraWithBase(Suspend)(Foldable, Comonad) {
|
||||||
extract() {
|
extract() {
|
||||||
return this.reduce(reduceArray, [])
|
return this.reduce(reduceArray, [])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static empty() {
|
||||||
|
return List.empty()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -120,9 +132,3 @@ const Empty = new ListPure(Nil)
|
||||||
*/
|
*/
|
||||||
const reduceArray = (acc, value) => acc.concat(value)
|
const reduceArray = (acc, value) => acc.concat(value)
|
||||||
|
|
||||||
|
|
||||||
const a = Array.from({ length: 10 }).map((_, i) => i)
|
|
||||||
|
|
||||||
const wawa = List.from(a)
|
|
||||||
console.log(wawa.reduce((acc, value) => acc.concat(value), []))
|
|
||||||
|
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
import { Algebra, Foldable, Functor, Monad } from './index.js'
|
import { Algebra, Foldable, Monad, Monoid } from './index.js'
|
||||||
|
|
||||||
/** @import { Morphism } from './types.js' */
|
/** @import { Morphism } from './types.js' */
|
||||||
|
|
||||||
/** @template T */
|
/** @template T */
|
||||||
export class Some extends Algebra(Monad, Foldable) {
|
export class Some extends Algebra(Monoid, Monad, Foldable) {
|
||||||
/** @type {T} */
|
/** @type {T} */
|
||||||
#value
|
#value
|
||||||
|
|
||||||
|
@ -59,10 +59,14 @@ export class Some extends Algebra(Monad, Foldable) {
|
||||||
reduce(f, init) {
|
reduce(f, init) {
|
||||||
return f(init, this.#value)
|
return f(init, this.#value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
empty() {
|
||||||
|
return Option.empty()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @template T */
|
/** @template T */
|
||||||
class None extends Algebra(Monad, Foldable) {
|
class None extends Algebra(Monoid, Monad, Foldable) {
|
||||||
/**
|
/**
|
||||||
* @template R
|
* @template R
|
||||||
* @param {Morphism<T, R>} _f
|
* @param {Morphism<T, R>} _f
|
||||||
|
@ -99,6 +103,10 @@ class None extends Algebra(Monad, Foldable) {
|
||||||
reduce(_f, init) {
|
reduce(_f, init) {
|
||||||
return init
|
return init
|
||||||
}
|
}
|
||||||
|
|
||||||
|
empty() {
|
||||||
|
return Option.empty()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -113,6 +121,10 @@ export class Option {
|
||||||
static of(value) {
|
static of(value) {
|
||||||
return Some.of(value)
|
return Some.of(value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static empty() {
|
||||||
|
return none
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
71
src/algebra/reader.js
Normal file
71
src/algebra/reader.js
Normal file
|
@ -0,0 +1,71 @@
|
||||||
|
import { id } from './fn.js'
|
||||||
|
import { Algebra, Monad } from './index.js'
|
||||||
|
|
||||||
|
/** @import { InferredMorphism } from './types.js' */
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @template T
|
||||||
|
* @typedef {InferredMorphism<T>} ReaderFn
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @template T */
|
||||||
|
export class Reader extends Algebra(Monad) {
|
||||||
|
#run
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {InferredMorphism<T>} run
|
||||||
|
*/
|
||||||
|
constructor(run) {
|
||||||
|
super()
|
||||||
|
|
||||||
|
this.#run = run
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @template T
|
||||||
|
* @param {T} a
|
||||||
|
* @returns {Reader<T>}
|
||||||
|
*/
|
||||||
|
static of(a) {
|
||||||
|
return new Reader(/** @type {InferredMorphism<T>} */(_env => a))
|
||||||
|
}
|
||||||
|
|
||||||
|
/** @template T */
|
||||||
|
static ask() {
|
||||||
|
return new Reader(/** @type {InferredMorphism<T>} */(id))
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {InferredMorphism<T>} f
|
||||||
|
* @returns {Reader<T>}
|
||||||
|
*/
|
||||||
|
map(f) {
|
||||||
|
return new Reader(/** @type {InferredMorphism<T>} */(env => f(this.#run(env))))
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {InferredMorphism<T>} f
|
||||||
|
* @returns {Reader<T>}
|
||||||
|
*/
|
||||||
|
chain(f) {
|
||||||
|
return new Reader(env => f(this.#run(env)).run(env))
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {InferredMorphism<T>} f
|
||||||
|
* @returns {Reader<T>}
|
||||||
|
*/
|
||||||
|
local(f) {
|
||||||
|
return new Reader(/** @type {InferredMorphism<T>} */(env => this.#run(f(env))))
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @template R
|
||||||
|
* @param {T} env
|
||||||
|
* @returns {R}
|
||||||
|
*/
|
||||||
|
run(env) {
|
||||||
|
return this.#run(env)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -15,6 +15,7 @@ export class Ok extends Algebra(Monad, Foldable) {
|
||||||
*/
|
*/
|
||||||
constructor(value) {
|
constructor(value) {
|
||||||
super()
|
super()
|
||||||
|
|
||||||
this.#value = value
|
this.#value = value
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue