我想知道在我的具体案例中使用switch
语句是否更好。
我正在编写Alexa自定义技能,我需要根据可用信息(也称为插槽)“重定向”到适当的意图。以下是我目前使用的if/else
):
if (_type === "IntentRequest") {
this.handler.state = states.START;
if (_slots.indexOf("address") != -1) {
this.emitWithState("GoingToAddressIntent");
} else if (_slots.indexOf("place") != -1) {
this.emitWithState("GoingToPlaceIntent");
} else if (_slots.indexOf("type") != -1) {
this.emitWithState("GoingToTypeIntent");
} else if (_slots.indexOf("purpose") != -1) {
this.emitWithState("GoingToPurposeIntent");
} else {
this.emit("Unhandled");
}
}
我希望_slots
是四个元素[ "address", "place", "type", "purpose" ]
的任何排列的数组。因此,它可以是[ "address" ]
到[ "place", "purpose" ]
等等,但总是以相同的顺序(例如[ "purpose", "address" ]
永远不会发生)。< / p>
比较的顺序很重要,因为信息存在“等级”;因此,如果存在“地址”广告位,我必须emit
"GoingToAddressIntent"
,无论其他广告位是否可用。鉴于这个要求,我认为使用switch
语句可能更直接和可读,尽管必须有一些额外的代码行来将字符串数组“转换”为一个布尔数组。它清楚地说明了层次结构和确保按顺序评估它们。我能做到:
if (_type === "IntentRequest") {
this.handler.state = states.START;
slots = [
_slots.indexOf("address") != -1,
_slots.indexOf("place") != -1,
_slots.indexOf("type") != -1,
_slots.indexOf("purpose") != -1
]
switch(slots.indexOf(true)) {
case 0:
this.emitWithState("GoingToAddressIntent");
break;
case 1:
this.emitWithState("GoingToAddressIntent");
break;
case 2:
this.emitWithState("GoingToTypeIntent");
break;
case 3:
this.emitWithState("GoingToPurposeIntent");
break;
default:
this.emit("Unhandled");
}
}
...在这种情况下,我有一个额外的行来定义布尔数组,使用indexOf()
来获取第一次出现的true
文字的索引(因为所有4个插槽总是按层次结构顺序),并通过switch语句运行它。然而,我想问专家他们对这种情况下最佳编程实践的理念及其背后的原因,因为我希望这成为一个可维护的长期项目,而且我相信我可以从他们的见解中学到一些东西。 / p>
如果您认为应该将其迁移到SE上的其他社区,请发表评论,但是从我的research(虽然3岁)我相信这应该没问题(我对此并不是100%自信)这一点)。
答案 0 :(得分:4)
如果他们总是按照myVar = setInterval(function1, function2());
中的优先顺序排列,也许您可以制作一个哈希映射到您要发出的状态......
_slots
答案 1 :(得分:1)
我不会用你的switch语句示例。人们可以理解你正在尝试做什么,但看起来确实很复杂。我使用switch语句非常自由,主要是在后端代码中,我认为它可以正常工作。一组if / else也很好,因为你需要解决的只有4个案例。让我们按照开关语句滚动,因为那是你要问的问题。
根据您的解释,虽然您获得的第一个值可能不同,但订单总是相同的。所以解决方案就是简单地抓取第一个值,然后切换它。
if (!!slots.length) {
var keyword = slots[0];
switch (keyword) {
case 'address':
this.emitWithState("GoingToAddressIntent");
break;
case 'place':
this.emitWithState("GoingToPlaceIntent");
break;
case 'type':
this.emitWithState("GoingToTypeIntent");
break;
case 'purpose':
this.emitWithState("GoingToPurposeIntent");
break;
default:
this.emit('Unhandled'); // I typically throw an exception here
}
}