理解'No Shadowed Variable'警告



我有一个函数,它根据传入的特定规则检查顺序流中的当前阶段,并根据该值在我的 Angular 2 应用程序中分配下一个值。它看起来像这样:

private getNextStageStep(currentDisciplineSelected) {
const nextStageStep = '';
if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 1') {
const nextStageStep = 'step 2';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 2') {
const nextStageStep = 'step 3';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 3') {
const nextStageStep = 'step 4';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 4') {
const nextStageStep = 'step 5';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 5') {
const nextStageStep = 'step 6';
}
return nextStageStep;
}

我在这里所做的是返回nextStageStep的值,因为这就是我将传递的内容,以便发生正确的阶段步骤。

现在,我的 tslint 正在用警告no shadowed variables为每个nextStageStep变量的出现下划线。如果我删除初始化为空字符串的行,则警告会消失,但随后出现错误,Cannot find nextStageStep显示在我的 return 语句中。

原始阴影变量警告有什么问题,是否有另一种方法来编写它,和/或在这种情况下我应该简单地忽略 tslint 警告?

linter 抱怨是因为您多次重新定义同一个变量。从而替换包含它的闭包中的那些。

与其重新声明它,不如使用它:

private getNextStageStep(currentDisciplineSelected) {
let nextStageStep = '';
if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 1') {
nextStageStep = 'step 2';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 2') {
nextStageStep = 'step 3';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 3') {
nextStageStep = 'step 4';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 4') {
nextStageStep = 'step 5';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 5') {
nextStageStep = 'step 6';
}
return nextStageStep;
}

通常,
当局部作用域中的变量和包含作用域中的变量具有相同的名称时,会发生阴影。阴影使得无法访问包含范围内的变量,并掩盖标识符实际引用的值。

const a = 'no shadow';
function print() {
console.log(a);
}
print(); // logs 'no shadow'.
const a = 'no shadow';
function print() {
const a = 'shadow'; // TSLint will complain here.
console.log(a);
}
print(); // logs 'shadow'.

有关解释这一点的代码示例,请参阅本文。

这与在不同的作用域中定义相同的变量有关。您正在函数范围内定义nextStageStep,并且在每个if块中定义。一种选择是删除 if 块中的变量声明

if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 1') {
nextStageStep = 'step 2';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 2') {
nextStageStep = 'step 3';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 3') {
nextStageStep = 'step 4';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 4') {
nextStageStep = 'step 5';
} else if (this.stageForDiscipline(this.currentDisciplineSelected) === 'step 5') {
nextStageStep = 'step 6';
}

这里有一个关于阴影变量的好资源 http://eslint.org/docs/rules/no-shadow

你在每个 if 块中重新声明相同的变量const nextStageStep

Juste 将const nextStageStep = 'step 2';替换为nextStageStep = 'step 2';(如果情况为所有其他(,一切都会好起来的。

添加到 : https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/const

ES6 const 是块范围的,因此:


{
const TAG='<yourIt>';
console.log(TAG);
}
{
const TAG = '<touchingBase NoImNOt="true">';
console.log(TAG);
}
console.log(TAG);  // ERROR expected

AFAICT,这不是阴影的情况 - 每个常量都在其大括号内正确排列。

如果我们不能重用变量名,我们最终会得到晦涩难懂的程序。 而不是通知。

我认为警告是错误的

首先,即使你继续警告,你的函数"getNextStageStep()"也将始终返回空值,

  • 因为 "const" a 是块范围的变量,并且

  • 它不支持重新定义值 [无法更改初始化的值]。

return块变量"nextStageStep"包含空字符串值,而内部块"nextStageStep"变量不会屏蔽或覆盖外块的"nextStageStep"变量值。

所以每当你返回"nextStageStep"时,它总是会返回空字符串。

内块"nextStageStep"变量的范围在if块范围内,这里外块"nextStageStep"变量与内块"nextStageStep"变量完全不同。

因此,如果您希望代码正常工作并且必须要使用const变量,请在 if 块中使用多个 return 语句。

下面是我检查的代码并且工作正常。 您可以根据需要使用它。

function  getNextStageStep(currentDisciplineSelected) {
const nextStageStep = '';
if (currentDisciplineSelected === 'step 1') {
const nextStageStep = 'step 2';
return nextStageStep;
} else if (currentDisciplineSelected === 'step 2') {
const nextStageStep = 'step 3';
return nextStageStep;
} else if (currentDisciplineSelected === 'step 3') {
const nextStageStep = 'step 4';
return nextStageStep;
} else if (currentDisciplineSelected === 'step 4') {
const nextStageStep = 'step 5';
return nextStageStep;
} else if (currentDisciplineSelected === 'step 5') {
const nextStageStep = 'step 6';
return nextStageStep;
}
return nextStageStep;
}
console.log(getNextStageStep('step 1'));

但是,最好使用let变量编写这些返回语句,从而重新定义变量值。对于您的问题,我认为@toskv解决方案是合适的。

找到并打开 tslint.json 文件,并将以下设置为 false

"no-shadowed-variable": false,

使用 Visual Studio时,可能需要重新启动 Visual Studio。

相关内容

最新更新