Domanda

Se ho un oggetto JavaScript, ad esempio

var myObject = new Object();
myObject["firstname"] = "Gareth";
myObject["lastname"] = "Simpson";
myObject["age"] = 21;

esiste un modo migliore integrato o accettato per ottenere la lunghezza di questo oggetto?

È stato utile?

Soluzione

La risposta più robusta (es.che cattura l'intento di ciò che stai cercando di fare causando il minor numero di bug) sarebbe:

Object.size = function(obj) {
    var size = 0, key;
    for (key in obj) {
        if (obj.hasOwnProperty(key)) size++;
    }
    return size;
};

// Get the size of an object
var size = Object.size(myObj);

C'è una sorta di convenzione in JavaScript secondo cui tu non aggiungere cose a Object.prototype, perché può interrompere le enumerazioni in varie librerie.Tuttavia, l'aggiunta di metodi a Object è generalmente sicura.


Ecco un aggiornamento a partire dal 2016 e diffusione diffusa di ES5 e oltre. Per IE9+ e tutti gli altri browser moderni compatibili con ES5+, puoi utilizzare Object.keys() quindi il codice sopra diventa semplicemente:

var size = Object.keys(myObj).length;

Da allora questo non deve modificare alcun prototipo esistente Object.keys() è ora integrato.

Modificare:Gli oggetti possono avere proprietà simboliche che non possono essere restituite tramite il metodo Object.key.Quindi la risposta sarebbe incompleta senza menzionarli.

Il tipo di simbolo è stato aggiunto al linguaggio per creare identificatori univoci per le proprietà degli oggetti.Il vantaggio principale del tipo Symbol è la prevenzione delle sovrascritture.

Object.keys O Object.getOwnPropertyNames non funziona per le proprietà simboliche.Per restituirli è necessario utilizzare Object.getOwnPropertySymbols.

var person = {
  [Symbol('name')]: 'John Doe',
  [Symbol('age')]: 33,
  "occupation": "Programmer"
};

const propOwn = Object.getOwnPropertyNames(person);
console.log(propOwn.length); // 1

let propSymb = Object.getOwnPropertySymbols(person);
console.log(propSymb.length); // 2

Altri suggerimenti

Se lo sai non devi preoccuparti hasOwnProperty controlli, puoi farlo in modo molto semplice:

Object.keys(myArray).length

Aggiornato:Se stai usando Sottolineato.js (consigliato, è leggero!), allora puoi semplicemente farlo

_.size({one : 1, two : 2, three : 3});
=> 3

Altrimenti, e non vuoi scherzare con le proprietà dell'oggetto per nessun motivo e stai già utilizzando jQuery, un plug-in è ugualmente accessibile:

$.assocArraySize = function(obj) {
    // http://stackoverflow.com/a/6700/11236
    var size = 0, key;
    for (key in obj) {
        if (obj.hasOwnProperty(key)) size++;
    }
    return size;
};

Ecco la soluzione più cross-browser.

Questa è migliore della risposta accettata perché utilizza Object.keys nativo se esiste.Pertanto, è il più veloce per tutti i browser moderni.

if (!Object.keys) {
    Object.keys = function (obj) {
        var arr = [],
            key;
        for (key in obj) {
            if (obj.hasOwnProperty(key)) {
                arr.push(key);
            }
        }
        return arr;
    };
}

Object.keys(obj).length;

Non sono un esperto di JavaScript, ma sembra che dovresti scorrere gli elementi e contarli poiché Object non ha un metodo di lunghezza:

var element_count = 0;
for (e in myArray) {  if (myArray.hasOwnProperty(e)) element_count++; }

@palmsey:In tutta onestà verso l'OP, la documentazione JavaScript in realtà si riferisce esplicitamente all'utilizzo di variabili di tipo Object in questo modo come "array associativi".

Questo metodo ottiene tutti i nomi delle proprietà del tuo oggetto in un array, in modo da poter ottenere la lunghezza di tale array che è uguale alla lunghezza delle chiavi del tuo oggetto.

Object.getOwnPropertyNames({"hi":"Hi","msg":"Message"}).length; // => 2

Per non scherzare con il prototipo o altro codice, potresti creare ed estendere il tuo oggetto:

function Hash(){
    var length=0;
    this.add = function(key, val){
         if(this[key] == undefined)
         {
           length++;
         }
         this[key]=val;
    }; 
    this.length = function(){
        return length;
    };
}

myArray = new Hash();
myArray.add("lastname", "Simpson");
myArray.add("age", 21);
alert(myArray.length()); // will alert 2

Se usi sempre il metodo add, la proprietà length sarà corretta.Se temi che tu o altri dimentichiate di usarlo, potresti aggiungere anche il contatore delle proprietà che gli altri hanno pubblicato al metodo della lunghezza.

Naturalmente, potresti sempre sovrascrivere i metodi.Ma anche se lo facessi, il tuo codice probabilmente fallirebbe notevolmente, facilitando il debug.;)

