检查多个变量的最佳方法是什么?

时间:2012-06-30 13:47:30

标签: javascript variables error-handling

这更像是一般性实践问题。

我正在使用的语言是Javascript。我有一个函数正在获取一个包含许多变量的对象(好吧,只有10个变量)。确保此函数获取所有必需变量并且它们都已设置的最佳方法是什么?

我知道,我知道,为什么不使用if声明。这是if语句中的一小部分!随着我成长为程序员,我知道这可能不是最好的方法。我正在寻找一条捷径。如何检查存在的大量变量和非空值?

4 个答案:

答案 0 :(得分:1)

这是处理验证的一种非常巧妙的方法,我通常在检查表单输入中的必填字段时使用它。

var theObj = { /* object loaded from server */ }

function checkTheObj(testObj)
{
  var requiredKeys = ['key1', 'key2', 'key3'];
  for(var keyPos = 0; keyPos < requiredKeys.length; keyPos++)
  {
    if(typeof(testObj[requiredKeys[keyPos]]) == 'undefined')
    {
      return false;
    }
  }
  return true;
}

if(checkTheObj(theObj))
{
  //do stuff
}

你当然可以调整它来返回或抛出一个异常,告诉第一个丢失的字段(或使用内部数组返回所有缺失字段的列表)。

答案 1 :(得分:1)

function objectHas(obj, properties) {
    var len = properties.length
    for (var i=0; i<len; i++) {
        if (i in properties) {
            if((!obj.hasOwnProperty(properties[i])) || (!obj.propertyIsEnumerable(properties[i]))) {
                return false;
            }
        }
    }
    return true;
}

用法:

if(objectHas(user, ["email", "password", "phone"])) {
    console.log("awesome");
}

这很简单,但是做到了。

编辑:在一个理想的世界中,您可以扩展Object原型以获得更简洁的语法,例如 if(object.has([“a”,“b”,“c”])) ,但显然扩展了Object原型是incarnation of evil,所以函数必须这样做:)

答案 2 :(得分:1)

首先,您需要提高对这些语言的理解并学习正确的术语。

  1. There is no (single) language named "Javascript" at all.您隐式在这里使用几种语言(取决于运行时环境),所有这些都是ECMAScript实现,而一个是{ {3}}。
  2. 对象没有变量,它有属性不是:keys)。全局代码,功能代码和eval代码可以包含变量;这是不同(但相似)的概念。
  3. 该函数未获取对象,正在传递对对象的引用作为参数
  4. 作为程序员,您应该已经知道可以循环执行重复性任务; ECMAScript实现中的关联语句是Netscape/Mozilla JavaScript (in Mozilla-based software like Firefox)。所以你必须写几个if语句。

    您可以通过两种方式访问​​for, for-in, while and do,其中property属性名称

    1. 点符号:obj.property
    2. 括号表示法:obj["property"]
    3. 如果属性名称是标识符,则第二个等同于第一个,即它是否遵循某些命名规则。如果属性名称不是标识符,或者它是可变的,则必须使用第二个。这也表明所有属性名称是字符串值。因此,您可以将属性的名称存储为变量或其他属性的值,然后访问属性访问器中的变量或属性。在下文中,属性名称(property)存储在变量中并使用:

      var propertyName = "property";
      obj[propertyName]
      

      将它与循环结合使用可以迭代对象的某些属性。遗憾的是,到目前为止提供的解决方案在两个方面存在缺陷:for - in语句仅针对对象的可枚举属性进行迭代,并且在任意订单。此外,它还会迭代可枚举的继承的属性(这就是为什么一个解决方案需要hasOwnProperty()调用)。

      一种简单,可靠且有效的方法,只按定义的顺序迭代对象的某些属性,如下所示:

      var propertyNames = ['name1', 'name2', 'name3'];
      for (var i = 0, len = propertyNames.length; i < len; ++i)
      {
        /* … */ myObject[propertyNames[i]] /* … */
      }
      

      这是有效的,因为propertyNames引用了一个Array实例,它封装了一个数组数据结构。数组的元素是Array实例的属性,其整数索引从0到65535(2 32 -1)。因为索引不是标识符(它们以十进制数字开头),所以你必须使用括号属性访问器语法(有些人误解了这一点,并将所有ECMAScript对象称为“数组”,甚至将它们称为“关联数组”和{{1 “数组运算符”)。因此,[…]计算每次迭代中数组元素的值,因为propertyNames[i]每次增加1。因此,i在每个循环中访问具有该名称的属性。

      现在,要确定属性是否已设置,您需要定义这意味着什么。访问不存在的属性会导致myObject[propertyNames[i]]值(不是错误)。但是,现有属性也可能具有undefined值作为其值。

      如果“未设置”表示该对象没有该属性(但可以继承它),那么您应该使用Mahn解决方案中使用的undefined

      如果“未设置”表示该对象没有该属性且未继承该属性,则应使用hasOwnProperty()运算符,前提是该对象 a { {3}}(因为properties of an object host object):

      in

      如果“未设置”表示对象具有或继承该属性,但该属性具有if (propertyNames[i] in obj) 值,或者该对象既没有也没有继承该属性,那么您应该使用{{1}在Bob Davies和aetaur的解决方案中使用的运算符(但后者使用the in operator的方法原样不太兼容;该方法在ECMAScript Edition 5之前未指定,并且在IE / JScript中不可用&lt; 9 )。

      ECMAScript Edition 5.x有第三个选项,is not specified for them(尽管名称)返回对undefined实例的引用,该实例包含所有未继承属性的名称。参数:

      typeof

      如果它不是内置的,那么模仿Array是个好主意,因为这种算法经常有用。

答案 3 :(得分:0)

如果variableNameList中所有变量(所需变量名称列表)在对象o中设置,则此表达式返回true:

variableNameList.every(function(varName){ return typeof o[varName] !== 'undefined'; });

您可以使用下划线_.all功能代替原生every,并使用下划线_.isUndefined代替typeof ...