Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

3.手写柯里化函数 #3

Open
gumingWu opened this issue May 19, 2022 · 3 comments
Open

3.手写柯里化函数 #3

gumingWu opened this issue May 19, 2022 · 3 comments

Comments

@gumingWu
Copy link
Owner

乘热打铁,刚刚写完bind。那就可以来一个很相近的柯里化啦!
还是老样子,一篇博文镇楼 羽哥的柯里化

在数学和计算机科学中,柯里化是一种将使用多个参数的一个函数转换成一系列使用一个参数的函数的技术。

function add(a, b) {
    return a + b;
}

// 执行 add 函数,一次传入两个参数即可
add(1, 2) // 3

// 假设有一个 curry 函数可以做到柯里化
var addCurry = curry(add);
addCurry(1)(2) // 3

请写出这个curry函数

@gumingWu
Copy link
Owner Author

/**
 * 柯里化,currying,将接收多个参数的函数,变成分别接收不定数参数的函数
 * 本质就是利用闭包保存传入的参数,当入参个数足够时,就计算并返回结果
 */
function add(a, b, c) {
  return a + b + c;
}

// 变成
function curryingAdd(a) {
  return function (b) {
    return function (c) {
      return a + b + c;
    };
  };
}

// 写好看点
const beautifulCurryingAdd = (a) => (b) => (c) => a + b + c;

console.log(add(1, 2, 3)); // 6
console.log(curryingAdd(1)(2)(3)); // 6
console.log(beautifulCurryingAdd(1)(2)(3)); // 6

function currying(fn, ...args) {
  let allArgs = [...args];
  const needLen = fn.length; // 函数的长度,等于入参的个数

  const next = (...newArgs) => {
    allArgs = [...allArgs, ...newArgs];
    if (allArgs.length >= needLen) {
      return fn(...allArgs);
    } else {
      return next;
    }
  };

  return next;
}

console.log(currying(add, 1)(2, 3)); // 6
console.log(currying(add)(1, 2)(3)); // 6

@ClearMing
Copy link

function curry(fn) {
    //保存预置函数
    const presetArgs = [].slice.call(arguments, 1)
    //返回一个新函数
    function curried() {
        //新函数调用的时候继续传参
        const restArgs = [].slice.call(arguments)
        const allArgs = [...presetArgs, ...restArgs]
        return curry.call(null, fn, ...allArgs)
    }

    //重写toString
    curried.toString = function () {
        return fn.apply(null, presetArgs)
    }
    return curried

}


//测试案例
function dynamicAdd() {
    return [...arguments].reduce((prev, curr) => {
        return prev + curr
    }, 0)
}
const add = curry(dynamicAdd)
console.log(add(1)(2)(3)(4).toString());
console.log(add(1, 2)(3, 4)(5, 6).toString());

@LuMMao
Copy link

LuMMao commented May 23, 2022

来了来了

// 已知参数个数
const TEN_BASE = 10;
const TWO_BASE = 2;
function base(base_number) {
  return function multiple(x) {
    return base_number * x;
  };
}
let ten_multiple = base(TEN_BASE)(3);
let two_multiple = base(TWO_BASE)(3);
console.log(ten_multiple, two_multiple);

// 不定参数个数
function add(...oldArgs) {
  let args = oldArgs;

  function inner(...newArgs) {
    args = args.concat(newArgs);
    return inner;
  }

  inner.toString = function () {
    return args.reduce((prev, cur) => {
      return prev + cur;
    });
  };

  return inner;
}
let add_simple1 = +add(1)(2)(3);
let add_simple2 = +add(1, 2)(3, 4, 5)(6)(7, 8);
console.log(add_simple1, add_simple2);

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants