我们有一个包含信息的请求对象。该特定对象有一个名为partnerId
的字段,用于确定我们要对请求执行的操作。
典型的方法是巨大的if / then / else:
function processRequest( request ){
if( request.partnerId === 1 ){
//code here
}else if( request.partnerId === 23 ){
//code here
}
//and so on. This would be a **huge** if then else.
}
这种方法有两个主要问题:
为了绕过以前的问题,我挑战我的同事想出一个不同的解决方案,他想出了一个动态构建我们想要使用的函数名称并调用它的函数。听起来很复杂,但这段代码将澄清它:
const functionHolder = {
const p1 = request => {
//deals with request
};
const p23 = request => {
//deals with request
};
return { p1, p23 };
};
const processRequest = request => {
const partnerId = request.partnerId;
const result = functionHolder[`p${partnerId}`](request);
return result;
};
此解决方案优于前一个解决方案:
然而,它也存在一些问题:
functionHolder
。 p1
和p23
并不共享任何共同点,我们只是使用此对象,因为我们不知道我们如何动态构建函数的名称并将其命名为else
个案。如果我们得到一个不正确的参数代码就会爆炸。 non-used-vars
的out eslint抱怨p1
和p23
未被使用,我们也不知道如何修复它(https://eslint.org/docs/rules/no-unused-vars)。 最后一个问题给我们的印象是,这个解决方案可能不是那么好。也许这种模式可以避免如果其他的话还有一些我们尚未发现的邪恶。
functionHolder
对象?期待任何反馈!
答案 0 :(得分:1)
你可以通过从不首先声明它们来摆脱未使用的变量:
const functionHolder = {
p1: request => {
//deals with request
},
p23: request => {
//deals with request
};
};
const processRequest = request => {
const partnerId = request.partnerId;
const method = functionHolder[`p${partnerId}`]
if(method) // Is there a method for `partnerId`?
return method(request);
return null; // No method found. Return `null` or call your default handler here.
};
回答你的观点:
答案 1 :(得分:0)
也许我没有正确理解这个问题,但为什么不能成为持有这些方法的对象?
const functionHolder = {
1: function(request) {
// do something
},
23: function(request) {
// do something
},
_default: function(request) {
// do something
}
}
function processRequest(request) {
(functionHolder[request.partnerId] || functionHolder._default)(request)
}
说明:
functionHolder
包含用于处理给定请求的每种方法。functionHolder
的键(例如1
)将直接对应request.partnerId
的值,这些成员的值是适当的方法。< / LI>
processRequest
&#34;选择&#34; functionHolder
中的适当方法(即object[key]
),并将此方法作为参数调用此方法(即method(parameter)
)。_default
与任何现有密钥不匹配,我们在密钥request.partnerId
下也有默认方法。鉴于a || b
;如果a
是&#34; falsy&#34;,在这种情况下undefined
(因为没有对象的相应成员),请评估为b
。如果您担心functionHolder
&#34;臃肿&#34;,那么您可以将每种方法分开:
const p1 = request => {
// do something
}
const p23 = request => {
// do something
}
const _default = request => {
// do something
}
然后将它们组合成一个&#34;摘要&#34;各种各样的对象。
const functionHolder = {
1: p1,
23: p23,
_default: _default
}
processRequest
与上述相同。
这会增加很多全局变量。
另一个优点是您可以动态导入/更改/声明方法。 e.g。
functionHolder[1] = p1b // where p1b is another request handler (function) for `request.partnerId` = 1
functionHolder[5] = p5 // where p5 is a request handler (function) that has not yet been declared for `request.partnerId` = 5
结合上述内容,无需声明许多全局变量,同时还能够分离每种方法的声明:
const functionHolder = {}
functionHolder._default = request => {
// do something
}
functionHolder[1] = request => {
// do something
}
functionHolder[23] = request => {
// do something
}
processRequest
与上述相同。
你必须确保这些方法已经加载到&#34;在致电functionHolder
之前致processRequest
。