javascript - 这不是纯函数吗?
问题描述
我正在学习 Web 开发的状态管理,并遇到了这个带有纯功能的 redux 教程,如下所示。然而声明:“action.todo.id = state.todos.length + 1;” 让我怀疑这个纯函数是……不纯的。请赐教,谢谢!
export function rootReducer(state: IAppState, action): IAppState {
switch (action.type) {
case ADD_TODO:
action.todo.id = state.todos.length + 1;
return Object.assign({}, state, {
todos: state.todos.concat(Object.assign({}, action.todo)),
lastUpdate: new Date()
})
case TOGGLE_TODO:
var todo = state.todos.find(t => t.id === action.id);
var index = state.todos.indexOf(todo);
return Object.assign({}, state, {
todos: [
...state.todos.slice(0, index),
Object.assign({}, todo, {isCompleted: !todo.isCompleted}),
...state.todos.slice(index+1)
],
lastUpdate: new Date()
})
case REMOVE_TODO:
return Object.assign({}, state, {
todos: state.todos.filter(t => t.id !== action.id),
lastUpdate: new Date()
})
case REMOVE_ALL_TODOS:
return Object.assign({}, state, {
todos: [],
lastUpdate: new Date()
})
}
return state;
}
解决方案
TL; DR - 不,不是。
让我们检查一下纯函数的定义。来自维基百科:
在计算机编程中,纯函数是具有以下属性的函数:
对于相同的参数,它的返回值是相同的(本地静态变量、非本地变量、可变引用参数或来自 I/O 设备的输入流没有变化)。
它的评估没有副作用(没有局部静态变量、非局部变量、可变引用参数或 I/O 流的突变)。
尽管您的函数确实符合第二个条件,但使用new Date()
- 使其不纯。
在您的情况下,其杂质的原因是每个函数调用的日期都不同 - 无论传递的参数如何。
为了使其纯净,您应该将日期作为附加参数传递,这将允许您对相同的输入具有相同的输出。
Zaptree 还提到改变您的项目 ID 的长度,即 action.todo.id = state.todos.length + 1
不纯,因为它可能会影响引用它的其他方。
推荐阅读
- google-bigquery - 运行 SQL 执行即时查询以在 python 函数内的 Bigquery 中合并表
- sql - sql server 按字母顺序排序,然后是数字
- node.js - “无效的钩子调用。只能在函数组件的主体内部调用钩子”,同时使用 react-router-dom 中的 useLocation() 钩子
- python - 如何检查字符串是一个单词还是一堆没有意义的字母?
- woocommerce - 自定义价格计算后缀小数位无法正确显示的问题
- python - 如何对熊猫数据框中的所有输入变量进行秩归一化迭代
- docker - 如果一个服务不可访问,Traefik 路由到不同的服务
- typescript - 为什么 Typescript 说 X 可能在 useMemo 内部未定义,而此时它永远不可能未定义
- r - 在 R 中解决“错误:填充参数既不是颜色也不是有效的变量名”?
- javascript - 如何处理带有过滤器的承诺拒绝?