我的csv数据如下所示:
标题1,heading2,heading3,heading4,heading5,value1_1,value2_1,value3_1,value4_1,value5_1,value1_2,value2_2,value3_2,value4_2,value5_2 ....
如何使用Javascript读取此数据并转换为这样的数组?:
[heading1:value1_1,heading2:value2_1,heading3:value3_1,heading4 :value4_1,heading5:value5_1],[heading1:value1_2, heading2:value2_2,heading3:value3_2,heading4:value4_2,heading5 :value5_2] ....
我尝试过这段代码,但没有运气!:
<script type="text/javascript">
var allText =[];
var allTextLines = [];
var Lines = [];
var txtFile = new XMLHttpRequest();
txtFile.open("GET", "file://d:/data.txt", true);
txtFile.onreadystatechange = function()
{
allText = txtFile.responseText;
allTextLines = allText.split(/\r\n|\n/);
};
document.write(allTextLines);<br>
document.write(allText);<br>
document.write(txtFile);<br>
</script>
答案 0 :(得分:188)
无需自己编写......
jQuery-CSV库有一个名为$.csv.toObjects(csv)
的函数,可以自动执行映射。
注意:该库旨在处理符合RFC 4180的任何CSV数据,包括大多数“简单”解决方案忽略的所有令人讨厌的边缘情况。
就像@Blazemonger已经说过的那样,首先你需要添加换行符以使数据有效CSV。
使用以下数据集:
heading1,heading2,heading3,heading4,heading5
value1_1,value2_1,value3_1,value4_1,value5_1
value1_2,value2_2,value3_2,value4_2,value5_2
使用代码:
var data = $.csv.toObjects(csv):
“数据”中保存的输出将为:
[
{ heading1:"value1_1",heading2:"value2_1",heading3:"value3_1",heading4:"value4_1",heading5:"value5_1" }
{ heading1:"value1_2",heading2:"value2_2",heading3:"value3_2",heading4:"value4_2",heading5:"value5_2" }
]
注意:从技术上讲,编写键值映射的方式是无效的JavaScript。包含键值对的对象应该用括号括起来。
如果您想亲自尝试一下,我建议您查看“toObjects()”标签下的Basic Usage Demonstration。
免责声明:我是jQuery-CSV的原作者。
<强>更新强>
编辑使用op提供的数据集,并包含一个指向演示的链接,可以测试数据的有效性。
<强> UPDATE2:强>
由于关闭了Google Code。 jquery-csv has moved to GitHub
答案 1 :(得分:104)
注意:在我提醒有关CSV文件中可能出现的所有“特殊情况”(例如转义引号)之前,我编制了此解决方案。对于那些想要快速而又肮脏的人,我会留下我的答案,但我建议Evan's answer来提高准确性。
当您的data.txt
文件是一长串逗号分隔的条目而没有换行符时,此代码将起作用:
data.txt中:
heading1,heading2,heading3,heading4,heading5,value1_1,...,value5_2
的javascript:
$(document).ready(function() {
$.ajax({
type: "GET",
url: "data.txt",
dataType: "text",
success: function(data) {processData(data);}
});
});
function processData(allText) {
var record_num = 5; // or however many elements there are in each row
var allTextLines = allText.split(/\r\n|\n/);
var entries = allTextLines[0].split(',');
var lines = [];
var headings = entries.splice(0,record_num);
while (entries.length>0) {
var tarr = [];
for (var j=0; j<record_num; j++) {
tarr.push(headings[j]+":"+entries.shift());
}
lines.push(tarr);
}
// alert(lines);
}
以下代码适用于“真实”的CSV文件,每个记录集之间都有换行符:
data.txt中:
heading1,heading2,heading3,heading4,heading5
value1_1,value2_1,value3_1,value4_1,value5_1
value1_2,value2_2,value3_2,value4_2,value5_2
的javascript:
$(document).ready(function() {
$.ajax({
type: "GET",
url: "data.txt",
dataType: "text",
success: function(data) {processData(data);}
});
});
function processData(allText) {
var allTextLines = allText.split(/\r\n|\n/);
var headers = allTextLines[0].split(',');
var lines = [];
for (var i=1; i<allTextLines.length; i++) {
var data = allTextLines[i].split(',');
if (data.length == headers.length) {
var tarr = [];
for (var j=0; j<headers.length; j++) {
tarr.push(headers[j]+":"+data[j]);
}
lines.push(tarr);
}
}
// alert(lines);
}
答案 2 :(得分:61)
不要在逗号上拆分 - 它对大多数CSV文件都不起作用,而且这个问题对于提问者的输入数据适用于每个人的看法太多了。解析CSV有点可怕,因为没有真正的官方标准,许多分隔的文本编写者不会考虑边缘情况。
这个问题很陈旧,但我相信现在有Papa Parse可用的更好的解决方案。这是我在贡献者的帮助下编写的一个库,用于解析CSV文本或文件。它是我所知道的唯一支持文件千兆字节大小的JS库。它还可以优雅地处理格式错误的输入。
1分钟内解析1 GB文件:
(更新:使用Papa Parse 4,同样的文件在Firefox中只用了大约30秒。对于浏览器,Papa Parse 4现在是the fastest known CSV parser。)
解析文本非常简单:
var data = Papa.parse(csvString);
解析文件也很简单:
Papa.parse(file, {
complete: function(results) {
console.log(results);
}
});
流式文件类似(这是流式传输远程文件的示例):
Papa.parse("http://example.com/bigfoo.csv", {
download: true,
step: function(row) {
console.log("Row:", row.data);
},
complete: function() {
console.log("All done!");
}
});
如果您的网页在解析期间锁定,Papa可以使用网络工作人员来保持您的网站被动反应。
如果存在标题行,Papa可以自动检测分隔符并将值与标题列匹配。它还可以将数值转换为实际数字类型。它适当地解析换行符和引号以及其他奇怪的情况,甚至可以尽可能稳健地处理格式错误的输入。我从现有的库中汲取灵感来制作Papa,这是其他JS实现的道具。
答案 3 :(得分:7)
我正在使用 d3.js 来解析csv文件。非常好用。 这是docs。
步骤:
使用Es6;
import { csv } from 'd3-request';
import url from 'path/to/data.csv';
csv(url, function(err, data) {
console.log(data);
})
有关详情,请参阅docs。
更新 - 不推荐使用d3-request。你可以使用d3-fetch
答案 4 :(得分:3)
这是一个解析CSV数据的JavaScript函数,用于记录引号内的逗号。
// Parse a CSV row, accounting for commas inside quotes
function parse(row){
var insideQuote = false,
entries = [],
entry = [];
row.split('').forEach(function (character) {
if(character === '"') {
insideQuote = !insideQuote;
} else {
if(character == "," && !insideQuote) {
entries.push(entry.join(''));
entry = [];
} else {
entry.push(character);
}
}
});
entries.push(entry.join(''));
return entries;
}
使用该函数解析看起来像这样的CSV文件的示例:
"foo, the column",bar
2,3
"4, the value",5
进入数组:
// csv could contain the content read from a csv file
var csv = '"foo, the column",bar\n2,3\n"4, the value",5',
// Split the input into lines
lines = csv.split('\n'),
// Extract column names from the first line
columnNamesLine = lines[0],
columnNames = parse(columnNamesLine),
// Extract data from subsequent lines
dataLines = lines.slice(1),
data = dataLines.map(parse);
// Prints ["foo, the column","bar"]
console.log(JSON.stringify(columnNames));
// Prints [["2","3"],["4, the value","5"]]
console.log(JSON.stringify(data));
以下是如何将数据转换为对象,例如D3's csv parser(这是一个可靠的第三方解决方案):
var dataObjects = data.map(function (arr) {
var dataObject = {};
columnNames.forEach(function(columnName, i){
dataObject[columnName] = arr[i];
});
return dataObject;
});
// Prints [{"foo":"2","bar":"3"},{"foo":"4","bar":"5"}]
console.log(JSON.stringify(dataObjects));
这是working fiddle of this code。
享受! - Curran
答案 5 :(得分:1)
我通过在这里将1更改为0来实现此目的:
for (var i=1; i<allTextLines.length; i++) {
更改为
for (var i=0; i<allTextLines.length; i++) {
它将计算一个连续行的文件,其allTextLines.length为1.因此,如果循环从1开始并且只要它小于1就运行,它就永远不会运行。因此空白警报框。
答案 6 :(得分:1)
以下是将外部CSV读入Javascript 的另一种方式(使用jQuery)。
它有点啰嗦,但我觉得通过将数据读入阵列,您可以完全按照流程进行操作,并且可以轻松排除故障。
可以帮助别人。
数据文件示例:
Time,data1,data2,data2
08/11/2015 07:30:16,602,0.009,321
以下是代码:
$(document).ready(function() {
// AJAX in the data file
$.ajax({
type: "GET",
url: "data.csv",
dataType: "text",
success: function(data) {processData(data);}
});
// Let's process the data from the data file
function processData(data) {
var lines = data.split(/\r\n|\n/);
//Set up the data arrays
var time = [];
var data1 = [];
var data2 = [];
var data3 = [];
var headings = lines[0].split(','); // Splice up the first row to get the headings
for (var j=1; j<lines.length; j++) {
var values = lines[j].split(','); // Split up the comma seperated values
// We read the key,1st, 2nd and 3rd rows
time.push(values[0]); // Read in as string
// Recommended to read in as float, since we'll be doing some operations on this later.
data1.push(parseFloat(values[1]));
data2.push(parseFloat(values[2]));
data3.push(parseFloat(values[3]));
}
// For display
var x= 0;
console.log(headings[0]+" : "+time[x]+headings[1]+" : "+data1[x]+headings[2]+" : "+data2[x]+headings[4]+" : "+data2[x]);
}
})
希望这可以帮助将来的某个人!
答案 7 :(得分:1)
function CSVParse(csvFile)
{
this.rows = [];
var fieldRegEx = new RegExp('(?:\s*"((?:""|[^"])*)"\s*|\s*((?:""|[^",\r\n])*(?:""|[^"\s,\r\n]))?\s*)(,|[\r\n]+|$)', "g");
var row = [];
var currMatch = null;
while (currMatch = fieldRegEx.exec(this.csvFile))
{
row.push([currMatch[1], currMatch[2]].join('')); // concatenate with potential nulls
if (currMatch[3] != ',')
{
this.rows.push(row);
row = [];
}
if (currMatch[3].length == 0)
break;
}
}
我喜欢让正则表达式做得尽可能多。此正则表达式将所有项目视为带引号或不带引号,后跟列分隔符或行分隔符。或者文字的结尾。
这就是为什么最后一个条件 - 没有它它将是一个无限循环,因为模式可以匹配零长度字段(在csv中完全有效)。但由于$是一个零长度断言,它不会进入非匹配并结束循环。
而且仅供参考,我必须做出第二个选择,不包括价值周围的报价;似乎它是在我的javascript引擎上的第一个替代品之前执行并将引号视为未引用值的一部分。我不会问 - 只是让它起作用。
答案 8 :(得分:1)
您可以使用PapaParse来提供帮助。 https://www.papaparse.com/
这是一个CodePen。 https://codepen.io/sandro-wiggers/pen/VxrxNJ
Papa.parse(e, {
header:true,
before: function(file, inputElem){ console.log('Attempting to Parse...')},
error: function(err, file, inputElem, reason){ console.log(err); },
complete: function(results, file){ $.PAYLOAD = results; }
});
答案 9 :(得分:1)
如果要解决此问题而不使用Ajax,请使用FileReader()
Web API。
实施示例:
.csv
文件
function readSingleFile(e) {
var file = e.target.files[0];
if (!file) {
return;
}
var reader = new FileReader();
reader.onload = function(e) {
var contents = e.target.result;
displayContents(contents);
displayParsed(contents);
};
reader.readAsText(file);
}
function displayContents(contents) {
var element = document.getElementById('file-content');
element.textContent = contents;
}
function displayParsed(contents) {
const element = document.getElementById('file-parsed');
const json = contents.split(',');
element.textContent = JSON.stringify(json);
}
document.getElementById('file-input').addEventListener('change', readSingleFile, false);
<input type="file" id="file-input" />
<h3>Raw contents of the file:</h3>
<pre id="file-content">No data yet.</pre>
<h3>Parsed file contents:</h3>
<pre id="file-parsed">No data yet.</pre>
答案 10 :(得分:1)
有点晚了,但我希望它能对某人有所帮助。
前一段时间,甚至我遇到了一个问题,即字符串数据之间包含\n
,同时读取文件时读取的内容也不同。
例如
"Harry\nPotter","21","Gryffindor"
阅读时:
Harry
Potter,21,Gryffindor
我在我的有角项目中使用了一个库csvtojson来解决此问题。
您可以使用以下代码将CSV文件作为字符串读取,然后将该字符串传递给csvtojson库,它将为您提供JSON列表。
示例代码:
const csv = require('csvtojson');
if (files && files.length > 0) {
const file: File = files.item(0);
const reader: FileReader = new FileReader();
reader.readAsText(file);
reader.onload = (e) => {
const csvs: string = reader.result as string;
csv({
output: "json",
noheader: false
}).fromString(csvs)
.preFileLine((fileLine, idx) => {
//Convert csv header row to lowercase before parse csv file to json
if (idx === 0) { return fileLine.toLowerCase() }
return fileLine;
})
.then((result) => {
// list of json in result
});
}
}
答案 11 :(得分:1)
我使用 import pygal as pyg
line_chart = pyg.HorizontalBar()
line_chart.title = 'Friends favorite pizza topping'
line_chart.add('olives', 24)
line_chart.add('TOMATO', 32)
line_chart.add('pepperoni', 42)
line_chart.add('mushroom', 0.5)
line_chart.add('other', 1.5)
data = line_chart.render(pretty_print=True)
print(data.decode())
with open('image.svg' 'wb') as fh:
fh.write(data)
#line_chart.render_to_file('image.svg')
#line_chart.render_to_png('test.png')
line_chart.render_in browser()
来做到这一点。
我提供以下两个例子
J_train = numpy.zeros((12, 1))
J_cv = numpy.zeros((12, 1))
NumberOfExamples = numpy.zeros((12, 1))
for i in range (12):
Xtrain = X[0:i+1]
Ytrain = y[0:i+1]
theta = inv(Xtrain.T * Xtrain ) * Xtrain.T * Ytrain
J_train[i] = (1/(2*m)) * numpy.sum(numpy.power((Xtrain * theta - Ytrain) , 2))
J_cv[i] = (1/(2*m)) * numpy.sum(numpy.power((Xval * theta - yval) , 2))
NumberOfExamples[i] = i + 1
plt.plot(NumberOfExamples, J_train, NumberOfExamples, J_cv)
jquery-csv
答案 12 :(得分:0)
$(function() {
$("#upload").bind("click", function() {
var regex = /^([a-zA-Z0-9\s_\\.\-:])+(.csv|.xlsx)$/;
if (regex.test($("#fileUpload").val().toLowerCase())) {
if (typeof(FileReader) != "undefined") {
var reader = new FileReader();
reader.onload = function(e) {
var customers = new Array();
var rows = e.target.result.split("\r\n");
for (var i = 0; i < rows.length - 1; i++) {
var cells = rows[i].split(",");
if (cells[0] == "" || cells[0] == undefined) {
var s = customers[customers.length - 1];
s.Ord.push(cells[2]);
} else {
var dt = customers.find(x => x.Number === cells[0]);
if (dt == undefined) {
if (cells.length > 1) {
var customer = {};
customer.Number = cells[0];
customer.Name = cells[1];
customer.Ord = new Array();
customer.Ord.push(cells[2]);
customer.Point_ID = cells[3];
customer.Point_Name = cells[4];
customer.Point_Type = cells[5];
customer.Set_ORD = cells[6];
customers.push(customer);
}
} else {
var dtt = dt;
dtt.Ord.push(cells[2]);
}
}
}
答案 13 :(得分:0)
实际上,您可以使用名为any-text的轻量级库。
npm i -D any-text
var reader = require('any-text');
reader.getText(`path-to-file`).then(function (data) {
console.log(data);
});
或使用async-await:
var reader = require('any-text');
const chai = require('chai');
const expect = chai.expect;
describe('file reader checks', () => {
it('check csv file content', async () => {
expect(
await reader.getText(`${process.cwd()}/test/files/dummy.csv`)
).to.contains('Lorem ipsum');
});
});