如何检查JavaScript中的对象属性是否未定义?
当前回答
在《探索JavaScript中的空和未定义的深渊》一文中,我看到Undercore.js等框架使用了这个函数:
function isUndefined(obj){
return obj === void 0;
}
其他回答
我很惊讶我还没有看到这个建议,但它比使用typeof测试更具特异性。如果您需要知道对象属性是用undefined初始化的还是从未初始化过,请使用Object.getOwnPropertyDescriptor():
// to test someObject.someProperty
var descriptor = Object.getOwnPropertyDescriptor(someObject, 'someProperty');
if (typeof descriptor === 'undefined') {
// was never initialized
} else if (typeof descriptor.value === 'undefined') {
if (descriptor.get || descriptor.set) {
// is an accessor property, defined via getter and setter
} else {
// is initialized with `undefined`
}
} else {
// is initialized with some other value
}
这是什么意思:“未定义的对象属性”?
实际上,这可能意味着两件截然不同的事情!首先,它可以表示对象中从未定义过的属性,其次,它可以指具有未定义值的属性。让我们看一下这段代码:
var o = { a: undefined }
o.a是否未定义?对其值未定义。是否未定义o.b?当然根本没有属性“b”!好了,现在看看不同的方法在两种情况下的表现:
typeof o.a == 'undefined' // true
typeof o.b == 'undefined' // true
o.a === undefined // true
o.b === undefined // true
'a' in o // true
'b' in o // false
我们可以清楚地看到,obj.prop==“undefined”和obj.prop==undefineed的类型是等价的,它们不能区分这些不同的情况。obj中的“prop”可以检测属性根本没有定义并且没有注意可能未定义的属性值的情况。
那该怎么办?
1) 您想知道一个属性是由第一个含义还是第二个含义定义的(最典型的情况)。
obj.prop === undefined // IMHO, see "final fight" below
2) 您只想知道对象是否具有某些属性,而不关心其值。
'prop' in obj
笔记:
不能同时检查对象及其属性。例如,此x.a==未定义或此类型的x.a=='未定义'引发ReferenceError:如果未定义x,则未定义x。变量undefined是一个全局变量(所以实际上它在浏览器中是window.unded)。自ECMAScript第1版以来,它一直受到支持,自ECMASript 5以来,它是只读的。因此,在现代浏览器中,它不能被重新定义为真实,因为许多作者喜欢用它来吓唬我们,但这对于旧浏览器来说仍然是真实的。
最后一战:obj.prop==未定义vs obj.prop类型==“未定义”
obj.prop的加号==未定义:
它短了一点,看起来更漂亮一点如果您拼错了undefined,JavaScript引擎会给您一个错误
obj.prop的最小值==未定义:
在旧浏览器中可以重写undefined
obj.prop类型的加号==“undefined”:
它真的很普遍!它可以在新旧浏览器中使用。
obj.prop类型的最小值==“undefined”:
这里的“undefined”(拼写错误)只是一个字符串常量,因此如果您像我刚才那样拼写错误,JavaScript引擎将无法帮助您。
更新(针对服务器端JavaScript):
Node.js支持未定义为global.undefined的全局变量(也可以在没有“global”前缀的情况下使用)。我不知道服务器端JavaScript的其他实现。
检查是否存在密钥的一种简单方法是:
if (key in obj) {
// Do something
} else {
// Create key
}
const obj = {
0: 'abc',
1: 'def'
}
const hasZero = 0 in obj
console.log(hasZero) // true
简单地说,JavaScript中没有定义的任何东西都是未定义的,无论它是Object/Array中的属性还是只是一个简单的变量。。。
JavaScript具有类型of,因此很容易检测未定义的变量。
只需检查typeof whatever==“undefined”,就会返回布尔值。
这就是AngularJs v.1x中著名的函数isUndefined()的编写方式:
function isUndefined(value) {return typeof value === 'undefined';}
因此,当您看到函数接收到一个值时,如果定义了该值,它将返回false,否则对于未定义的值,返回true。
让我们看看传递值时会得到什么结果,包括如下所示的对象财产,这是我们拥有的变量列表:
var stackoverflow = {};
stackoverflow.javascipt = 'javascript';
var today;
var self = this;
var num = 8;
var list = [1, 2, 3, 4, 5];
var y = null;
我们如下所示进行检查,您可以在他们面前看到结果作为评论:
isUndefined(stackoverflow); //false
isUndefined(stackoverflow.javascipt); //false
isUndefined(today); //true
isUndefined(self); //false
isUndefined(num); //false
isUndefined(list); //false
isUndefined(y); //false
isUndefined(stackoverflow.java); //true
isUndefined(stackoverflow.php); //true
isUndefined(stackoverflow && stackoverflow.css); //true
正如您所看到的,我们可以在代码中使用类似的东西来检查任何情况,正如前面所提到的,您可以在您的代码中简单地使用typeof,但是如果您反复使用它,请创建一个像我共享的angular sample这样的函数,并将其作为以下DRY代码模式继续重用。
还有一件事,要检查真实应用程序中对象的属性,即使您不确定该对象是否存在,也要先检查对象是否存在。
如果您检查对象的属性而该对象不存在,将抛出错误并停止整个应用程序的运行。
isUndefined(x.css);
VM808:2 Uncaught ReferenceError: x is not defined(…)
如此简单,您可以像下面这样包装在if语句中:
if(typeof x !== 'undefined') {
//do something
}
也等于在Angular 1.x中定义的。。。
function isDefined(value) {return typeof value !== 'undefined';}
其他javascript框架(如下划线)也有类似的定义检查,但如果您尚未使用任何框架,我建议您使用typeof。
我还从MDN中添加了这一部分,它提供了关于typeof、undefined和void(0)的有用信息。
严格相等和未定义您可以使用undefined和严格相等和不相等运算符来确定变量是否具有一个值。在以下代码中,未定义变量xif语句的计算结果为true。
var x;
if (x === undefined) {
// these statements execute
}
else {
// these statements do not execute
}
注意:严格等式运算符而不是标准等式这里必须使用运算符,因为x==undefined还检查x为空,而严格相等不为空。null不等于未定义。有关详细信息,请参见比较运算符。
运算符类型和未定义或者,可以使用typeof:
var x;
if (typeof x === 'undefined') {
// these statements execute
}
使用typeof的一个原因是,如果尚未声明变量。
// x has not been declared before
if (typeof x === 'undefined') { // evaluates to true without errors
// these statements execute
}
if (x === undefined) { // throws a ReferenceError
}
然而,这种技术应该避免。JavaScript是静态作用域语言,因此知道是否声明了变量可以通过查看它是否在封闭上下文中声明来读取。这个唯一的例外是全局范围,但全局范围与全局对象,因此检查全局上下文可以通过检查全局对象(例如,使用in运算符)。
无效运算符和未定义void运算符是第三种选择。
var x;
if (x === void 0) {
// these statements execute
}
// y has not been declared before
if (y === void 0) {
// throws a ReferenceError (in contrast to `typeof`)
}
更多>此处
if (somevariable == undefined) {
alert('the variable is not defined!');
}
您也可以将其转换为函数,如下所示:
function isset(varname){
return(typeof(window[varname]) != 'undefined');
}