Creazione dinamica di chiavi nell'array associativo JavaScript


199

Come posso creare dinamicamente le chiavi negli array associativi javascript?

Tutta la documentazione che ho trovato finora è quella di aggiornare le chiavi che sono già state create:

 arr['key'] = val;

Ho una stringa come questa " name = oscar "

E voglio finire con qualcosa del genere:

{ name: 'whatever' }

Cioè ho diviso la stringa e ho il primo elemento, e voglio metterlo in un dizionario.

Codice

var text = ' name = oscar '
var dict = new Array();
var keyValuePair = text.split(' = ');
dict[ keyValuePair[0] ] = 'whatever';
alert( dict ); // prints nothing.

24
Salta il link alla risposta di Eugene per comodità
user56reinstatemonica8

Risposte:


143

Usa il primo esempio. Se la chiave non esiste verrà aggiunta.

var a = new Array();
a['name'] = 'oscar';
alert(a['name']);

Apparirà una finestra di messaggio contenente 'oscar'.

Provare:

var text = 'name = oscar'
var dict = new Array()
var keyValuePair = text.replace(/ /g,'').split('=');
dict[ keyValuePair[0] ] = keyValuePair[1];
alert( dict[keyValuePair[0]] );

L'ho eseguito come esempio in Firefox solo per essere sicuro. Ti sei assicurato di inserire "nome" tra virgolette?
tvanfosson,

1
No, no, perché sto creando la chiave "dinamicamente" non staticamente. Consentitemi di ricontrollare comunque :)
OscarRyz

2
Si prega di fare riferimento alla spiegazione più completa di Danny. Non sarai in grado di fare riferimento ai valori della matrice in un ciclo for con un indice (come myarray [i]). Spero che non sia troppo confuso.
MK_Dev

4
Ancora meglio è usare un oggetto (notazione parentesi {}) per evitare il sovraccarico di avere .length, .slice (), ecc. Che sono inclusi nel prototipo Array
bjornl

488

In qualche modo tutti gli esempi, sebbene funzionino bene, sono troppo complicati:

  • Usano new Array(), che è un overkill (e un overhead) per un semplice array associativo (dizionario AKA).
  • I migliori usano new Object(). Funziona bene, ma perché tutta questa digitazione extra?

Questa domanda è taggata "principiante", quindi rendiamola semplice.

Il modo semplicissimo di usare un dizionario in JavaScript o "Perché JavaScript non ha un oggetto dizionario speciale?":

// create an empty associative array (in JavaScript it is called ... Object)
var dict = {};   // huh? {} is a shortcut for "new Object()"

// add a key named fred with value 42
dict.fred = 42;  // we can do that because "fred" is a constant
                 // and conforms to id rules

// add a key named 2bob2 with value "twins!"
dict["2bob2"] = "twins!";  // we use the subscript notation because
                           // the key is arbitrary (not id)

// add an arbitrary dynamic key with a dynamic value
var key = ..., // insanely complex calculations for the key
    val = ...; // insanely complex calculations for the value
dict[key] = val;

// read value of "fred"
val = dict.fred;

// read value of 2bob2
val = dict["2bob2"];

// read value of our cool secret key
val = dict[key];

Ora cambiamo i valori:

// change the value of fred
dict.fred = "astra";
// the assignment creates and/or replaces key-value pairs

// change value of 2bob2
dict["2bob2"] = [1, 2, 3];  // any legal value can be used

// change value of our secret key
dict[key] = undefined;
// contrary to popular beliefs assigning "undefined" does not remove the key

// go over all keys and values in our dictionary
for (key in dict) {
  // for-in loop goes over all properties including inherited properties
  // let's use only our own properties
  if (dict.hasOwnProperty(key)) {
    console.log("key = " + key + ", value = " + dict[key]);
  }
}

Anche cancellare valori è facile:

// let's delete fred
delete dict.fred;
// fred is removed, the rest is still intact

// let's delete 2bob2
delete dict["2bob2"];

// let's delete our secret key
delete dict[key];

// now dict is empty

// let's replace it, recreating all original data
dict = {
  fred:    42,
  "2bob2": "twins!"
  // we can't add the original secret key because it was dynamic,
  // we can only add static keys
  // ...
  // oh well
  temp1:   val
};
// let's rename temp1 into our secret key:
if (key != "temp1") {
  dict[key] = dict.temp1; // copy the value
  delete dict.temp1;      // kill the old key
} else {
  // do nothing, we are good ;-)
}

2
Ciao, so che sto rispondendo alla vecchia risposta, ma è molto alta su Google, quindi chiederò comunque. Sono un po 'confuso su ciò che "nel nostro esempio non possiamo aggiungere la chiave segreta originale perché era dinamica, possiamo solo aggiungere chiavi statiche".
Karel Bílek,

1
Significa esattamente ciò che dice: non conosciamo il suo valore, quindi non possiamo rappresentarlo come costante, che è necessario quando si specifica una chiave in un oggetto letterale.
Eugene Lazutkin,

3
Tuttavia, "non possiamo aggiungere la chiave segreta originale perché era dinamica" non è di per sé corretta, anche se non è possibile utilizzare una variabile come chiave direttamente in {} o come chiave con notazione punto. Possiamo ancora aggiungere una chiave dinamica tramite "dict [key] = val", come mostrato all'inizio nell'esempio. Il limite è con l'uso della {} notazione, piuttosto che della chiave stessa.
Zut,

8
Sembra la risposta di Sheldon Cooper :)
jpatiaga,

4
risposta completa perfetta, dovrebbe essere l'impostazione predefinita
Dennis Golomazov,

29

Javascript non ha matrici associative , ha oggetti .

Le seguenti righe di codice fanno esattamente la stessa cosa: imposta il campo "name" su un oggetto su "orion".

