2017-10-22 115 views
1

我的目標是告訴功能與可選reviver argument,我希望它是否傳遞給calc(string)函數的字符串有一個名爲"expr"的鍵執行該表達式內的操作,然後繼續向外工作以操作其餘的字符串。JSON.parse reviver函數嵌套對象

每當我運行這個我越來越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); 

回答

1

的幾點:

  • reviver會給你已經被解析的值,則不需要再次解析他們。
  • 如果您將expr轉換爲值,您的addsubtract函數需要能夠讀取這些值,而不僅僅是number - 我想,也許您打算使用不同的邏輯。這就是爲什麼我按照我的方式得到operand。無論哪種方式,您都需要意識到可能沒有number參數,並處理該參數。
  • 你得到的原因是NaN正是因爲上述原因 - 你試圖從沒有物體的number中得到 s的結果,這給你undefined打破了計算。

基本上,記得

{"op": "subtract", "expr" : {"op" : "add", "number" : 15}}

{"op": "subtract", "expr" : 37}

你復活的表達後,所以你需要處理的。

var initNum = 0; 
 

 
var calc = function(string) { 
 
    var calcObj = JSON.parse(string, reviver); 
 

 
    add(calcObj); 
 
    subtract(calcObj); 
 
}; 
 

 
var add = function(obj) { 
 
    if (obj["op"] == "add") { 
 
     var operand = (obj["number"])? obj["number"] : obj["expr"]; 
 
     initNum = operand + initNum; 
 
     console.log("running total : "+initNum); 
 
     return initNum; 
 
    } 
 
} 
 
var subtract = function(obj) { 
 
    if (obj["op"] == "subtract") { 
 
     var operand = (obj["number"])? obj["number"] : obj["expr"]; 
 
     initNum = initNum - operand; 
 
     console.log("running total : "+initNum); 
 
     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);

+0

謝謝你這麼多。這使得wayyyyyyy現在更有意義。因此,在var操作數部分中,您現在說「如果JSON對象具有」數字「鍵,請使用該鍵,否則使用」expr「鍵。」謝謝謝謝。 – giggidy

+0

'如果JSON對象有一個「數字」鍵,那麼使用它,否則使用「expr」鍵'是的,確切地說。並且因爲'reviver'是[定義](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/JSON/parse#Using_the_reviver_parameter)「工作」,從最嵌套的屬性開始進行到原來的價值本身',所有'expr's應該已經被轉換爲他們的價值觀,當他們被看到'add或'subtract'圍繞他們。 –

+0

剛剛輝煌。總體感覺。 :) – giggidy