Il più semplice è

Object.keys(myObject).length

Ecco come fare e non dimenticare di controllare che la proprietà non sia sulla catena del prototipo:

var element_count = 0;
for(var e in myArray)
    if(myArray.hasOwnProperty(e))
        element_count++;

Usalo semplicemente per ottenere il file length:

Object.keys(myObject).length

In alcuni casi è meglio memorizzare semplicemente la dimensione in una variabile separata.Soprattutto se stai aggiungendo all'array un elemento in un unico posto e puoi facilmente incrementare la dimensione.Ovviamente funzionerebbe molto più velocemente se fosse necessario controllare spesso le dimensioni.

Ecco una soluzione completamente diversa che funzionerà solo con i browser più moderni (IE9+, Chrome, Firefox 4+, Opera 11.60+, Safari 5.1+)

Vedere jsFiddle

Imposta la tua classe Array associativo

/**
 * @constructor
 */
AssociativeArray = function () {};

// Make the length property work
Object.defineProperty(AssociativeArray.prototype, "length", {
    get: function () {
        var count = 0;
        for (var key in this) {
            if (this.hasOwnProperty(key))
                count++;
        }
        return count;
    }
});

Ora puoi utilizzare questo codice come segue...

var a1 = new AssociativeArray();
a1["prop1"] = "test";
a1["prop2"] = 1234;
a1["prop3"] = "something else";
alert("Length of array is " + a1.length);

Utilizzo:

var myArray = new Object();
myArray["firstname"] = "Gareth";
myArray["lastname"] = "Simpson";
myArray["age"] = 21;
obj = Object.keys(myArray).length;
console.log(obj)

@palmsey:In tutta onestà verso l'OP, i documenti javascript in realtà si riferiscono esplicitamente all'utilizzo di variabili di tipo Object in questo modo come "array associativi".

E in tutta onestà nei confronti di @palmsey aveva ragione, non sono array associativi, sono sicuramente oggetti :) - facendo il lavoro di un array associativo.Ma per quanto riguarda il punto più ampio, sembra che tu ne abbia decisamente ragione, secondo questo articolo piuttosto bello che ho trovato:

Gli “array associativi” JavaScript sono considerati dannosi

Ma secondo tutto questo, non è così risposta accettata stessa cattiva pratica?

Specificare una funzione prototipo size() per Object

Se è stato aggiunto qualcos'altro a Object .prototype, il codice suggerito fallirà:

<script type="text/javascript">
Object.prototype.size = function () {
  var len = this.length ? --this.length : -1;
    for (var k in this)
      len++;
  return len;
}
Object.prototype.size2 = function () {
  var len = this.length ? --this.length : -1;
    for (var k in this)
      len++;
  return len;
}
var myArray = new Object();
myArray["firstname"] = "Gareth";
myArray["lastname"] = "Simpson";
myArray["age"] = 21;
alert("age is " + myArray["age"]);
alert("length is " + myArray.size());
</script>

Non penso che la risposta dovrebbe essere quella accettata in quanto non ci si può fidare che funzioni se hai altro codice in esecuzione nello stesso contesto di esecuzione.Per farlo in modo affidabile dovresti sicuramente definire il metodo size all'interno di myArray e controllare il tipo dei membri mentre li scorri.

Che ne dici di qualcosa del genere...

function keyValuePairs() {
    this.length = 0;
    function add(key, value) { this[key] = value; this.length++; }
    function remove(key) { if (this.hasOwnProperty(key)) { delete this[key]; this.length--; }}
}

Se abbiamo l'hashish

cancelletto = {"a" :"avanti Cristo":"D"};

possiamo ottenere la lunghezza usando la lunghezza delle chiavi che è la lunghezza dell'hash:

chiavi(hash).lunghezza

Se stai usando AngularJS 1.x puoi fare le cose in modo AngularJS creando un filtro e utilizzando il codice di uno qualsiasi degli altri esempi come il seguente:

// Count the elements in an object
app.filter('lengthOfObject', function() {
  return function( obj ) {
    var size = 0, key;
    for (key in obj) {
      if (obj.hasOwnProperty(key)) size++;
    }
   return size;
 }
})

Utilizzo

Nel controller:

$scope.filterResult = $filter('lengthOfObject')($scope.object)

Oppure secondo te:

<any ng-expression="object | lengthOfObject"></any>

<script>
myObj = {"key1" : "Hello", "key2" : "Goodbye"};
var size = Object.keys(myObj).length;
console.log(size);
</script>

<p id="myObj">The number of <b>keys</b> in <b>myObj</b> are: <script>document.write(size)</script></p>

Questo funziona per me:

var size = Object.keys(myObj).length;

Se hai bisogno di una struttura dati associativa che ne esponga le dimensioni, è meglio utilizzare una mappa invece di un oggetto.

var myMap = new Map();
myMap.set("firstname", "Gareth");
myMap.set("lastname", "Simpson");
myMap.set("age", 21);
myMap.size; // 3

