Search code examples
javascriptfunctional-programmingfunctor

Is this a Functor


Recently I am learning functors and monads but it seems a little bit confusing. I have written this to chain multiple operations and wonder if it is a functor and I understand it correctly?

function Init(store = {}) {
  const map = (fn) => {
    const result = fn(store)
    return Init(result ? {...store, ...result} : store)
  }
  const unwrap = () => store
  return {
    map,
    unwrap
  }
}

// example usage
Init()
.map(fetchData)
.map(fetchOtherData)
.map(compareTwoData)
.map(saveAllData)
// ...etc

Solution

  • I don't think it is, because Functors must preserve composition map(g°h)=map(g)°map(h), which yours does not:

    function Init(store = {}) {
        const map = (fn) => {
            const result = fn(store)
            return Init(result ? {...store, ...result} : store)
        }
        const unwrap = () => store
        return {
            map,
            unwrap
        }
    }
    
    a = x => ({...x, a:1})
    b = x => 0
    
    
    console.log(Init({X:1}).map(a).map(b).unwrap())
    console.log(Init({X:1}).map(x => b(a(x))).unwrap())

    Here's an example of a basic Functor that satisfies both functor laws:

    function Functor(value) {
        const fmap = (fn) => {
            const result = fn(value)
            return Functor(result)
        }
        return {fmap, value}
    }
    
    //
    
    let id = x => x
    let a = x => x * 5
    let b = x => x + 3
    
    
    // identity
    console.log(
        Functor(7).value === Functor(7).fmap(id).value
    )
    
    // composition
    console.log(
        Functor(7).fmap(a).fmap(b).value ===
        Functor(7).fmap(x => b(a(x))).value
    )