it-swarm.com.de

Wie kann man in JavaScript nach "undefined" suchen?

Wie kann am besten getestet werden, ob eine Variable in JavaScript undefiniert ist? Ich habe verschiedene Möglichkeiten gesehen:

if (window.myVariable)

Oder

if (typeof(myVariable) != "undefined")

Oder

if (myVariable) //This throws an error if undefined. Should this be in Try/Catch?
2214

Wenn Sie herausfinden möchten, ob eine Variable unabhängig von ihrem Wert deklariert wurde, ist die Verwendung des Operators in der sicherste Weg. Betrachten Sie dieses Beispiel.

// global scope
var theFu; // theFu has been declared, but its value is undefined
typeof theFu; // "undefined"

In einigen Fällen ist dies jedoch möglicherweise nicht das beabsichtigte Ergebnis, da die Variable oder Eigenschaft deklariert, jedoch nicht initialisiert wurde. Verwenden Sie den Operator in für eine zuverlässigere Prüfung.

"theFu" in window; // true
"theFoo" in window; // false

Wenn Sie wissen möchten, ob die Variable nicht deklariert wurde oder den Wert undefined hat, verwenden Sie den Operator typeof.

if (typeof myVar !== 'undefined')

Der Operator typeof gibt garantiert eine Zeichenfolge zurück. Direkte Vergleiche mit undefined sind problematisch, da undefined überschrieben werden kann.

window.undefined = "omg";
"omg" == undefined // true

Wie @CMS betonte, wurde dies in ECMAScript 5th ed gepatcht, und undefined ist nicht beschreibbar.

if (window.myVar) enthält auch diese falschen Werte, daher ist es nicht sehr robust:

 false 
 0 
 "" 
 NaN 
 null 
 undefined 

Vielen Dank an @CMS für den Hinweis, dass Ihr dritter Fall - if (myVariable) auch in zwei Fällen einen Fehler auslösen kann. Das erste ist, wenn die Variable nicht definiert wurde, was ein ReferenceError auslöst.

// abc was never declared.
if (abc) {
    // ReferenceError: abc is not defined
} 

Der andere Fall ist, wenn die Variable definiert wurde, aber eine Getter-Funktion hat, die beim Aufrufen einen Fehler auslöst. Zum Beispiel,

// or it's a property that can throw an error
Object.defineProperty(window, "myVariable", { 
    get: function() { throw new Error("W00t?"); }, 
    set: undefined 
});
if (myVariable) {
    // Error: W00t?
}
2484
Anurag

Ich persönlich benutze

myVar === undefined

Warnung: Bitte beachten Sie, dass === über == verwendet wird und dass myVar zuvor deklariert (nicht definiert) war.


Ich mag typeof myVar === "undefined" nicht. Ich denke, es ist langwierig und unnötig. (Ich kann dasselbe in weniger Code erledigen.)

Jetzt werden einige Leute vor Schmerzen umkippen, wenn sie dies lesen und schreien: "Warten Sie! WARTEN SIE !!! undefined kann neu definiert werden!"

Cool. Ich weiß das. Andererseits können die meisten Variablen in Javascript neu definiert werden. Sollten Sie niemals eine integrierte Kennung verwenden, die neu definiert werden kann?

Wenn Sie diese Regel befolgen, ist das gut für Sie: Sie sind kein Heuchler.

Die Sache ist, dass Entwickler sich darauf verlassen müssen, dass redefinierbare Bezeichner das sind, was sie sind, um in JS viel echte Arbeit leisten zu können. Ich höre keine Leute, die mir sagen, dass ich setTimeout nicht verwenden soll, weil es jemand kann

window.setTimeout = function () {
    alert("Got you now!");
};

Unterm Strich ist das Argument "es kann neu definiert werden", dass kein roher === undefined verwendet wird, falsch.

(Wenn Sie immer noch Angst haben, dass undefined neu definiert wird, warum integrieren Sie ungeprüften Bibliothekscode blind in Ihre Codebasis? Oder noch einfacher: ein Flusentool.)


Ebenso wie der typeof -Ansatz kann diese Technik nicht deklarierte Variablen "erkennen":

if (window.someVar === undefined) {
    doSomething();
}

Aber diese beiden Techniken lecken in ihrer Abstraktion. Ich fordere Sie auf, dies nicht zu verwenden oder gar

if (typeof myVar !== "undefined") {
    doSomething();
}

Erwägen:

var iAmUndefined;

