typescript - OO 到函数式——从日常问题中学习

标签 typescript functional-programming fp-ts

我正准备使用 fp-ts 学习函数式编程,我只是在问自己,将这样的东西“转换”为函数式范式的正确函数式方法是什么:

//OOP:

interface Item {
  name: string;
}

class X {
  private readonly items: { [s:string]: Item[] } = {};

  add(i: Item): Item {
    if(!this.items.hasOwnProperty(i.name))
      this.items[i.name] = [];

    if(this.items[i.name].indexOf(i) < 0)    
      this.items[i.name].push(i);

    return i;
  }
}

所以,我想我应该这样做:

import * as O from 'fp-ts/es6/Option';
import * as E from 'fp-ts/es6/Either';

// using interfaces from above

interface state {
  items: { [s:string]: Item[] }
}

export const createState = (): State => ({ items: {} });


export const add = (s: State, i: Item) => pipe(
  // using IO here?
  E.fromPredicate(
    () => s.hasOwnProperty(i.name),
    () => []
  )
  
    
)

// to use it:

import { createState, add } from './fx';

let state = createState();

// update
state = add(state, {name: 'foo'})

既然add()操作涉及到state的修改,是不是应该依赖IO?如果 add 返回一个新的状态对象,它是一个纯函数,所以它不需要使用 IO?所以我在这里提出的问题可能有点宽泛,但是:这里推荐的技术/模式是什么?

最佳答案

Since the add() operation involves the modification of state, should it rely on IO?

是的,add() 不会返回任何内容,但具有状态效果,因此它应该返回 IO<void>

If add returns a new state object, it is a pure function, so it wouldn't need to use IO?

正确。

What are the recommended techniques/pattern here?

函数式程序员通常不惜一切代价避免可变状态。

您要实现的是写时复制多重映射。您不需要 fp-ts 中的任何内容为此。

type MyItem = { name: string };

// we've made the store polymorphic
type MyObj<Item> = { [s: string]: Item[] };

// this is only necessary if you want to expose an implementation-independent api.
export const empty = {};

// i before o, in case we want currying later, o will change more.
const add = <Item>(k: string, v: Item, o: MyObj<Item>) => 
  // abuse the spread operator to get create a new object, and a new array
  ({ ...o, [k]: [v, ...(o[k] || [])] });

// specialization for your item's case
export const addMyItem = (i: MyItem, o: MyObj<MyItem>) => add(i.name, i, o);

然后你可以这样做:

const a = addMyItem({ name: "test" }, addMyItem({ name: "test" }, empty));

关于typescript - OO 到函数式——从日常问题中学习,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/65714555/

相关文章:

angular - 我应该将什么样的对象传递给 `FormBuilder.group()` 才能正确实例化字段?

language-agnostic - "lazy evaluation"和 "reactive programming"

concurrency - 如何限制 fp-ts 中的并发

TypeScript 推断数组 [index]

javascript - 在应用程序或组件加载 Angular 7 之前运行服务

generics - 无法在Rust的递归枚举中推断泛型函数的类型

typescript - 如何使用 fp-ts 将 TaskOption 转换为 TaskEither?

typescript - 在 fp-ts 中,如何组合 2 个(或更多)Ord 实例

kendo-ui - 将 Kendo UI 与 TypeScript 0.9.1 结合使用会导致 Kendo 的定义文件中出现许多错误

haskell - Haskell 中的插入排序