Una variazione su alcuni dei precedenti è:

var objLength = function(obj){    
    var key,len=0;
    for(key in obj){
        len += Number( obj.hasOwnProperty(key) );
    }
    return len;
};

È un modo un po' più elegante per integrare hasOwnProp.

Se non ti interessa supportare Internet Explorer 8 o versioni precedenti, puoi facilmente ottenere il numero di proprietà in un oggetto applicando i due passaggi seguenti:

  1. Corri o Object.keys() per ottenere un array che contenga i nomi solo delle proprietà che lo sono enumerabile O Object.getOwnPropertyNames() se vuoi includere anche i nomi delle proprietà che non sono enumerabili.
  2. Ottenere il .length proprietà di quell'array.

Se hai bisogno di farlo più di una volta, potresti racchiudere questa logica in una funzione:

function size(obj, enumerablesOnly) {
    return enumerablesOnly === false ?
        Object.getOwnPropertyNames(obj).length :
        Object.keys(obj).length;
}

Come utilizzare questa particolare funzione:

var myObj = Object.create({}, {
    getFoo: {},
    setFoo: {}
});
myObj.Foo = 12;

var myArr = [1,2,5,4,8,15];

console.log(size(myObj));        // Output : 1
console.log(size(myObj, true));  // Output : 1
console.log(size(myObj, false)); // Output : 3
console.log(size(myArr));        // Output : 6
console.log(size(myArr, true));  // Output : 6
console.log(size(myArr, false)); // Output : 7

Guarda anche questo violino per una dimostrazione.

var myObject = new Object();
myObject["firstname"] = "Gareth";
myObject["lastname"] = "Simpson";
myObject["age"] = 21;
  1. Oggetto.valori(miooggetto).lunghezza
  2. Voci.oggetto(miooggetto).lunghezza
  3. Oggetto.chiavi(miooggetto).lunghezza

Ecco una versione diversa della risposta di James Cogan.Invece di passare un argomento, crea semplicemente il prototipo della classe Object e rendi il codice più pulito.

Object.prototype.size = function () {
    var size = 0,
        key;
    for (key in this) {
        if (this.hasOwnProperty(key)) size++;
    }
    return size;
};

var x = {
    one: 1,
    two: 2,
    three: 3
};

x.size() === 3;

esempio di jsfiddle: http://jsfiddle.net/qar4j/1/

Puoi semplicemente usare Object.keys(obj).length su qualsiasi oggetto per ottenere la sua lunghezza.Object.keys restituisce un array contenente tutto l'oggetto chiavi (proprietà) che possono tornare utili per trovare la lunghezza di quell'oggetto utilizzando la lunghezza dell'array corrispondente.Puoi anche scrivere a funzione per questo.Prendiamo creativo e scrivi a metodo anche per questo (insieme a una proprietà getter più comoda):

function objLength(obj)
{
  return Object.keys(obj).length;
}

console.log(objLength({a:1, b:"summit", c:"nonsense"}));

// Works perfectly fine
var obj = new Object();
obj['fish'] = 30;
obj['nullified content'] = null;
console.log(objLength(obj));

// It also works your way, which is creating it using the Object constructor
Object.prototype.getLength = function() {
   return Object.keys(this).length;
}
console.log(obj.getLength());

// You can also write it as a method, which is more efficient as done so above

Object.defineProperty(Object.prototype, "length", {get:function(){
    return Object.keys(this).length;
}});
console.log(obj.length);

// probably the most effictive approach is done so and demonstrated above which sets a getter property called "length" for objects which returns the equivalent value of getLength(this) or this.getLength()

Il modo più semplice è così

Object.keys(myobject).length

dove miooggetto è l'oggetto di cui vuoi la lunghezza

Puoi sempre farlo Object.getOwnPropertyNames(myObject).length per ottenere lo stesso risultato di [].length darebbe per un array normale.

Di seguito è riportata una versione della risposta di James Coglan in CoffeeScript per coloro che hanno abbandonato JavaScript diretto :)

Object.size = (obj) ->
  size = 0
  size++ for own key of obj
  size

Proprietà

Object.defineProperty(Object.prototype, 'length', {
    get: function () {
        var size = 0, key;
        for (key in this)
            if (this.hasOwnProperty(key))
                size++;
        return size;
    }
});

Utilizzo

var o = {a: 1, b: 2, c: 3};
alert(o.length); // <-- 3
o['foo'] = 123;
alert(o.length); // <-- 4

Possiamo trovare la lunghezza di Object utilizzando:

Object.values(myObject).length

È un po' tardi per il gioco, ma un buon modo per raggiungere questo obiettivo (solo IE9+) è definire un getter magico sulla proprietà length:

Object.defineProperty(Object.prototype, "length", {
    get: function () {
        return Object.keys(this).length;
    }
});

E puoi semplicemente usarlo in questo modo:

var myObj = { 'key': 'value' };
myObj.length;

Darebbe 1.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top