Um festzustellen, ob diese Variable deklariert ist oder nicht, müssen Sie möglicherweise auf den Operator in zurückgreifen. (In vielen Fällen können Sie einfach den Code O_o lesen).

if ("myVar" in window) {
    doSomething();
}

Aber warte! Es gibt mehr! Was ist, wenn ein Prototyp von Kettenmagie passiert? Jetzt reicht auch der übergeordnete Operator in nicht aus. (Okay, ich bin hier mit diesem Teil fertig, mit der Ausnahme, dass in 99% der Fälle === undefined (und **** cough **** typeof) gut funktioniert. Wenn Sie wirklich egal, Sie können über dieses Thema allein lesen.)

1045
Thomas Eding

Ich bevorzuge die Verwendung von typeof. Es funktioniert, wenn die Variable noch nie deklariert wurde, im Gegensatz zu einem Vergleich mit den Operatoren == oder === oder der Typenzwang mit if. (undefined kann im Gegensatz zu null auch in ECMAScript 3-Umgebungen neu definiert werden, was es für den Vergleich unzuverlässig macht, obwohl fast alle gängigen Umgebungen jetzt mit ECMAScript 5 oder höher kompatibel sind.).

if (typeof someUndeclaredVariable == "undefined") {
    // Works
}

if (someUndeclaredVariable === undefined) { 
    // Throws an error
}
175
Tim Down

Sie müssen typeof verwenden.

if (typeof something != "undefined") {
    // ...
}
59
Jacob Relkin

Update vom 25.07.2018

Es ist fast fünf Jahre her, seit dieser Beitrag erstellt wurde, und JavaScript hat einen langen Weg zurückgelegt. Bei der Wiederholung der Tests im ursprünglichen Beitrag habe ich keinen konsistenten Unterschied zwischen den folgenden Testmethoden festgestellt:

  • abc === undefined
  • abc === void 0
  • typeof abc == 'undefined'
  • typeof abc === 'undefined'

Sogar als ich die Tests modifizierte, um zu verhindern, dass Chrome sie wegoptimierte, waren die Unterschiede unbedeutend. Aus diesem Grund würde ich abc === undefined aus Gründen der Klarheit empfehlen.

Relevanter Inhalt von chrome://version:

  • Google Chrome: 67.0.3396.99 (offizielles Build) (64-Bit) (Kohorte: Stabil)
  • Revision: a337fbf3c2ab8ebc6b64b0bfdce73a20e2e2252b-refs/branch-heads/3396 @ {# 790}
  • Betriebssystem: Windows
  • JavaScript: V8 6.7.288.46
  • User Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, wie Gecko) Chrome/67.0.3396.99 Safari/537.36

Ursprünglicher Beitrag 01.11.2013

In Google Chrome war Folgendes etwas schneller als ein typeof -Test:

if (abc === void 0) {
    // Undefined
}

Der Unterschied war vernachlässigbar. Dieser Code ist jedoch prägnanter und für jemanden, der weiß, was void 0 bedeutet, auf einen Blick klarer. Beachten Sie jedoch, dass abcmuss noch deklariert werden.

Sowohl typeof als auch void waren signifikant schneller als der direkte Vergleich mit undefined. Ich habe das folgende Testformat in der Entwicklerkonsole Chrome verwendet:

var abc;
start = +new Date();
for (var i = 0; i < 10000000; i++) {
    if (TEST) {
        void 1;
    }
}
end = +new Date();
end - start;

Die Ergebnisse waren wie folgt:

Test: | abc === undefined      abc === void 0      typeof abc == 'undefined'
------+---------------------------------------------------------------------
x10M  |     13678 ms               9854 ms                 9888 ms
  x1  |    1367.8 ns              985.4 ns                988.8 ns

Beachten Sie, dass sich die erste Zeile in Millisekunden befindet, während sich die zweite Zeile in Nanosekunden befindet. Ein Unterschied von 3,4 Nanosekunden ist nichts. Die Zeiten waren in nachfolgenden Tests ziemlich konsistent.

40
Zenexer

Wenn es undefiniert ist, ist es nicht gleich einer Zeichenfolge, die die Zeichen "undefiniert" enthält, da die Zeichenfolge nicht undefiniert ist.

Sie können den Typ der Variablen überprüfen:

if (typeof(something) != "undefined") ...

Manchmal muss man nicht einmal den Typ überprüfen. Wenn der Wert der Variablen beim Festlegen nicht mit false bewertet werden kann (z. B. wenn es sich um eine Funktion handelt), können Sie die Variable einfach auswerten. Beispiel:

