问题描述
我正在使用 CSV package for Node 来解析项目中的一些 CSV 文件。我需要能够处理有和没有标题的情况。所以:
const withHeader = `h1,h2,h3
d1a,d2a,d3a
d1b,d2b,d3b`;
const withoutHeader = `d1a,d3b`;
我的应用程序不知道列数及其名称。它们要么从标题中读取,要么应该以数字方式生成,例如col0,col1,col2
。
这是我遇到问题的地方。我总是希望 csvParse 的输出采用对象字面量形式。当最终用户指出 CSV 具有标题时,这很容易:
> csvParse(withHeader,{columns: true})
[
{ h1: 'd1a','h2': 'd2a','h3': 'd3a' },{ h1: 'd1b','h2': 'd2b','h3': 'd3b' }
]
但是当用户指出没有标题行时,似乎不可能以对象字面量形式与以编程方式生成的列标题结束数据。
columns
的 3 个选项是 boolean | array | function
。
- 通过提供
false
,返回的数据是一个数组数组,然后我需要将其转换为对象字面量形式。不理想! - 要提供一个列名数组,我已经需要知道有多少列......在解析之前,这是没有意义的。我可以解析第一行以获取计数,然后再次开始提供数组,但这似乎很笨拙。
- 我可以提供一个以编程方式生成列键的函数。例如。
column => column
无济于事,因为 a) 没有提供索引,并且 b) 这会忽略第一行,因为它被假定为将列标题转换为所需的列键。
有没有我错过的方法来做到这一点?以下是两种看似笨拙且效率低下的方法。
解析1行,然后解析所有
// Obviously in actual use I'd handle edge cases
const colCount = csvParse(withoutHeader,{to_line: 1})[0].length;
// 3
const data = csvParse(withoutHeader,{columns: [...Array(colCount).keys()].map(i => `col{i}`)})
/*
[
{ col0: 'd1a',col1: 'd2a',col2: 'd3a' },{ col0: 'd1b',col1: 'd2b',col2: 'd3b' }
]
*/
解析成数组数组,然后转换
csvParse(withoutHeader).map(
row => row.reduce(
(obj,item,index) => {
obj[`col${index}`] = item;
return obj;
},{}
)
)
/*
[
{ col0: 'd1a',col2: 'd3b' }
]
*/
对我来说,能够将 columns
指定为函数是理想的,该函数将列索引作为参数而不是标题行。
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)