2010-01-17 13 views
16

Gibt es eine Möglichkeit, ein Objekt in Javascript falsch zurückgeben?Kann ein Objekt falsch sein?

var obj = new Object(); 

console.log(!!obj) // prints "true" even if it's empty 

Antwort

20

Nein. Ein Objekt, dem keine Eigenschaften zugewiesen sind, wird nicht als "leer" betrachtet.

Die Tatsache, dass eine Variable eine Instanz eines Objekts enthält, genügt, damit JavaScript die Variable mit dem Wert true behandelt, wenn ein Ausdruck einen booleschen Wert erfordert.

bearbeiten

Es gibt eindeutig einige Nuancen hier Blick auf die anderen Antworten geklärt werden.

null ist nicht ein Objekt, es ist das deutliche Fehlen eines Objekts. Die Frage bezieht sich auf ein Objekt, das gerade erstellt wurde.

+1

Beachten Sie, dass sogar 'new Boolean (false)' als 'wahr' gilt. Also nein, alle Objekte sind wahr. – Thilo

5

Nein, aber null wird false konvertieren.

> typeof(null) 
"object" 
> null instanceof Object 
false 
> !!null 
false 

Um zu sehen, ob das Objekt alle Eigenschaften enthält, verwenden (schamlos von How do I count a JavaScript object's attributes? kopiert):

function isEmpty (obj) { 
    for (var k in obj) 
     if (obj.hasOwnProperty(k)) 
      return false; 
    return true; 
} 
+3

, um Dinge zu klären: 'null' ist ein primitiver Wert vom Typ 'Null' und kein Objekt; es ist nur, dass "typeof" ist etwas gebrochen – Christoph

+0

'typeof' ist ein JS-Schlüsselwort keine Funktion. Die Klammern sind nicht erforderlich. –

+1

@Web_Designer: Ich weiß, aber denke, es ist nur auf diese Weise klarer. – kennytm

5

A null "Objekt" (wirklich Wert) falsch zurück.

var obj = null; 

console.log(!!obj); 

Wenn Sie überprüfen wollen, ob es keine Eigenschaften hat, können Sie versuchen:

var obj = new Object(); 
var empty = true; 
for (var p in obj) { 
    if (obj.hasOwnProperty(p)) { 
     empty = false; 
     break; 
    } 
} 
console.log(empty); 
+0

null ist kein Objekt. – Taurus

2

Ich denke, dass mit dem ersten ! Sie obj auf eine boolean werfen und negiert seine wert- was true wenn obj ist Null -, und mit dem zweiten ! es wieder negieren.

+1

Nein, das erste '!' Wandelt das Objekt in den Booleschen Zustand * und negiert es dann. Das zweite '!' Negiert es wieder *, so dass das Endergebnis dem Booleschen Objekt entspricht. Der Fragesteller hat keine Probleme in dieser Aussage. – kennytm

+0

Natürlich danke für die Korrektur. Bearbeitet. –

3

Nr

nicht sicher, warum Sie dies wünschen würde, aber es gibt einen Weg Sie etwas wie dies tun könnte, aber es ist irgendwie Hacky ...

var obj = { 
    toString: function() { return ''; } 
}; 

alert(!! (''+obj)); 
+1

Ein möglicher Grund: Sie haben Code, der einen Boolean umgeht. Jetzt wollen Sie diesen Code so ändern, dass im 'false'-Fall auch ein Grund dafür angegeben wird, warum der Wert false ist. Wenn Sie etwas für Boolesche Operationen als falsch erscheinen lassen, aber auch zusätzliche Daten anhängen, muss der vorhandene Code nicht geändert werden. Leider scheint dies nicht möglich zu sein. – joeytwiddle

0

In Ihrem Fall

console.log(!obj); wird false zurückgeben.

weil ein Objekt oder ein leeres Objekt immer ein Truthy ist.

1

Wir Object.prototype.valueOf überschreiben können, ein Objekt zu machen scheinen falsch zu sein, wenn es in eine primitiven dazu gezwungen, zum Beispiel während ==.

aber es nicht erscheinen falsch sein, wenn wir es in einen boolean mit !! zwingen, so ist es nicht wirklich im allgemeinen Fall arbeiten.

var obj = { 
    valueOf: function() { 
     return false 
    } 
} 

> obj == false 
true    // Good, we fooled them! 

> !!obj 
true    // Not so good, we wanted false here 

> Boolean(obj) 
true    // Not so good, we wanted false here 
0

In Konsole:

> ({})?true:false 
< true 

So ist die Antwort nein.

6

Ab ES8, nein, können Sie nicht bewirken, dass ein Objekt in JavaScript als false ausgewertet wird.

In der Beschreibung sind alle boolean Kontrollen (?!if etc.) hängt von ToBoolean,
das ist sehr, sehr einfach:

  • False, wenn nicht definiert, null, false, null, NaN, oder leere Zeichenfolge.
  • gilt für alles andere (Object, Proxy, Symbol, usw.)

Wenn der Typ des Eingabeobjekts ist, ist das Ergebnis true. Keine Frage gestellt. No valueOf, kein Sonderfall.

Es gibt keine Möglichkeit, ein Falsy-Objekt in JavaScript zu erstellen. Nur Nicht-Objekte können falsch sein.

Manchmal können Sie in Objekt-wie "Zeug" laufen, die falsch zurückgeben. Leere Zeichenfolge, zum Beispiel wie ein Objekt die ganze Zeit verwendet. document.all ist ein weiteres falsches "Objekt".

Dies sind jedoch keine realen Objekte. Sie können keine benutzerdefinierten Eigenschaften haben, können nicht als Prototyp verwendet werden und verhalten sich nicht immer wie ein Objekt, z. typeof oder streng gleich.

Dieses Verhalten ist höchstwahrscheinlich hier, um Abwärtskompatibilität zu erhalten.

+1

Oh, dieses Dokument ist interessant. Obwohl es tatsächlich ein echtes Objekt zu sein scheint. Sie * können * benutzerdefinierte Eigenschaften hinzufügen, sie * können * als Prototyp verwendet werden und sie * verhält sich * wie ein Objekt mit strengem Gleichheitszeichen. Es gibt nur vor, "undefiniert" zu sein, wenn es mit "typeof", loose equal oder 'ToBoolean' verwendet wird. Trotzdem hilft das wahrscheinlich nicht, es sei denn, Sie opfern ein neues "document.implementation.createHTMLDocument(). All", wenn Sie ein falsches Objekt benötigen. – Robert

+1

@Robert Das Problem ist, solche Anwendungen sind außerhalb der Spezifikation und Browser abhängig. IE 11 gibt "undefined" für "Object.create (document.all)" zurück, und in anderen Browsern haben Sie die Falsy-Eigenschaft verloren.In Firefox 52 können Sie keine numerischen Eigenschaften zuweisen. Kurz gesagt, die Verwendung von nativen Objekten als Falsy-Objekt wird von es oder dom spec nicht unterstützt, und Sie riskieren, dass zukünftige Browser Ihren Code auf eine Art und Weise brechen, die schwer zu debuggen und zu beheben ist. – Sheepy

+0

sicher. Ich habe nur gesagt, dass es als Prototyp benutzt werden kann. Nicht einmal sicher, ob es in allen Browsern funktioniert. Aber natürlich ist die Prototyp-Kette nicht an der Überprüfung von Falschheit beteiligt, so dass es nicht wirklich wichtig ist. Interessanterweise weigert sich IE11, das Ergebnis von "Object.create (document.all)" in der Konsole anzuzeigen, aber immer noch "Object.create (document.all) .__ proto__ === document.all" in meinem Test. Was die nicht beschreibbaren Eigenschaften anbelangt, so steht natürlich eine Menge Magie dahinter und jeder Browser scheint sich in dieser Hinsicht anders zu verhalten. – Robert

Verwandte Themen