if (something) {
  something(param);
}
21
Guffa
if (typeof foo == 'undefined') {
 // Do something
};

Beachten Sie, dass ein strikter Vergleich (!==) in diesem Fall nicht erforderlich ist, da typeof immer eine Zeichenfolge zurückgibt.

17
Mathias Bynens

Einige Szenarien, die die Ergebnisse der verschiedenen Antworten veranschaulichen: http://jsfiddle.net/drzaus/UVjM4/

(Beachten Sie, dass die Verwendung von var für in -Tests in einem Wrapper mit Gültigkeitsbereich einen Unterschied ausmacht.)

Code als Referenz:

(function(undefined) {
    var definedButNotInitialized;
    definedAndInitialized = 3;
    someObject = {
        firstProp: "1"
        , secondProp: false
        // , undefinedProp not defined
    }
    // var notDefined;

    var tests = [
        'definedButNotInitialized in window',
        'definedAndInitialized in window',
        'someObject.firstProp in window',
        'someObject.secondProp in window',
        'someObject.undefinedProp in window',
        'notDefined in window',

        '"definedButNotInitialized" in window',
        '"definedAndInitialized" in window',
        '"someObject.firstProp" in window',
        '"someObject.secondProp" in window',
        '"someObject.undefinedProp" in window',
        '"notDefined" in window',

        'typeof definedButNotInitialized == "undefined"',
        'typeof definedButNotInitialized === typeof undefined',
        'definedButNotInitialized === undefined',
        '! definedButNotInitialized',
        '!! definedButNotInitialized',

        'typeof definedAndInitialized == "undefined"',
        'typeof definedAndInitialized === typeof undefined',
        'definedAndInitialized === undefined',
        '! definedAndInitialized',
        '!! definedAndInitialized',

        'typeof someObject.firstProp == "undefined"',
        'typeof someObject.firstProp === typeof undefined',
        'someObject.firstProp === undefined',
        '! someObject.firstProp',
        '!! someObject.firstProp',

        'typeof someObject.secondProp == "undefined"',
        'typeof someObject.secondProp === typeof undefined',
        'someObject.secondProp === undefined',
        '! someObject.secondProp',
        '!! someObject.secondProp',

        'typeof someObject.undefinedProp == "undefined"',
        'typeof someObject.undefinedProp === typeof undefined',
        'someObject.undefinedProp === undefined',
        '! someObject.undefinedProp',
        '!! someObject.undefinedProp',

        'typeof notDefined == "undefined"',
        'typeof notDefined === typeof undefined',
        'notDefined === undefined',
        '! notDefined',
        '!! notDefined'
    ];

    var output = document.getElementById('results');
    var result = '';
    for(var t in tests) {
        if( !tests.hasOwnProperty(t) ) continue; // bleh

        try {
            result = eval(tests[t]);
        } catch(ex) {
            result = 'Exception--' + ex;
        }
        console.log(tests[t], result);
        output.innerHTML += "\n" + tests[t] + ": " + result;
    }
})();

Und Ergebnisse:

definedButNotInitialized in window: true
definedAndInitialized in window: false
someObject.firstProp in window: false
someObject.secondProp in window: false
someObject.undefinedProp in window: true
notDefined in window: Exception--ReferenceError: notDefined is not defined
"definedButNotInitialized" in window: false
"definedAndInitialized" in window: true
"someObject.firstProp" in window: false
"someObject.secondProp" in window: false
"someObject.undefinedProp" in window: false
"notDefined" in window: false
typeof definedButNotInitialized == "undefined": true
typeof definedButNotInitialized === typeof undefined: true
definedButNotInitialized === undefined: true
! definedButNotInitialized: true
!! definedButNotInitialized: false
typeof definedAndInitialized == "undefined": false
typeof definedAndInitialized === typeof undefined: false
definedAndInitialized === undefined: false
! definedAndInitialized: false
!! definedAndInitialized: true
typeof someObject.firstProp == "undefined": false
typeof someObject.firstProp === typeof undefined: false
someObject.firstProp === undefined: false
! someObject.firstProp: false
!! someObject.firstProp: true
typeof someObject.secondProp == "undefined": false
typeof someObject.secondProp === typeof undefined: false
someObject.secondProp === undefined: false
! someObject.secondProp: true
!! someObject.secondProp: false
typeof someObject.undefinedProp == "undefined": true
typeof someObject.undefinedProp === typeof undefined: true
someObject.undefinedProp === undefined: true
! someObject.undefinedProp: true
!! someObject.undefinedProp: false
typeof notDefined == "undefined": true
typeof notDefined === typeof undefined: true
notDefined === undefined: Exception--ReferenceError: notDefined is not defined
! notDefined: Exception--ReferenceError: notDefined is not defined
!! notDefined: Exception--ReferenceError: notDefined is not defined
17
drzaus

