【问题标题】:javascript serialize json array with commasjavascript用逗号序列化json数组
【发布时间】:2020-07-02 19:52:10
【问题描述】:

我正在尝试将这个函数 How parameterize array to as single comma separated value? 应用到一个“按其名称调用的函数”脚本中,但它没有按预期工作:

function add(a,b,c){
    return a+b+c
}

var vals = callFct("add", window, 2,3,4); 
document.getElementById('result').innerHTML += "<br>Function result: "+vals
// result = Function result: 9 ----> 2+3+4 : OK

值来自:json={a:[2,3,4]}

function serialize(vals){
    var output = [];
    for (var prop in vals) {
        if (vals.hasOwnProperty(prop)){
            output.push(vals[prop].join(','));
        }
    }
    return output;
}

var json = {a:[2,3,4]};
document.getElementById('result').innerHTML += "<br>Used data:  "+serialize(json)
// result = Used data: 2,3,4 ---> seems to be OK... but

var test = callFct("add", window, serialize(json)); 
document.getElementById('result').innerHTML += "<br>Function result:  "+test
// result = Function result : 2,3,4undefinedundefined ---> oups

我已尝试删除“未定义”...

document.getElementById('result').innerHTML += "<br>Function result :  "+test.replace(/undefined/g,'')
// result = Function result : 2,3,4 ---> nope

被调用函数:

function callFct(w, y, z ) {  
  var z = Array.prototype.slice.call(arguments, 2);
  console.log('vars = '+z)
  let v = w.split(".");
  let x = v.pop();
  for(var i = 0; i < v.length; i++) {
    y = y[v[i]];
  }
  return y[x].apply(y, z);
}

我的前进方式有什么问题?

【问题讨论】:

  • 你为什么不用JSON.stringify
  • json 变量是一个对象,而不是 JSON(这是一种文本格式),serialize 不会将其转换为 JSON。它将它变成一个字符串数组。
  • 如果您需要帮助,您需要显示callFct 的代码。
  • 功能添加有问题

标签: javascript arrays json


【解决方案1】:

请提供比wyz 更好的参数名称...

如果您将名称更改为在下面的演示中看到的名称,您的 return 语句将如下所示:

return scope[last].apply(funcName, serialized);

如果您注意到,您正在致电window.add 申请。确保该方法存在。我不确定add 是什么样子,但它会采用“序列化”的 JSON 数据,并且调用的范围将是传入的字符串(第一个)参数(显然可以用点分隔)。

注意事项

  1. 您可以将这个:[...output, json[prop].join(',')] 更改为这个:output.concat(json[prop].join(',')),以实现浏览器兼容性。
  2. flatMap 的“基本”polyfill 可以在这里找到:https://stackoverflow.com/a/39838385/1762224

const json = { a: [2, 3, 4] };

document.getElementById('result-1').innerHTML = 'Values: ' + serialize(json);

let sum = callFct('add', window, serialize(json));
document.getElementById('result-2').innerHTML = 'Sum: ' + sum;

let difference = callFct('subtract', window, serialize(json));
document.getElementById('result-3').innerHTML = 'Difference: ' + difference;

function serialize(json) {
  return Object.keys(json).reduce((output, prop) => {
    return [...output, json[prop].join(',')];
  }, []);
}

function callFct(funcName, scope, serialized) {
  serialized = Array.from(arguments).slice(2);
  console.log('vars = ' + serialized)
  const tokens = funcName.split('.');
  const last = tokens.pop();
  for (let i = 0; i < tokens.length; i++) {
    scope = scope[tokens[i]];
  }
  return scope[last].apply(funcName, serialized);
}

function prepareValues(serialized) {
  return serialized
    .flatMap(v => v.split(/,\s*/g))
    .map(v => parseInt(v, 10));
}

function add(serialized) {
  return prepareValues(serialized)
    .reduce((s, v) => s + v, 0);
}

function subtract(serialized) {
  return prepareValues(serialized)
    .reduce((s, v) => s - v);
}
div[id^="result-"] { font-family: monospace; }
<script src="https://polyfill.io/v3/polyfill.min.js?features=Array.prototype.flatMap"></script>
<div id="result-1"></div>
<div id="result-2"></div>
<div id="result-3"></div>

【讨论】:

  • 它没有解决问题:问题中解释的使用数据是正确的 (2,3,4),但不是功能可利用的格式。
  • @Wolden 好的,您在我最初回答后提供的包含的功能,我试图解释发生了什么。
  • @Wolden 我更新了我的add 函数以平面映射结果,然后拆分值。您的序列化正在返回一个“序列化”值的数组。这不是一个真正的字符串。您正在将结果构建为每个键的连接值数组。
  • yeeeeeeees 非常感谢,它完美运行 :-) ...顺便说一句,是否有一种“经典方式”来替换尚未被所有浏览器识别的 flatMap?
  • @Wolden 你可以创建一个polyfill。我会将其添加到问题中。
【解决方案2】:

终于找到了一个最简单的解决方案:

// define empty vars
let a, b, c;    
const vars = [a, b, c];

// call function by its name
function callFct(fct) {  
  const toks = fct.split(".");
  const last = toks.pop();
  for(var i = 0; i < toks.length; i++) {
    window = window[toks[i]];
  }
  return window[last].apply(window, vars); // vars now in array
}

// functions to be called
function add(){
   return a+b+c
}
function substract(){
   return a-b-c
}  
function multiply(){
   return a*b*c
}

// produce real vars values
a = 20, b = 10, c = 5;

// get results
var add = callFct("add");
console.log(add); // 20+10+5 = 35

c = -5 // actualize any value
var subs = callFct("substract");
console.log(subs); // 20-10--5 = 15

var mult = callFct("multiply");
console.log(mult); // -1000

// mixing functions results
function mix(){
    return add/subs
}
var mixed = callFct("mix");
console.log(mixed); // 2.3333333333333335

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-07-13
    • 1970-01-01
    • 2019-02-12
    • 2016-06-04
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多