web-dev-qa-db-ja.com

「影のない変数」tslint警告の意味を理解する

渡された特定の分野に基づいて、順次ストリームの現在のステージをチェックし、その値に応じて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は「nextStageStep」変数の各発生に下線を引いており、「no shadowed variables」という警告が表示されています。警告が消える空の文字列に初期化する行を削除すると、returnステートメントに「NextStageStepが見つかりません」というエラーが表示されます。

元のシャドウ変数警告の問題は何ですか?これを記述する別の方法がありますか、この状況でtslint警告を単に無視する必要がありますか?

26
Ademo

同じ変数を複数回再定義しているため、リンターは文句を言います。したがって、それを含むクロージャ内のものを置き換えます。

再宣言する代わりに、それを使用してください:

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;
}
45
toskv

これは、異なるスコープで同じ変数を定義することに関係しています。関数スコープ内および各ifブロック内でnextStageStepを定義しています。 1つのオプションは、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

3
LLai

に追加: 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、これはではなくシャドーイングの場合です-各定数はブレース内で正しくソーピングされます。

変数名を再利用できない場合、わかりにくいプログラムがわかりにくくなります。知らせるよりも。

警告は間違っていると思います

2

各ifブロックで同じ変数const nextStageStepを再宣言しています。

Justeはconst nextStageStep = 'step 2';nextStageStep = 'step 2';(および他のすべてのifケース)に置き換えれば大丈夫です。

2
FatL

一般に、このエラーが発生しますローカルスコープの変数とそれを含むスコープの変数の名前が同じ場合、シャドウイングが発生します。シャドウイングにより、包含スコープの変数にアクセスできなくなり、識別子が実際に参照する値がわかりにくくなります

これを説明するコードサンプルについては、これを参照してください 記事 .

1
Junaid

まず、警告を続行しても、関数「getNextStageStep()」は常に空の値を返しますが、

  • "const" aはblock-scoped変数であり、

  • 値のre-definingをサポートしていません[初期化された値は変更できません]。

returnブロック変数 "nextStageStep"には空の文字列値が含まれ、内部ブロック "nextStageStep"変数は外部ブロックの "nextStageStep"変数値をマスクまたはオーバーライドしません。

したがって、「nextStageStep」を返すときは常に、常に空の文字列を返します。

内部ブロックの「nextStageStep」変数のスコープは、ブロックのみで、ここで外部ブロックの「nextStageStep」変数が内部ブロックの「nextStageStep」変数と完全に異なる場合です。

コードが機能するで、mustconst変数を使用する場合は、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'));

ただし、代わりにこれらの多くのreturnステートメントを記述して、変数値を再定義できるlet変数を使用する方が適切です。あなたの問題については@ toskvソリューションが適切だと思います。

0
Sridhar K