JavaScript使用HTML5 FileReader读取文件存数组遇问题求助
解决JavaScript读取TXT文件后无法存入数组的问题
嘿,我看了你的代码,其实readFile函数本身没毛病——控制台能正常打印出解析后的数字,就说明data是有值的,你遇到的问题核心是异步操作的时机问题,说不定还有点对作用域的小误解,咱们一步步来搞定:
为啥会出问题?
- FileReader是异步干活的:
reader.readAsText(file)不会马上把文件内容给你,它得等文件读完了,才会触发onload回调函数。要是你在回调外面去碰content数组,那时候文件还没读完呢,数组自然是空的。 - 你注释里说
data未定义,但console.log(JSON.parse(data))能正常打印,这大概率是你之前写代码时的笔误(比如不小心把变量名写错了),但咱们重点解决你后续没法用数组内容的问题。
修正后的代码方案
方案1:直接在回调里处理内容(最简单直接)
既然文件内容只有在onload回调触发时才准备好,那所有要用到这个内容的逻辑,都得放在这个回调里:
fileBtn.addEventListener("change", function() { var content = []; var file = fileBtn.files[0]; readFile(file, function(data) { const parsedData = JSON.parse(data); console.log(parsedData); // 正常打印1 content.push(parsedData); // 所有需要用content的逻辑都放这儿! console.log("现在数组里有:", content); // 这里能看到[1] // 比如调用你自己的函数去处理这个数组 doSomethingWithContent(content); }); }); function readFile(file, f) { var reader = new FileReader(); reader.onload = function(evt) { f(evt.target.result); }; reader.readAsText(file); } // 举个例子,处理数组的函数 function doSomethingWithContent(arr) { console.log("把数组里的数翻倍:", arr.map(item => item * 2)); // 输出[2] }
方案2:用Promise封装(适合复杂场景,代码更清爽)
如果你的业务逻辑比较复杂,不想把所有代码都嵌套在回调里,可以把readFile改成返回Promise的形式,用async/await来写,看起来更像同步代码:
fileBtn.addEventListener("change", async function() { var content = []; var file = fileBtn.files[0]; try { const data = await readFile(file); const parsedData = JSON.parse(data); content.push(parsedData); console.log("现在数组里有:", content); // 后续逻辑直接往下写就行,不用嵌套回调啦 } catch (err) { console.error("读取文件出错啦:", err); } }); // 改成返回Promise的readFile function readFile(file) { return new Promise((resolve, reject) => { var reader = new FileReader(); reader.onload = function(evt) { resolve(evt.target.result); }; reader.onerror = function(err) { reject(err); // 加上错误处理更稳妥 }; reader.readAsText(file); }); }
几个小提醒
- 千万别在异步回调外面直接用依赖异步结果的变量(比如你的
content),因为那时候异步操作还没做完,变量值根本没更新。 - 你的TXT文件里只有
"1",其实不用JSON.parse,直接用Number(data)转换更靠谱——万一文件里不小心多了个空格,JSON解析会报错,用Number就不会有这问题。
内容的提问来源于stack exchange,提问作者Ptero
相关产品推荐
相关产品推荐