var f = new Object(); f.name = 'orion';
var f = new Object(); f['name'] = 'orion';
var f = new Array(); f.name = 'orion';
var f = new Array(); f['name'] = 'orion';
var f = new XMLHttpRequest(); f['name'] = 'orion';

Sembra che tu abbia un array associativo perché Arrayè anche un Object- tuttavia non stai affatto aggiungendo cose all'array, stai impostando campi sull'oggetto.

Ora che è stato chiarito, ecco una soluzione funzionante al tuo esempio

var text = '{ name = oscar }'
var dict = new Object();

// Remove {} and spaces
var cleaned = text.replace(/[{} ]/g, '');

// split into key and value
var kvp = cleaned.split('=');

// put in the object
dict[ kvp[0] ] = kvp[1];
alert( dict.name ); // prints oscar.

Supponendo che la stringa di testo abbia effettivamente le parentesi graffe, potresti più o meno trattarla come JSON .. sostituisci il segno = con un: e hai un oggetto da
valutare

1
Spiacenti, la stringa non è delimitata correttamente. Niente regex non può essere risolto.
Neonski,

9

In risposta a MK_Dev, si è in grado di iterare, ma non consecutivamente. (Per questo ovviamente è necessario un array)

La ricerca rapida su Google fa apparire tabelle hash in javascript

Codice di esempio per il looping dei valori in un hash (dal collegamento sopra menzionato):

var myArray = new Array();
myArray['one'] = 1;
myArray['two'] = 2;
myArray['three'] = 3;

// show the values stored
for (var i in myArray) {
    alert('key is: ' + i + ', value is: ' + myArray[i]);
}

5

Codice originale (ho aggiunto i numeri di riga in modo che possano fare riferimento a loro):

1  var text = ' name = oscar '
2  var dict = new Array();
3  var keyValuePair = text.split(' = ');
4  dict[ keyValuePair[0] ] = 'whatever';
5  alert( dict ); // prints nothing.

Quasi lì...

  • riga 1: dovresti fare un trimtesto così com'è name = oscar.
  • linea 3: va bene purché abbiate SEMPRE spazi attorno al vostro pari. potrebbe essere meglio non essere trimnella riga 1, usare =e tagliare ogni keyValuePair
  • aggiungi una riga dopo 3 e prima di 4:

    key = keyValuePair[0];`
  • linea 4: ora diventa:

    dict[key] = keyValuePair[1];
  • riga 5: modifica in:

    alert( dict['name'] );  // it will print out 'oscar'

Quello che sto cercando di dire è che dict[keyValuePair[0]]non funziona, devi impostare una stringa keyValuePair[0]e usarla come chiave associativa. Questo è l'unico modo per far funzionare la mia. Dopo averlo impostato, puoi fare riferimento ad esso con un indice numerico o digitare le virgolette.

Spero che aiuti.


4

Tutti i browser moderni supportano una mappa , che è una limitazione dei dati chiave / valore. Ci sono un paio di ragioni che rendono l'utilizzo di una mappa migliore di Object:

  • Un oggetto ha un prototipo, quindi ci sono chiavi predefinite nella mappa.
  • Le chiavi di un oggetto sono stringhe, dove possono avere qualsiasi valore per una mappa.
  • Puoi ottenere facilmente le dimensioni di una mappa mentre devi tenere traccia delle dimensioni di un oggetto.

Esempio:

var myMap = new Map();

var keyObj = {},
    keyFunc = function () {},
    keyString = "a string";

myMap.set(keyString, "value associated with 'a string'");
myMap.set(keyObj, "value associated with keyObj");
myMap.set(keyFunc, "value associated with keyFunc");

myMap.size; // 3

myMap.get(keyString);    // "value associated with 'a string'"
myMap.get(keyObj);       // "value associated with keyObj"
myMap.get(keyFunc);      // "value associated with keyFunc"

Se desideri che le chiavi a cui non viene fatto riferimento da altri oggetti vengano raccolte in modo inutile, prendi in considerazione l'utilizzo di una WeakMap anziché di una mappa.



1
var myArray = new Array();
myArray['one'] = 1;
myArray['two'] = 2;
myArray['three'] = 3;
// show the values stored
for (var i in myArray) {
    alert('key is: ' + i + ', value is: ' + myArray[i]);
}

questo è ok ma scorre attraverso ogni proprietà dell'oggetto array. se vuoi iterare solo attraverso le proprietà myArray.one, myArray.two ... prova così

myArray['one'] = 1;
myArray['two'] = 2;
myArray['three'] = 3;
myArray.push("one");
myArray.push("two");
myArray.push("three");
for(i=0;i<maArray.length;i++{
    console.log(myArray[myArray[i]])
}

ora puoi accedere ad entrambi tramite myArray ["one"] e iterare solo attraverso queste proprietà.


Hai contato il conteggio dei mistypes nel tuo esempio? :-) maArray, dimenticato dimenticato ')' ...
Brian Haak,

Grazie per l'esempio Potremmo unirci Arraye Objectlavorare solo con gli Objectalberi! Intuizione meravigliosa! È molto utile da fare Object.getOwnPropertyNames(obj/array)!
Brian Haak,

1
var obj = {};

                for (i = 0; i < data.length; i++) {
                    if(i%2==0) {
                        var left = data[i].substring(data[i].indexOf('.') + 1);
                        var right = data[i + 1].substring(data[i + 1].indexOf('.') + 1);

                        obj[left] = right;
                        count++;
                    }
                }
                console.log("obj");
                console.log(obj);
                // show the values stored
                for (var i in obj) {
                    console.log('key is: ' + i + ', value is: ' + obj[i]);
                }

            }
        };

}

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.