【问题标题】:How to execute a function that returns a function inside of IO monad如何执行返回 IO monad 内部函数的函数
【发布时间】:2022-01-30 19:10:24
【问题描述】:

我正在使用“Ramda/Fantasy”库来创建 Monad。我正在尝试结合 IO 从 DOM 中获取元素并更改其文本内容。但问题是改变元素内容的函数需要接受两个参数元素和我们想要设置的文本。我不知道我如何才能有效地找到一个看起来像这样的解决方案:

const getElement = id => IO(() => document.querySelector(id));
const setElementText = element => text => IO(() => element.textcontent = text);

getElement('h1').map(setElementText).runIO()('New Title').runIO();

有没有更好的办法?

【问题讨论】:

标签: javascript functional-programming monads ramda.js ramda-fantasy


【解决方案1】:

对您的示例有所帮助的两个小改动:

  • 将参数的顺序交换为setElementText 允许您部分应用文本值。
  • 使用chain 而不是map 消除对第二个runIO 调用的需要。
const getElement = id => IO(() => document.querySelector(id))
const setElementText = text => element => IO(() => element.textContent = text)

getElement('h1').chain(setElementText('New Title')).runIO()

【讨论】:

  • 该解决方案有效,我还找到了使用“ap()”方法的第二个解决方案,但我不知道是否可以调用两次“runIO()”?
  • 调用runIO 两次不一定是错误的,尽管通常没有必要,因为当你这样做时你会“突破” IO 类型。对于大量使用类似 IO 类型的应用程序,它们通常由许多组合在一起的 IO 类型组成,然后在应用程序的入口点调用 runIO 并使用 IO 值。
【解决方案2】:

我还找到了使用“ap()”方法的第二种解决方案,该方法将函数(由此 IO 实例中的操作产生)应用于给定 IO 实例中的操作产生的值。

import {IO} from "ramda-fantasy";

const getElement = id => IO(() => document.querySelector(id))
const setElementText = element => text => IO(() => element.textContent = text)

const someText = IO(() => 'New Title')

const setHeading = getElement('h1').map(setElementText).ap(someText).runIO();
setHeading.runIO(); // It works

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-02-23
    • 1970-01-01
    • 1970-01-01
    • 2019-02-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多