“对象为空——还是不为空?” 解决JavaScript开发者的永恒难题
\n\n想象一下:你正在编写一个应用程序,从API收到响应,你需要知道——数据是否已到达?还是对象为空,需要向用户显示占位符?或者你在处理表单,需要检查用户是否至少填写了一个字段?每个写JavaScript的人都会遇到这种令人头疼的情况。
\n\n看起来,这能有多难?if (obj === {})——不就搞定了?可惜,不行。在JavaScript中,两个对象,即使内容完全相同,也永远不会相等,除非它们是内存中的同一个对象。检查JavaScript空对象——这是一个在Stack Overflow上积累了数千次浏览并催生了大量解决方案的任务。
在本文中,我们将探讨5种可靠的方法来判断你面前的是否是一个空对象。从经典方法到现代方法,从快速方法到安全方法。开始吧!
\n\nJavaScript中的“空对象”是什么意思?
\n\n在深入代码之前,让我们先统一一下术语。JavaScript中的空对象是指没有自身可枚举属性的对象。也就是说,{}是空的。而{ name: "Alice" }则不是。
一个重要细节:任何对象都有原型(Object.prototype),因此它也有继承的属性(例如,toString、hasOwnProperty)。这些我们不关心。我们只检查我们自己添加的属性。
另一个陷阱是null。如果变量等于null或undefined,我们甚至无法调用它的方法。因此,首先要检查对象是否存在。
方法1:Object.keys()——黄金标准
\n\n现代JavaScript中最流行且推荐的方法。Object.keys()方法返回对象自身可枚举属性的数组。如果数组为空——对象为空。
function isEmpty(obj) {\n return Object.keys(obj).length === 0;\n}\n\n// 使用示例\nconsole.log(isEmpty({})); // true\nconsole.log(isEmpty({a: 1})); // false\nconsole.log(isEmpty({name: 'John', age: 30})); // false\n\n为什么这样有效?Object.keys()会忽略继承的属性,只返回对象自身的属性。使用Object.keys()检查对象是否为空——这是干净、可读且快速的代码。
重要提示:此方法不检查传入的值是否为对象。如果传入字符串或数字,它会返回一个空数组,我们会错误地认为对象为空。因此,为了安全起见,我们添加类型检查:
\n\nfunction isEmptySafe(obj) {\n return obj && typeof obj === 'object' && Object.keys(obj).length === 0;\n}\n\nconsole.log(isEmptySafe('hello')); // false(字符串不是对象)\nconsole.log(isEmptySafe(null)); // false\nconsole.log(isEmptySafe({})); // true\n\n方法2:JSON.stringify()——出人意料但有效
\n\n有时程序员开玩笑地称这种方法为“拐杖”,但它确实有效。思路很简单:将对象序列化为JSON字符串,然后将其与'{}'进行比较。
function isEmptyJSON(obj) {\n return JSON.stringify(obj) === '{}';\n}\n\nconsole.log(isEmptyJSON({})); // true\nconsole.log(isEmptyJSON({key: 'val'})); // false\n\n为什么这种方法不理想?首先,JSON.stringify()会忽略函数、undefined和符号。如果对象有一个值为undefined的属性,它会在序列化时消失,对象会被认为为空,尽管它实际上有一个键。
const obj = { a: undefined };\nconsole.log(isEmptyJSON(obj)); // true——但应该是false!\n\n其