例如,从这个例子:
export const ADD_TODO = 'ADD_TODO'
export const DELETE_TODO = 'DELETE_TODO'
export const EDIT_TODO = 'EDIT_TODO'
export const COMPLETE_TODO = 'COMPLETE_TODO'
export const COMPLETE_ALL = 'COMPLETE_ALL'
export const CLEAR_COMPLETED = 'CLEAR_COMPLETED'
它不像你在保存字符。变量名称与字符串完全相同,永远不会更改。如果有一天你做了类似的事情,我理解制作常数:
ADD_TODO = 'CREATE_TODO'
但这种情况从未发生过。那么这些常数的用途是什么呢?
答案 0 :(得分:61)
你是对的,它不是关于保存字符,但是在代码缩小后你可以节省一些空间。
在redux中,你至少在两个地方使用这些常量 - 在你的reducer和动作创建过程中。因此,在某个文件中定义一次常量非常方便,例如actionTypes.js
export const ADD_TODO = 'ADD_TODO';
export const DELETE_TODO = 'DELETE_TODO';
export const EDIT_TODO = 'EDIT_TODO';
export const COMPLETE_TODO = 'COMPLETE_TODO';
export const COMPLETE_ALL = 'COMPLETE_ALL';
export const CLEAR_COMPLETED = 'CLEAR_COMPLETED';
然后在动作创建者文件中要求它,例如actions.js
import { ADD_TODO } from './actionTypes';
export function addTodo(text) {
return { type: ADD_TODO, text };
}
在某些减速机中
import { ADD_TODO } from './actionTypes';
export default (state = [], action) => {
switch (action.type) {
case ADD_TODO:
return [
...state,
{
text: action.text,
completed: false
}
];
default:
return state
}
};
它允许您在项目中轻松找到该常量的所有用法(如果您使用IDE)。它还可以防止你引入由错别字引起的愚蠢错误 - 在这种情况下,你会立即获得ReferenceError
。
答案 1 :(得分:46)
我想引用@dan_abramov,Redux的作者来自对类似Github问题的评论。
的链接为什么这有益?通常声称常量是不必要的,对于小项目,这可能是正确的。对于较大的项目,将操作类型定义为常量有一些好处:
它有助于保持命名的一致性,因为所有操作类型都集中在一个地方。
有时您希望在处理新功能之前查看所有现有操作。可能你需要的行动已经被团队中的某个人添加,但你不知道。
在Pull Request中添加,删除和更改的操作类型列表可帮助团队中的每个人跟踪新功能的范围和实施。
如果在导入动作常量时输入拼写错误,则会得到未定义的内容。当你想知道为何在调度行动时没有任何反应时,这比输入错字更容易注意到。
答案 2 :(得分:4)
这在其他语言中更有用,但在JavaScript中也有一些用处。例如,如果我在整个代码中使用"ADD_TODO"
而不是ADD_TODO
,那么如果我输入任何字符串时出错,如果它是代码if (action === 'ADD_TODOz')
,那么该代码执行,它会做错事。但是如果你错误输入了const if (action === ADD_TODOz)
的名字,那么当该行试图执行时,你会得到ReferenceError: ADD_TODOz is not defined
,因为ADD_TODOz
是无效的引用。当然,在静态语言中,您将在“编译时”收到错误。