【问题标题】:Is this the correct recursive way to write curry function?这是编写咖喱函数的正确递归方式吗?
【发布时间】:2022-03-12 15:39:56
【问题描述】:

我不明白这个递归咖喱函数是否正确。

function curry(fn) {
  return function curryInner(...args) {
    if (args.length >= fn.length) return fn(...args);
    return function (...next) {
      return curryInner(...args, ...next);
    };
  };
}

const example = {
  multiplier: 5,
  calculate: function (a, b) {
    return (a + b) * this.multiplier;
  },
};
example.curriedVersion = curry(example.calculate);

console.log(example.calculate(1, 2));
console.log(example.curriedVersion(1)(2));

我有带绑定的 curry 函数实现,但我不确定它为什么起作用而递归不起作用。你能帮我理解一下吗,我认为我对这个函数的上下文理解不正确

function curry(func) {
    return function curried(...args) {

        if (args.length >= func.length) {
            return func.apply(this, args)
        } else {
            return curried.bind(this, ...args)
        }
    }
}

【问题讨论】:

  • 你对哪一部分感到困惑?
  • "我不明白这个递归柯里函数是否正确。" 如果用这个函数柯里化的结果是错误的,那么柯里函数是错误的。为什么你不相信这一点?
  • 我不明白为什么它不正确

标签: javascript closures bind currying


【解决方案1】:

你的curring是正确的,问题出在this.multiplier

当您使用表达式example.calculate 而不调用函数时,它不会绑定this。所以this.multiplier 将是undefined

使用example.calculate.bind(example),您的柯里化将按预期工作。

function curry(fn) {
  return function curryInner(...args) {
    if (args.length >= fn.length) return fn(...args);
    return function (...next) {
      return curryInner(...args, ...next);
    };
  };
}

const example = {
  multiplier: 5,
  calculate: function (a, b) {
    return (a + b) * this.multiplier;
  },
};
example.curriedVersion = curry(example.calculate.bind(example));

console.log(example.calculate(1, 2));
console.log(example.curriedVersion(1)(2));

【讨论】:

  • 作为后续,我能问一下为什么我们在第二个实现中使用 apply 吗?
  • apply() 是在 ES6 中添加扩展语法之前的旧方式。
猜你喜欢
  • 2013-02-09
  • 1970-01-01
  • 1970-01-01
  • 2012-05-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-06-28
相关资源
最近更新 更多