Javascript JSON.parse reviver函数嵌套对象
我的目标是使用可选的Javascript JSON.parse reviver函数嵌套对象,javascript,json,parsing,reviver-function,Javascript,Json,Parsing,Reviver Function,我的目标是使用可选的reviver参数告诉JSON.parse函数,如果传递给calc(string)函数的字符串有一个名为“expr”的键来执行该表达式内部的操作,我会使用它,然后继续向外工作,对管柱的其余部分进行操作 每次运行此命令时,我都会得到NaN 如果我在console.log(initNumber)之前注释掉最后两个calc(string)调用,那么程序将按预期运行 因此,如果键是“expr”,嵌套的“op”键的值是“add”,则对该嵌套对象执行add()函数。如果“op”键是“su
reviver参数告诉JSON.parse
函数,如果传递给calc(string)
函数的字符串有一个名为“expr”
的键来执行该表达式内部的操作,我会使用它,然后继续向外工作,对管柱的其余部分进行操作
每次运行此命令时,我都会得到NaN
如果我在console.log(initNumber)
之前注释掉最后两个calc(string)
调用,那么程序将按预期运行
因此,如果键是“expr”
,嵌套的“op”
键的值是“add”
,则对该嵌套对象执行add()函数。如果“op”
键是“subtract”
,则同样适用
非常感谢您的帮助
var initNum = 0;
var calc = function(string) {
var calcString = JSON.parse(string, reviver);
add(calcString);
subtract(calcString);
};
var add = function(string) {
if (string["op"] == "add") {
var numString = parseInt(JSON.stringify(string["number"]));
initNum = numString + initNum;
return initNum;
}
}
var subtract = function(string) {
if (string["op"] == "subtract") {
var numString = parseInt(JSON.stringify(string["number"]));
initNum = initNum - numString;
return initNum;
}
}
var reviver = function(key, val) {
if (key == "expr") {
if (val.op == "add") {
return add(val);
}
else if (val.op == "subtract") {
return subtract(val);
}
}
else {
return val;
}
};
calc('{"op" : "add", "number" : 5}');
calc('{"op" : "subtract", "number" : 2}');
calc('{"op" : "add", "number" : 19}');
calc('{"op": "subtract", "expr" : {"op" : "add", "number" : 15}}');
calc('{"op": "add", "expr" : {"op" : "add", "expr" : {"op" : "subtract", "number" : 3}}}');
console.log(initNum);
有几点:
reviver
将为您提供已解析的值,您无需再次解析它们
- 如果您将一个
expr
转换为一个值,那么您的add
和subtract
函数需要能够读取这些值,而不仅仅是number
——我想,您可能想要不同的逻辑。这就是为什么我用下面的方法得到操作数。无论哪种方式,您都需要知道可能没有number
参数,并处理它
- 您获取
NaN
的原因是由于上述原因-您试图从没有编号的对象(恢复expr
s的结果)获取编号
,这会导致未定义
,从而破坏计算
基本上,记住这一点
{“op”:“subtract”,“expr”:{“op”:“add”,“number”:15}}
去
{“op”:“subtract”,“expr”:37}
在恢复表达式之后,需要处理它
var initNum=0;
var calc=函数(字符串){
var calcObj=JSON.parse(字符串,reviver);
添加(calcObj);
减去(calcObj);
};
var add=功能(obj){
如果(obj[“op”]=“添加”){
变量操作数=(obj[“number”])?obj[“number”]:obj[“expr”];
initNum=操作数+initNum;
log(“运行总数:+initNum”);
返回initNum;
}
}
var减法=函数(obj){
if(obj[“op”]=“减法”){
变量操作数=(obj[“number”])?obj[“number”]:obj[“expr”];
initNum=initNum-操作数;
log(“运行总数:+initNum”);
返回initNum;
}
}
var恢复器=功能(键,val){
如果(键==“expr”){
如果(val.op==“添加”){
返回添加(val);
}
否则如果(val.op==“减法”){
返回减法(val);
}
}
否则{
返回val;
}
};
计算(“{”op:“添加”,“编号”:5}”);
计算(“{”op:“减法”,“数字”:2}”);
计算(“{”op:“添加”,“编号:19}”);
计算(“{”op:“减法”,“表达式”:{”op:“加”,“数”:15}”);
计算(“{”op:“add”,“expr:{”op:“add”,“expr:{”op:“subtract”,“number”:3}}}”);
console.log(initNum)非常感谢你。这让Wayyyy现在更有意义了。因此,在变量操作数部分,您现在说“如果JSON对象有一个“number”键,请使用该键,否则请使用“expr”键。谢谢您。如果JSON对象有一个“number”键,请使用该键,否则请使用“expr”键
是的,完全正确。而且由于revivier
是“从最嵌套的属性开始,然后继续到原始值本身”,所以所有expr
s在被周围的add
或subtract
操作看到时,应该已经转换为它们的值。真是太棒了。完全有道理。:)