纯函数
在程序设计中,若一个函数符合以下条件,那么这个函数被称为纯函数:
- 此函数在 相同的输入值 时,需产出 相同的输出。
- 函数和输出和输入值以外的其他隐藏信息和状态无关,也和由于 I/O设备产生的外部输出无关。
- 该函数不能有语义上可观察到的函数副作用,诸如“触发事件”,使输出设备输出,或更改输出值以外物件的内容。
确定的输入一定会产生确定的输出
函数执行的过程中,不会产生任何的副作用
副作用:
在执行一个函数时,除了返回函数数值之外,还对调用函数产生了附加的影响,比如 修改了全局变量,修改参数或者改变外部存储。
柯里化
把接收多个参数的函数,变成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接收余下参数,而且返回结果的新函数的技术。
只传递一部分参数调用函数,并让它返回一个函数去处理剩余的参数的过程就叫做柯里化
function add (x, y, z) {
return x + y + z
}
const result = add(1, 2, 3)
console.log(result)
// add 函数的柯里化实现
function addC (x) {
return function (y) {
return function (z) {
return x + y + z
}
}
}
const resultC = addC(1)(2)(3)
console.log(resultC)
// sum 函数的柯里化简化版本
const addCS = x => {
return y => {
return z => {
return x + y + z
}
}
}
console.log(addCS(1)(2)(3))
const addCS2 = x => y => z => x + y + z
console.log(addCS2(1)(2)(3))
柯里化存在的原因(思想?)
- 在函数式编程中,我们希望一个函数处理的问题尽可能单一,所以将每次传入的参数在单一的函数中进行处理,处理完毕之后在下一个函数中再使用处理后的结果。
- 并且,柯里化还有助于我们进行逻辑的复用:
function log (date, type, message) {
console.log(`[${date.getHours()}:${date.getMinutes()}][${type}]:[${message}]`)
}
log(new Date(), 'DEBUG', '查找到轮播图的bug')
log(new Date(), 'DEBUG', '查询菜单的bug')
log(new Date(), 'DEBUG', '查询数据的bug')
// 柯里化使得逻辑复用,减少传参数目
const logC = date => type => message => {
console.log(`[${date.getHours()}:${date.getMinutes()}][${type}]:[${message}]`)
}
const nowLog = logC(new Date())
nowLog("DEBUG")("测试查找BUG")
const nowAndDebugLog = logC(new Date())('DEBUG')
nowAndDebugLog('查找轮播图BUG')
手写柯里化函数
function add (x, y, z) {
return this.a + x + y + z
}
function Currying (fn) {
function curried (...args) {
if (args.length >= fn.length) {
// 这里使用 fn.apply 是为了当 f.call({ a: 3 }, 10, 20, 30)
// 时将 {a: 3} 作为 fn 的 this
return fn.apply(this, args)
} else {
return function (...args2) {
return curried.apply(this, [...args, ...args2])
}
}
}
return curried
}
const f = Currying(add)
console.log(f.call({ a: 3 }, 10, 20, 30)) // 63
组合函数
假设我们现在要对某一个数据进行函数调用,需要依次执行两个函数 fn1、fn2,我们将这两个函数组合起来自动依次调用的过程就称为组合函数。
function double (num) {
return num * 2
}
function square (num) {
return num ** 2
}
let count = 10
let result = square(double(count))
console.log(result)
// 组合函数
function composeFn (f, g) {
return function (count) {
console.log(g(f(count)))
}
}
composeFn(double, square)(10)
通用组合函数
function hyCompose (...fns) {
const length = fns.length
for (let i = 0; i < length; i++) {
if (typeof fns[i] !== 'function') {
throw new TypeError('要求都是函数类型')
}
}
return function (...args) {
let idx = 0
let result = length ? fns[idx].apply(this, args) : args
while (++idx < length) {
result = fns[idx].call(this, result)
}
return result
}
}
function double (m) {
return m * 2
}
function square (n) {
return n ** 2
}
var newFn = hyCompose(double, square)
console.log(newFn(10))
标签:function,return,函数,组合,柯里化,console,log
From: https://www.cnblogs.com/dirtycat/p/17508837.html