我想编写一个 google 应用程序脚本来构建多级 JSON
I want to write a google app script to build a multi-level JSON
我有一个 table 这样的:
country
year
fx_rate
ES
2021
1
ES
2022
1
SE
2021
9.98
SE
2022
10.01
我想把它转换成嵌套的JSON(可能名字不对)。
我有这个代码:
function toJson(data,indexer){
var cols = data[0];
var index = cols.indexOf(indexer);
var jsonData = {};
for (i = 1; i < data.length; i++) {
if (!jsonData.hasOwnProperty(data[i][index])) {
jsonData[data[i][index]] = [];
}
var jsonCandidate = {};
for (j = 0; j < cols.length; j++) {
if (data[i][j] instanceof Date){
jsonCandidate[cols[j]] = Utilities.formatDate(data[i][j], 'Europe/Madrid', 'yyyy-MM-dd');
}else{
jsonCandidate[cols[j]] = data[i][j];
}
}
jsonData[data[i][index]].push(jsonCandidate);
}
return jsonData;
}
其中 data
是上面的 table,indexer
是 json 的第一级密钥。如果我使用国家作为索引器,那么我会得到这样的结果:
{"ES="[{year=2022.0,eur=1.0,"country=ES"},{year=2021.0,eur=1.0,"country=ES"},],"SE="[{year=2021.0,eur=9.98,"country=SE"},{year=2022.0,eur=10.01,"country=SE"}}
我想要的结果是:
{"ES="["year="["2021=" {eur=1.0,"country=ES"},"2022=" {eur=1.0,"country=ES"}]],"SE="["year="["2021="{eur=9.98,"country=SE"},{eur=10.01,"country=SE"}]]}
我想要这个的原因是能够根据国家和年份等动态字段调用我想要的值,所以我可以做类似 jsonData[country][year]['eur'] 并获得我想要的每个值的外汇汇率。
我能想到的最好的是这段代码:
function toJson3(data,indexer1,indexer2){
var cols = data[0];
var index1 = cols.indexOf(indexer1);
var index2 = cols.indexOf(indexer2);
var jsonData = {};
for (i = 1; i < data.length; i++) {
if (!jsonData.hasOwnProperty(data[i][index1])) {
jsonData[data[i][index1]] = {};
jsonData[data[i][index1]][data[i][index2]] = [];
}
var jsonCandidate = {};
for (j = 0; j < cols.length; j++) {
if (data[i][j] instanceof Date){
jsonCandidate[cols[j]] = Utilities.formatDate(data[i][j], 'Europe/Madrid', 'yyyy-MM-dd');
}else{
jsonCandidate[cols[j]] = data[i][j];
}
}
jsonData[data[i][index1]][data[i][index2]].push(jsonCandidate);
}
return jsonData;
}
但这失败说无法读取未定义的属性 'push'..
在此先感谢您的帮助
你的 JSON 看起来不太好。可能你想要这样的东西:
function myFunction() {
var sheet = SpreadsheetApp.getActiveSheet();
var range = sheet.getDataRange();
var [header, ...data] = range.getValues();
var obj = {};
while (data.length) {
var [country, year, rate] = data.shift();
try {
obj[country][year] = {'eur': rate, 'country': country};
} catch(e) {
var y = {};
y[year] = {'eur': rate, 'country': country};
obj[country] = y;
}
}
console.log(obj);
console.log(obj['ES']['2021'].eur);
console.log(obj['SE']['2022'].eur);
}
Sheet:
输出:
{ ES:
{ '2021': { eur: 1, country: 'ES' },
'2022': { eur: 1, country: 'ES' } },
SE:
{ '2021': { eur: 9.98, country: 'SE' },
'2022': { eur: 10.01, country: 'SE' } }
}
1
10.01
也许你根本不需要 属性 'country'。
我有一个 table 这样的:
country | year | fx_rate |
---|---|---|
ES | 2021 | 1 |
ES | 2022 | 1 |
SE | 2021 | 9.98 |
SE | 2022 | 10.01 |
我想把它转换成嵌套的JSON(可能名字不对)。
我有这个代码:
function toJson(data,indexer){
var cols = data[0];
var index = cols.indexOf(indexer);
var jsonData = {};
for (i = 1; i < data.length; i++) {
if (!jsonData.hasOwnProperty(data[i][index])) {
jsonData[data[i][index]] = [];
}
var jsonCandidate = {};
for (j = 0; j < cols.length; j++) {
if (data[i][j] instanceof Date){
jsonCandidate[cols[j]] = Utilities.formatDate(data[i][j], 'Europe/Madrid', 'yyyy-MM-dd');
}else{
jsonCandidate[cols[j]] = data[i][j];
}
}
jsonData[data[i][index]].push(jsonCandidate);
}
return jsonData;
}
其中 data
是上面的 table,indexer
是 json 的第一级密钥。如果我使用国家作为索引器,那么我会得到这样的结果:
{"ES="[{year=2022.0,eur=1.0,"country=ES"},{year=2021.0,eur=1.0,"country=ES"},],"SE="[{year=2021.0,eur=9.98,"country=SE"},{year=2022.0,eur=10.01,"country=SE"}}
我想要的结果是:
{"ES="["year="["2021=" {eur=1.0,"country=ES"},"2022=" {eur=1.0,"country=ES"}]],"SE="["year="["2021="{eur=9.98,"country=SE"},{eur=10.01,"country=SE"}]]}
我想要这个的原因是能够根据国家和年份等动态字段调用我想要的值,所以我可以做类似 jsonData[country][year]['eur'] 并获得我想要的每个值的外汇汇率。
我能想到的最好的是这段代码:
function toJson3(data,indexer1,indexer2){
var cols = data[0];
var index1 = cols.indexOf(indexer1);
var index2 = cols.indexOf(indexer2);
var jsonData = {};
for (i = 1; i < data.length; i++) {
if (!jsonData.hasOwnProperty(data[i][index1])) {
jsonData[data[i][index1]] = {};
jsonData[data[i][index1]][data[i][index2]] = [];
}
var jsonCandidate = {};
for (j = 0; j < cols.length; j++) {
if (data[i][j] instanceof Date){
jsonCandidate[cols[j]] = Utilities.formatDate(data[i][j], 'Europe/Madrid', 'yyyy-MM-dd');
}else{
jsonCandidate[cols[j]] = data[i][j];
}
}
jsonData[data[i][index1]][data[i][index2]].push(jsonCandidate);
}
return jsonData;
}
但这失败说无法读取未定义的属性 'push'..
在此先感谢您的帮助
你的 JSON 看起来不太好。可能你想要这样的东西:
function myFunction() {
var sheet = SpreadsheetApp.getActiveSheet();
var range = sheet.getDataRange();
var [header, ...data] = range.getValues();
var obj = {};
while (data.length) {
var [country, year, rate] = data.shift();
try {
obj[country][year] = {'eur': rate, 'country': country};
} catch(e) {
var y = {};
y[year] = {'eur': rate, 'country': country};
obj[country] = y;
}
}
console.log(obj);
console.log(obj['ES']['2021'].eur);
console.log(obj['SE']['2022'].eur);
}
Sheet:
输出:
{ ES:
{ '2021': { eur: 1, country: 'ES' },
'2022': { eur: 1, country: 'ES' } },
SE:
{ '2021': { eur: 9.98, country: 'SE' },
'2022': { eur: 10.01, country: 'SE' } }
}
1
10.01
也许你根本不需要 属性 'country'。