js函数式编程(二)-柯里化
这节开始讲的例子都使用简单的TS来写,尽量做到和es6差别不大,正文如下
我们在编程中必然需要用到一些变量存储数据,供今后其他地方调用。而函数式编程有一个要领就是最好不要依赖外部变量(当然允许通过参数传递咯),如何解决这个矛盾的问题呢?将函数柯里化`Curry`就可以了,这种技巧可以让函数记住一些历史数据,也就是缓存,怎么做呢?
说柯里化之前必须先说一下闭包,因为这是实现柯里化的方法。
## 闭包
const fun = () => {
let a = 0;
return () => {
a += 1;
return a;
};
};
const fa = fun();
console.log(fa()); // 1
console.log(fa()); // 2
console.log(fa()); // 3
每次运行这个函数居然结果不一样,why?因为`a`是`fun`函数内部变量,而这个变量又被`fun`返回的函数依赖,`fun()`执行后,fa所指向的那个函数(`fun`的返回值)还在依赖着`a`。根据js的垃圾回收机制,只要`fa`存在,那么`a`就不会被释放,一直在内存中。
进一步想,既然a
作为局部变量被依赖着就一直存在,那么这个局部变量要是参数是不是也有同样的效果呢,答案是肯定的。
```javascript
const fun = (a: number) => {
return () => {
a += 1;
return a;
};
};
const fa = fun(1);
console.log(fa()); // 2
console.log(fa()); // 3
console.log(fa()); // 4
```
好,闭包就讲这么多。回到柯里化。
## 柯里化
柯里化由函数闭包实现。我们把上面的例子改一改
```javascript
const fun = (a: number) => (b: number) => {
return a + b
};
const add2 = fun(2);
console.log(add2(2)); // 4
console.log(add2(3)); // 5
console.log(add2(4)); // 6
```
`fun(2)`就是`(b) => b+2`,所以`add2(2)`自然是`4`。以上就是柯里化,参数可以先后传入,全部传完才计算。以上是es6或ts的代码实现,比较简陋。事实上你完全不必要自己去实现一个函数的柯里化。可以使用成熟的库如ramda。ramda库还包含了很多已经柯里化的函数。
```javascript
import { curry } from 'ramda'
const fun = curry((a: number, b: number) => {
return a + b
});
const add2 = fun(2);
console.log(add2(2)); // 4
console.log(add2(3)); // 5
console.log(add2(4)); // 6
```
把一个你要柯里化的函数,原封不动的给curry函数,返回的就是柯里化的函数。但要注意函数参数从左往右的顺序是依次传给柯里化后函数的顺序。have fun!
js函数式编程(二)-柯里化的更多相关文章
- 函数式编程之柯里化(curry)
函数式编程curry的概念: 只传递给函数一部分参数来调用函数,然后返回一个函数去处理剩下的参数. var add = function(x) { return function(y) { retur ...
- JS中的反柯里化( uncurrying)
反柯里化 相反,反柯里化的作用在与扩大函数的适用性,使本来作为特定对象所拥有的功能的函数可以被任意对象所用.即把如下给定的函数签名, obj.func(arg1, arg2) 转化成一个函数形式,签名 ...
- JS 浅谈函数柯里化,不明觉厉
在计算机科学中,柯里化(Currying)是把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数且返回结果的新函数的技术.这个技术由 Christopher ...
- js bind es5函数柯里化
绑定函数 bind()最简单的用法是创建一个函数,使这个函数不论怎么调用都有同样的this值.常见的错误就像上面的例子一样,将方法从对象中拿出来,然后调用,并且希望this指向原来的对象. 如果不做特 ...
- js链式调用 柯里化
var d = 1; d.add(2).add(3).add(4) //输出10 写出这个add函数 Number.prototype.add = function(x){ return this + ...
- JavaScript函数的柯里化(currying)
转载请注明出处:http://www.cnblogs.com/shamoyuu/p/currying.html 什么是js函数的currying /柯里化? 说到js的柯里化,相信很多朋友都会头大.或 ...
- 简单粗暴详细讲解javascript实现函数柯里化与反柯里化
函数柯里化(黑人问号脸)???Currying(黑人问号脸)???妥妥的中式翻译既视感:下面来一起看看究竟什么是函数柯里化: 维基百科的解释是:把接收多个参数的函数变换成接收一个单一参数(最初函数的第 ...
- JavaScript ES6函数式编程(二):柯里化、偏应用和组合、管道
上一篇介绍了闭包和高阶函数,这是函数式编程的基础核心.这一篇来看看高阶函数的实战场景. 首先强调两点: 注意闭包的生成位置,清楚作用域链,知道闭包生成后缓存了哪些变量 高阶函数思想:以变量作用域作为根 ...
- Java函数式编程:二、高阶函数,闭包,函数组合以及柯里化
承接上文:Java函数式编程:一.函数式接口,lambda表达式和方法引用 这次来聊聊函数式编程中其他的几个比较重要的概念和技术,从而使得我们能更深刻的掌握Java中的函数式编程. 本篇博客主要聊聊以 ...
随机推荐
- (三)siege的使用
学习: ELK——http://dockone.io/article/3655 docker——http://www.testclass.net/docker/ Android Monkey压力测试— ...
- css3中-moz、-ms、-webkit、-o
-moz代表firefox浏览器私有属性-ms代表IE浏览器私有属性-webkit代表chrome.safari私有属性-o代表opera私有属性
- PAT甲级——1105 Spiral Matrix (螺旋矩阵)
此文同步发布在CSDN:https://blog.csdn.net/weixin_44385565/article/details/90484058 1105 Spiral Matrix (25 分) ...
- HTML5----前段各种常见BUG
1.在IE6下,DIV中的字会多出,并且自成一行,而且是原来的字. 这是注释bug,经典的ie6 bug. 说明:注释造成文字溢出是IE6的BUG,注释造成文字溢出与其位置有关,注释造成文字溢 ...
- [LOJ3054] 「HNOI2019」鱼
[LOJ3054] 「HNOI2019」鱼 链接 链接 题解 首先想 \(O(n^3)\) 的暴力,不难发现枚举 \(A\) 和 \(D\) 后, \((B,C)\) 和 \((E,F)\) 两组点互 ...
- Codeforces Round #432 (Div. 2, based on IndiaHacks Final Round 2017) D
Arpa has found a list containing n numbers. He calls a list bad if and only if it is not empty and g ...
- mysql 驱动问题
转 : https://blog.csdn.net/bloodycuckoo/article/details/51175339 转 : https://blog.csdn.net/u010746431 ...
- 单周期cpu设计代码解读
目录 写在前面 单周期cpu设计代码讲解 概念回顾 Verilog代码讲解 写在前面 欢迎转载,转载请说明出处. 单周期cpu设计代码讲解 概念回顾 一.电子计算机的部件 分为:中央处理器(cpu). ...
- windows 安装 jdk1.8并配置环境变量
1.查看电脑环境 我的电脑--右键--属性 2.下载jdk1.8 网址:https://www.oracle.com/technetwork/java/javase/downloads/jdk8-do ...
- 网络编程之异步IO,rabbitMQ笔记
对于网络并发编程而言,多线程与多进程算是最常见的需求场景了.毕竟网站开放就是想要更多的流量访问的. 回顾 回顾下之前学过的关于线程,进程和协程的知识点 IO密集型任务--用多线程更好计算密集型任务-- ...