變數宣告會先執行,然後是
console.log(obj);
obj.a = 6
這兩行實際上是在一起執行的。
但是我猜console.log(obj)
是非同步執行的(這樣效能比較好?),所以他真正印出obj時,下一行已經執行完畢了。
另外,在node.js沒這個現象,而且如果你跑比較複雜的node.js程式(處理資料、分析、需要大量IO等),console.log會嚴重影響效能。所以在node.js環境,恐怕console.log是同步執行的。(不過最近沒在寫,不知道還會不會這樣)
https://developer.mozilla.org/en-US/docs/Web/API/Console/log
補充一下,MDN有解釋這個問題,請參考「Logging objects」,如果是要記錄物件當下的狀態,他建議這樣做:
console.log(JSON.parse(JSON.stringify(obj)));
另外,如果你在console.log(obj);
之後插入一個會跑夠多時間的運算(例如巢狀的for迴圈),console.log的結果就跟你預期的一樣了。(剛剛測試一下...兩層各一百萬次,然後我只好關瀏覽器了...雖然console.log有正確出來)
js真的是得自己實做才能累積經驗的語言,坑實在太多了。
謝謝這邊大哥熱情討論 我一直以為我是我專案問題 看來我一輩子都不會懂javascript 謝謝
遇到傳參考,可以先 deepcopy 再給他.
不要單獨使用console.log來除錯
console.log不是一個坑,如果您真要用console.log除錯,是您自己挖個坑,您要注意自己不要跳進去,您必須管理物件的生命週期。基本觀念是:console.log都是紀錄物件的最後狀態, 通常要用瀏覽器的除錯器來檢測console.log的值。
如果您用瀏覽器的除錯器,在console.log處設下檢查點,您會看到停止在檢查點的最後狀態,如果您沒有使用除錯器,console.log輸出最終的最後狀態
瀏覽器 console.log 的結果為 Observer (至少 Chrome 是),所以才會看到 obj 的最終結果,實際上確實是先執行 console.log(obj);
再 obj.a = 6;
。
可以依照上面大大們的建議下中斷點,又或者使用: console.log(JSON.stringify(obj))
的方式打印出當下實際的狀況。
如果嫌麻煩,自己寫個 plugin 用用吧!
(() => {
if (window) {
window.console.copyLog = (data) => {
console.log(JSON.parse(JSON.stringify(data)));
}
}
})();