文档/教程前端【免费下载链接】en.javascript.infoModern JavaScript Tutorial项目地址https://gitcode.com/gh_mirrors/en/en.javascript.info点击查看免费下载导读在 JavaScript 中判断一个对象是否为空是对象基础章节里最常见、也最容易写出看似正确实则有坑的实用函数之一。本篇以 Modern JavaScript Tutorial 项目中 3-is-empty 练习 及其 官方参考答案 为骨架完整讲解isEmpty(obj)的 for..in 实现原理、与Object.keys()方案的取舍、undefined值带来的隐藏陷阱以及如何借助仓库内自带的 Mocha 测试用例验证函数正确性。读完本文你既能写出健壮的对象判空函数也能理解遍历对象属性这一核心操作在真实场景中的边界。练习背景需求与期望行为该练习位于1-js/04-object-basics/01-object对象基础章节下编号为3-is-empty难度标记为importance: 5五级中最重要的一档。原题要求编写函数isEmpty(obj)当对象没有属性时返回true否则返回false。题目给出了明确的期望行为示例let schedule {}; alert( isEmpty(schedule) ); // true schedule[8:30] get up; alert( isEmpty(schedule) ); // false这里特别值得注意schedule[8:30] get up使用了方括号语法square bracket notation写入一个含特殊字符:的多词属性名。这正是对象章节前文强调的能力——点号语法schedule.8:30无法解析而方括号可以接受任意字符串键。判空函数必须对这种键同样生效它关心的只是对象里有没有属性而不是属性名长什么样。官方答案for..in 循环的精妙一行逻辑练习的 官方参考答案 只有一句话但背后是完整的算法遍历对象如果至少有一个属性就立即return false。对应的完整实现位于仓库的测试视图文件 solution.jsfunction isEmpty(obj) { for (let key in obj) { // if the loop has started, there is a property return false; } return true; }逐行拆解执行过程for (let key in obj)启动for..in循环遍历对象的所有可枚举属性键property keys。声明在循环头部的let key在每次迭代中绑定当前键。循环体第一行return false;只要循环第一次进入迭代就说明至少存在一个属性此时立即返回false——提前终止遍历无需再看后续属性。若整个循环一次都没进入对象没有任何可枚举属性自然落到return true;。这个实现的巧妙之处在于不需要计数、不需要临时数组、不需要显式比较直接用循环是否开始作为判空信号时间复杂度最好情况下为 O(1)非空对象或 O(n)空对象为 O(0)。与对象章节的知识衔接for..in的语法与语义在章节正文 article.md 中有完整铺垫for (key in object) { // executes the body for each key among object properties }该章节同时提醒了两个与判空直接相关的知识点属性存在性测试key in obj运算符可以判断属性是否存在但isEmpty需要的是是否存在任意属性因此必须靠循环而非单个in查询。整数键排序for..in会先按升序输出整数键如49、1再按创建顺序输出其他键。这对判空结果没有影响——只要有任何键无论顺序如何循环都会进入——但理解这一点有助于避免在顺序敏感场景误用对象遍历。仓库自带的测试用例用 Mocha 验证判空逻辑为了确保答案正确仓库为练习配置了基于 Mocha 的测试文件 test.jsdescribe(isEmpty, function() { it(returns true for an empty object, function() { assert.isTrue(isEmpty({})); }); it(returns false if a property exists, function() { assert.isFalse(isEmpty({ anything: false })); }); });两个用例分别覆盖判空函数的两条关键路径用例输入断言覆盖的代码路径空对象{}assert.isTruefor..in一次未进入返回true含属性对象{ anything: false }assert.isFalse循环首次迭代即return false注意第二个用例刻意使用anything: false作为属性值——值本身是false假值但函数依然必须返回false对象不为空。这证明isEmpty判断的是键是否存在与属性的值是什么完全无关。这是对象判空与判断值真假类函数如!obj、Boolean(obj)的本质区别。深入对比isEmpty与Object.keys().length 0for..in并非唯一实现方案。仓库的姊妹练习 count-properties 展示了另一种常见思路其 参考答案 为function count(obj) { return Object.keys(obj).length; }由此可推出等价的判空写法function isEmpty(obj) { return Object.keys(obj).length 0; }两种方案在绝大多数场景下结果一致但存在一个关键差异正是官方答案选择for..in的原因之一for..in遍历的是包括继承来的可枚举属性enumerable properties from the prototype chainObject.keys()只返回对象自身的可枚举属性键。例如let animal { eats: true }; let rabbit Object.create(animal); // rabbit 的原型是 animal isEmpty(rabbit); // for..in 版本 → false继承的 eats 也能让循环开始 Object.keys(rabbit).length; // 0 → 认为空哪种行为正确取决于语义如果题目讨论的是对象本身是否有数据Object.keys更精确如果讨论的是遍历时能否看到任何键例如克隆、序列化、for..in深拷贝场景for..in才是更贴近实际遍历行为的选择。官方在基础章节选用for..in也让学习者提前熟悉这一遍历原语。补充Object.keys等对象方法属于Object静态方法而非原型方法在 08-prototypes 章节的 prototype-methods 中有专门讨论这也是它不会受原型链影响的原因。隐藏陷阱值为undefined的属性算不算空对象章节正文专门讨论过in运算符与undefined比较的区别见 article.md 的 Property existence testlet obj { test: undefined }; alert( obj.test ); // undefined看起来像没有该属性 alert( test in obj ); // true属性确实存在把这个陷阱映射到判空函数上一个属性存在但值为undefined的对象isEmpty必须返回false。好在基于for..in的实现天然正确——只要键存在循环就会进入并返回false不管值是什么let obj { test: undefined }; isEmpty(obj); // falsefor..in 版本正确反过来如果误用比较值的方式例如JSON.stringify(obj) {}、Object.values(obj).length 0、或检查obj[key] undefined则可能把这种对象误判为空。这是本练习刻意用importance: 5强调的边界之一判空的对象是键的集合键的存在性与值的类型无关。实战应用场景与完整示例对象判空在实际代码中常见于以下场景表单/配置校验判断用户是否提交了任何字段缓存与存储判断判断一个集合容器是否需要持久化或清理接口响应判断判断后端返回的对象是否携带数据初始化状态判断如题目中的schedule日程表——从空到有第一条安排即从空变为非空。结合题目场景的一个完整可运行示例可在浏览器控制台或 Node.js 中直接执行function isEmpty(obj) { for (let key in obj) { return false; } return true; } // —— 空对象 —— let schedule {}; console.log(isEmpty(schedule)); // true // —— 用方括号写入含冒号的时间键 —— schedule[8:30] get up; console.log(isEmpty(schedule)); // false // —— 值为假值/undefined 的对象 —— console.log(isEmpty({ anything: false })); // false console.log(isEmpty({ test: undefined })); // false键存在即非空 // —— 继承属性 vs 自身属性 —— let proto { inherited: true }; let obj Object.create(proto); console.log(isEmpty(obj)); // falsefor..in 会看到继承键小结官方推荐的isEmpty实现基于for..in循环一旦开始迭代即返回false否则返回true核心代码仅需 6 行逻辑在 solution.js 中可查该函数关注的是对象是否存在可枚举属性键与属性值无关——值为false、undefined甚至null的对象都不是空对象相比Object.keys(obj).length 0for..in版本会统计原型链上的可枚举属性两种方案适用语义不同需按场景选择仓库自带的 test.js 提供了两个 Mocha 用例分别覆盖空对象与含假值属性的对象可直接作为回归测试使用对象的基础语法方括号、in运算符、for..in遍历与整数键排序详见 对象章节正文本篇练习是其最直接的综合应用之一。赞分享文档/教程前端【免费下载链接】en.javascript.infoModern JavaScript Tutorial项目地址https://gitcode.com/gh_mirrors/en/en.javascript.info点击查看免费下载相关推荐JavaScript 检查对象是否为空isEmpty 函数的正确实现与边界情况JavaScript 检查对象是否为空isEmpty 函数的正确实现与边界情况 本篇文章围绕 Modern JavaScript Tutorial 中 Ch文档/教程前端Modern JavaScript Tutorial 实战用 for..in 遍历 salaries 对象并完成属性求和Modern JavaScript Tutorial 实战用 for..in 遍历 salaries 对象并完成属性求和 本篇文章以 Modern JavaS文档/教程前端打造多进度条应用BProgress 1.1新特性深度探索打造多进度条应用BProgress 1.1新特性深度探索 BProgress 是一款轻量级、可定制的进度条工具旨在提升用户体验。作为NProgress的现代上一篇崩坏星穹铁道终极自动化助手三月七小助手完整使用指南下一篇为什么专业开发者都选择chinese-address-generator实战深度解析创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考