JavaScript fetch读取JSON后数组元素无法单独访问打印问题
问题产生原因
核心原因是fetch属于异步非阻塞Web API,代码执行到fetch逻辑时不会等待请求返回、数据处理完成,而是会直接继续执行后续的同步代码。你遇到的现象具体成因:
- 代码执行到
console.log(word)、console.log(word[0])和函数外的console.log(word)时,fetch请求还没完成,填充word数组的逻辑还没执行,此时word还是空数组。 - 浏览器控制台对引用类型(数组、对象)的打印是懒解析机制:打印时只记录对象的引用,等你在控制台手动展开数组查看内容时,异步请求早就完成、数组已经被填充完毕,所以你展开后能看到元素。
- 而
console.log(word[0])是立刻读取执行当下的索引0值,当时数组为空,因此输出undefined。 - 额外问题:你的代码中没有定义
our_language变量,直接使用会抛出引用错误。
控制台异常运行效果参考:
可行修复方案
所有依赖fetch返回数据的逻辑,必须放到异步流程的回调中执行,不要在异步操作外部直接操作待填充的数组。
方案1:使用.then链式调用处理
把所有数组操作、打印逻辑放到数据填充完成的回调内部即可:
// 先定义要提取的目标语言 const our_language = "French"; const word = []; function readJson() { fetch('./data.json') .then(response => response.json()) .then(data => { // 数据填充 for (let index = 0; index < data.Sheet1.length; index++) { word.push(data.Sheet1[index][our_language]); } // 所有需要操作word数组的逻辑都放在填充完成后 console.log(word); // 输出 ["Bonjour", "mon", "ami"] console.log(word[0]); // 输出 Bonjour console.log(word[1]); // 输出 mon }) .catch(err => console.error("JSON读取失败:", err)); } readJson(); // 不要在此处写操作word数组的代码,执行到这里时异步请求还未完成
方案2:使用async/await语法(更简洁易读)
用async/await改写异步逻辑,更符合同步代码的书写习惯,还可以直接封装成按语言取词汇的通用函数:
async function getWordList(language) { try { const res = await fetch('./data.json'); const data = await res.json(); // 直接用map生成对应语言的词汇数组,无需手动循环push const wordList = data.Sheet1.map(item => item[language]); console.log(wordList); console.log(wordList[0]); return wordList; } catch (err) { console.error("数据读取失败:", err); return []; } } // 调用示例:获取法语词汇 getWordList("French");
注意:JS的事件循环机制会优先执行所有同步代码,再执行异步队列中的回调,任何需要等待网络请求、IO操作返回结果的逻辑,都不能放在同步代码流中直接调用。
内容的提问来源于stack exchange,提问作者Rony Cohen
相关产品推荐
相关产品推荐

