अपडेटेड नोट: यह क्रोम 49 में तय किया गया है ।
बहुत दिलचस्प सवाल! में खुदाई करते हैं।
मुख्य कारण
अंतर की जड़ यह है कि Node.js इन कथनों का मूल्यांकन कैसे करता है बनाम क्रोम विकास उपकरण कैसे करते हैं।
Node.js क्या करता है
Node.js का उपयोग करता repl इस के लिए मॉड्यूल।
Node.js REPL स्रोत कोड से :
self.eval(
'(' + evalCmd + ')',
self.context,
'repl',
function (e, ret) {
if (e && !isSyntaxError(e))
return finish(e);
if (typeof ret === 'function' && /^[\r\n\s]*function/.test(evalCmd) || e) {
// Now as statement without parens.
self.eval(evalCmd, self.context, 'repl', finish);
}
else {
finish(null, ret);
}
}
);
यह ({}+{})
क्रोम डेवलपर टूल में चलने की तरह ही काम करता है , जो "[object Object][object Object]"
आपकी अपेक्षा के अनुरूप भी होता है।
क्रोम डेवलपर टूल क्या करते हैं
दूसरी ओर क्रोम डवलपर टूल निम्नलिखित कार्य करता है :
try {
if (injectCommandLineAPI && inspectedWindow.console) {
inspectedWindow.console._commandLineAPI = new CommandLineAPI(this._commandLineAPIImpl, isEvalOnCallFrame ? object : null);
expression = "with ((window && window.console && window.console._commandLineAPI) || {}) {\n" + expression + "\n}";
}
var result = evalFunction.call(object, expression);
if (objectGroup === "console")
this._lastResult = result;
return result;
}
finally {
if (injectCommandLineAPI && inspectedWindow.console)
delete inspectedWindow.console._commandLineAPI;
}
तो मूल रूप से, यह call
अभिव्यक्ति के साथ ऑब्जेक्ट पर प्रदर्शन करता है । अभिव्यक्ति की जा रही है:
with ((window && window.console && window.console._commandLineAPI) || {}) {
{}+{};// <-- This is your code
}
तो, जैसा कि आप देख सकते हैं, रैपिंग कोष्ठक के बिना, अभिव्यक्ति को सीधे विकसित किया जा रहा है।
क्यों Node.js अलग तरह से कार्य करता है
Node.js का स्रोत इसे सही ठहराता है:
// This catches '{a : 1}' properly.
नोड ने हमेशा इस तरह का अभिनय नहीं किया। यहां वास्तविक प्रतिबद्धता है जिसने इसे बदल दिया है । रयान ने इस बदलाव पर निम्नलिखित टिप्पणी छोड़ी: "अंतर के उदाहरण के साथ सुधार करें कि कैसे REPL कमांडों को विकसित किया गया है"।
राइनो
अद्यतन - ओपी इस बात में रुचि रखता था कि राइनो कैसे व्यवहार करता है (और यह क्रोम डेत्टुल्स और नोड्ज के विपरीत क्यों व्यवहार करता है)।
राइनो क्रोम डेवलपर टूल्स और Node.js की REPL के विपरीत एक पूरी तरह से अलग JS इंजन का उपयोग करता है जो दोनों V8 का उपयोग करते हैं।
जब आप राइनो शेल में राइनो के साथ एक जावास्क्रिप्ट कमांड को विकसित करते हैं तो यहां की मूल पाइप लाइन होती है।
खोल चलता है org.mozilla.javascript.tools.shell.main
।
बारी में, यह कहता है इस new IProxy(IProxy.EVAL_INLINE_SCRIPT);
उदाहरण के लिए, यदि कोड इनलाइन स्विच -e के साथ सीधे पारित किया गया था।
यह IProxy की run
विधि को हिट करता है ।
यह आह्वान करता है evalInlineScript
( src )। यह बस स्ट्रिंग संकलित करता है और इसे विकसित करता है।
मूल रूप से:
Script script = cx.compileString(scriptText, "<command>", 1, null);
if (script != null) {
script.exec(cx, getShellScope()); // <- just an eval
}
तीन में से, राइनो का खोल वह है जो eval
किसी भी लपेट के बिना एक वास्तविक के सबसे करीब काम करता है । राइनो एक वास्तविक eval()
बयान के सबसे करीब है और आप eval
उससे वैसा ही व्यवहार करने की उम्मीद कर सकते हैं ।