【问题标题】:Strict mode constrictions in JavascriptJavascript 中的严格模式限制
【发布时间】:2017-02-07 22:12:12
【问题描述】:

嘿,所以我有一个函数,它从输入框中获取一个字符串并将其拆分为数字和字母,如下所示:

function sepNsLs() {
  "use strict"; 
  var letterArray = [];
  var numberArray = [];
  separatorSpacerator();
  var L = 0;
  var listResult = document.getElementById("listInput").value;
  var splitResult = listResult.split(separator.sep);
  for (; L < splitResult.length; L++) {
    if (isNaN(splitResult[L])) {
      letterArray.push(splitResult[L]);
    } else if (Number(splitResult[L])) {
      numberArray.push(splitResult[L]);
    }
  }
}

我的程序必须完美地通过 JSLint,这意味着我需要在严格模式下使用我的函数。我现在只将它们置于严格模式,这意味着我以后尝试调用我在 SepNsLs 函数中声明和填充的 letterArray 和 numberArray 的函数不再调用这些数组,并且这些数组未声明。这是其中之一的代码:

function addNumbers() {
  "use strict"; 
  var sum = 0;
  var i = 0;
  sepNsLs();
  while (i < numberArray.length) {
    sum = sum + Number(numberArray[i]);
    i++;
  }

如您所见,我在 addNumbers 函数中调用了 sepNsLs 函数,但由于严格模式,我无法使用 sepNsLs 创建的数组。我该如何解决?另外,有没有像 javascript beautifier 这样的网站可以修复我当前的代码以适应严格的模式约定?

编辑:分隔符在这里被声明为全局变量:

var separator = {
  sep: 0
};

separatorSpacerator 使得如果我选择在空格处分割我的输入字符串,告诉我的程序在空格处分割的输入框声明了单词“Space”,所以我可以看到它是我正在分割的空格我的字符串在。

function separatorSpacerator() {
  "use strict"; 
  var list = document.getElementById("listInput").value;
  if (document.getElementById("separatorInput").value === "space") {
    separator.sep = " ";
  } else if (document.getElementById("separatorInput").value === " ") {
    separator.sep = " ";
    document.getElementById("separatorInput").value = "space";
  } else {
    separator.sep = document.getElementById("separatorInput").value;
  }
  if (list.indexOf(separator.sep) === -1) {
    alert("Separator not found in list!");
    clearResults();
  }
}

【问题讨论】:

  • 这个separatorSpacerator函数有什么作用? separator.sep 是在哪里定义的??
  • 一秒钟我会编辑我的帖子
  • 现在编辑了

标签: javascript arrays syntax strict


【解决方案1】:

我无法使用 sepNsLs 创建的数组。我该如何解决?

解决此问题的一种方法是返回 sepNsLs 创建的数组,例如一个元组 - return [numberArray, letterArray]; ,然后像这样使用它:

a) es6 语法:

var [numberArray, letterArray] = sepNsLs();

b) pre-es6 语法:

var split = sepNsLs(),
    numberArray = split[0],
    letterArray = split[1];

您的 addNumbers 函数也应该返回 sum - 否则,它不会产生任何有意义的结果。

虽然与问题无关,更多的是命名约定偏好问题 - 您可能想探索 Hungarian notation 及其缺点。

【讨论】:

    【解决方案2】:

    您的问题是范围之一。当您尝试访问 addNumbers 内部的 numberArray 时,它不存在。

    你有几个选择:

    1. 将每个函数中需要访问的所有变量都设为全局变量。
    2. 将所有函数包装在一个外部函数中,并将“全局”变量放入该外部范围。

    更好的选择是#2,因为您实际上不会用变量污染全局范围。你可以在外部函数的顶部声明"use strict",它将强制其中的所有内容进入严格模式。

    类似这样的:

    (function() {
        "use strict";
    
        // These are now in-scope for all the inner functions, unless redclared
        var letterArray = [], numberArray = [], separator = {sep: 0};
    
        function sepNsLs() {
           // code goes here
        }
        function addNumbers(){ 
           // code goes here
        }
        function separatorSpacerator(){ 
           //code goes here
        }
        // ...more functions and stuff
    
        // and then call...
        theFunctionThatKicksOffTheWholeProgram();
    
    }());
    

    【讨论】:

    • 好的,所以我将整个程序包装在一个外部函数中,但现在它说在加载时清除我的网页的函数未定义,我的程序现在无法运行。
    • 看不到完整的源代码,实在无法给你更完整的答案。
    • 另外,如果我创建没有包装函数的 letterArray 和 numberArray 全局变量,我单击以操作 numberArray 的按钮会继续操作新的 numberArrays。例如,一个按钮根据输入字符串是否指示来加或减,但如果我让它加,然后我改变字符串并使其减,它加然后减去所有当前和以前的数字,而不是只保留在数组。
    【解决方案3】:

    变量letterArraynumberArray 声明为函数sepNsLs 的本地变量,它们只能在该范围内访问(无论是否为严格模式)。这是一个例子:

    function foo() {
      var fooVar = 5;
      console.log(fooVar);
    }// fooVar get destroyed here
    
    function bar() {
      console.log(fooVar); // undefined because fooVar is not defined
    }
    
    foo();
    bar();

    范围通常是从左大括号 { 到与之匹配的右大括号 }。在范围内声明的任何事物都只能在该范围内使用。示例 2:

    var globalVar = 5; // belongs to the global scope
    
    function foo() {
      var fooVar = 6; // belongs to the foo scope
      
      function bar1() {
        console.log(globalVar); // will look if there is a globalVar inside the scope of bar1, if not it will look if there is globalVar in the upper scope (foo's scope), if not it will in the global scope.
        console.log(fooVar); // same here
        
        var bar1Var = 7; // belongs to bar1 scope
      }
      
      function bar2() {
        var globalVar = 9; // belongs to the bar2 scope (shadows the global globalVar but not overriding it)
        
        console.log(globalVar); // will look if there is a globalVar in this scope, if not it will look in one-up scope (foo's scope) .... untill the global scope
        
        console.log(bar1Var); // undefined because bar1Var doesn't belong to this scope, neither to foo's scope nor to the global scope
      }
      
      bar1();
      bar2();
      
      console.log(globalVar); // prints 5 not 9 because the serach will be in foo's and the global scope in that order
    }
    
    foo();
        
      
      

    您需要做的是对变量letterArraynumberArray 进行贴花,sepNsLsaddNumbers 都可以访问它们(它们都在一个范围之上)。或者从sepNsLs 返回值并将其存储在addNumbers 内的变量中。像这样:

    function sepNsLs() {
    
      // logic here
    
      return numberArray; // return the array to be used inside addNumbers
    }
    
    function addNumbers() {
    
      var arr = sepNsLs(); // store the returned value inside arr
    
      for(var i = 0; i < arr.length; ... // work with arr
    
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-03-02
      • 2017-02-16
      • 2012-11-09
      • 1970-01-01
      • 2011-03-12
      • 2013-07-31
      • 1970-01-01
      • 2011-08-26
      相关资源
      最近更新 更多