In diesem Artikel habe ich gelesen, dass Frameworks wie nderscore.js diese Funktion verwenden:

function isUndefined(obj){
    return obj === void 0;
}
15
Marthijn

Persönlich verwende ich immer Folgendes:

var x;
if( x === undefined) {
    //Do something here
}
else {
   //Do something else here
}

Die window.undefined -Eigenschaft ist in allen modernen Browsern (JavaScript 1.8.5 oder höher) nicht beschreibbar. In der Dokumentation von Mozilla: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/undefined sehe ich Folgendes: Ein Grund für die Verwendung von typeof () ist das Es wird kein Fehler ausgegeben, wenn die Variable nicht definiert wurde.

Ich bevorzuge den Ansatz der Verwendung

x === undefined 

weil es fehlschlägt und in meinem Gesicht explodiert, anstatt stillschweigend vorbeizukommen/fehlzuschlagen, wenn x noch nicht deklariert wurde. Dies macht mich darauf aufmerksam, dass x nicht deklariert ist. Ich bin der Meinung, dass alle in JavaScript verwendeten Variablen deklariert werden sollten.

12
Hrishi

Die zuverlässigste Methode, mit der ich nach undefined suchen kann, ist die Verwendung von void 0.

Dies ist sowohl mit neueren als auch mit älteren Browsern kompatibel und kann nicht wie window.undefined in einigen Fällen überschrieben werden.

if( myVar === void 0){
    //yup it's undefined
}
10
Joseph Gabriel

Da mir keine der anderen Antworten weitergeholfen hat, schlage ich vor, dies zu tun. In Internet Explorer 8 hat es funktioniert:

if (typeof variable_name.value === 'undefined') {
    // variable_name is undefined
}
4
anmarti
// x has not been defined before
if (typeof x === 'undefined') { // Evaluates to true without errors.
   // These statements execute.
}

if (x === undefined) { // Throws a ReferenceError

}
4
sourcecode
    var x;
    if (x === undefined) {
        alert ("I am declared, but not defined.")
    };
    if (typeof y === "undefined") {
        alert ("I am not even declared.")
    };

    /* One more thing to understand: typeof ==='undefined' also checks 
       for if a variable is declared, but no value is assigned. In other 
       words, the variable is declared, but not defined. */

    // Will repeat above logic of x for typeof === 'undefined'
    if (x === undefined) {
        alert ("I am declared, but not defined.")
    };
    /* So typeof === 'undefined' works for both, but x === undefined 
       only works for a variable which is at least declared. */

    /* Say if I try using typeof === undefined (not in quotes) for 
       a variable which is not even declared, we will get run a 
       time error. */

    if (z === undefined) {
        alert ("I am neither declared nor defined.")
    };
    // I got this error for z ReferenceError: z is not defined 
3
Gaurav

Im Gegenteil zu @Thomas Eding Antwort:

Wenn ich vergesse, myVar in meinem Code zu deklarieren, erhalte ich myVar is not defined.

Nehmen wir ein reales Beispiel:

Ich habe einen Variablennamen, bin mir aber nicht sicher, ob er irgendwo deklariert ist oder nicht.

Dann hilft @ Anurags Antwort:

var myVariableToCheck = 'myVar';
if (window[myVariableToCheck] === undefined)
    console.log("Not declared or declared, but undefined.");

// Or you can check it directly 
if (window['myVar'] === undefined) 
    console.log("Not declared or declared, but undefined.");
3
Vikas

Ich benutze es als Funktionsparameter und schließe es bei der Funktionsausführung aus, so dass ich das "echte" undefinierte erhalte. Es erfordert jedoch, dass Sie Ihren Code in eine Funktion einfügen. Ich habe dies beim Lesen der jQuery-Quelle gefunden.

undefined = 2;

(function (undefined) {
   console.log(undefined); // prints out undefined
   // and for comparison:
   if (undeclaredvar === undefined) console.log("it works!")
})()

Natürlich können Sie auch einfach typeof verwenden. Aber mein gesamter Code befindet sich normalerweise sowieso in einer Containing-Funktion, sodass ich mit dieser Methode wahrscheinlich hier und da ein paar Bytes einsparen kann.

0