Domanda

questo è il mio frammento di codice, in cui il programma non entra nel ciclo foreach:

var ct = new Array();
ct["me"]= {"name" : "Jakub"};
ct["you"]= {"name" : "stack"};
ct.forEach(function (c){
    document.getElementById("tmp").appendChild(document.createTextNode(c));
});

Quando cambio gli indici degli array da stringhe ( "me", "tu") a numeri interi, funziona:

var ct = new Array();
ct[0]= {"name" : "Jakub"};
ct[1]= {"name" : "stack"};
ct.forEach(function (c){
    document.getElementById("tmp").appendChild(document.createTextNode(c));
});

Potete aiutarmi per implementare la soluzione per scorrere i array con tutti i tipi di indici? Il mio obiettivo è quello di memorizzare i valori per determinati oggetti di data.


utilizzo i dati per il Protovis biblioteca e AFAIK ha bisogno di una matrice come input.

La struttura dati che uso nell'esempio Protovis è più complicata mostrato sopra questa.

Nel mio progetto ho inviare via JavaBean l'insieme di alcuni oggetti. Coloro oggetto contiene tra le altre cose la data. Il mio obiettivo è quello di mostrare gli oggetti sul grafico come questo, ha presentato sul sito Protovis http: //. Vis.stanford.edu / Protovis / ex / area.html

I userà l'asse orizzontale per il tempo e l'asse verticale per numero di oggetti per un dato tempo. Ecco perché voglio avere la matrice filtrate per data, poiché AFAIK Protovis solo permette array come base di dati per i loro schemi nella modalità predefinita - funzione concatenamento.

modifica: Per ora ho cambiato il metodo. Invece di memorizzare stringhe come chiavi dell'array Io seguenti: la presente è il mio frammento di codice originale:
edit2 : ho aggiunto un po 'di input originale: var result2 = { "h": { 10 "documenti": [ 11 { 12 "biographicalCategories": [ 13], 14 "corpo": "Il governo conservatore greco ha ordinato un'indagine su un accordo del 1955 tra la C.I.A. ed il militare greca per la creazione di una rete di guerriglia per combattere le forze d'invasione del Patto di Varsavia in caso di una guerra", 15 "descrittori": [ 16], 17 "generalOnlineDescriptors": [ 18], 19 "guid": 0, 20 "titolo": "La Grecia per Indagare Piano per guerriglia", 21 "sedi": [ 22 "Grecia" 23], 24 "nomi": [ 25], 26 "onlineDescriptors": [ 27], 28 "onlineLocations": [ 29], 30 "onlineOrganizations": [ 31], 32 "onlinePeople": [ 33], 34 "onlineTitles": [ 35], 36 "organizzazioni": [ 37], 38 "persone": [ 39], 40 "publicationdate": "1990/11/21 00: 00: 00.0 CET", 41 "sourceFile": "0402635.xml", 42 "taxonomicClassifiers": [ 43], 44 "titoli": [ 45], 46 "typesOfMaterial": [ 47], 48 "punteggio": ,80,242133 millions 49},


var resultTmp = new Array();
var i = 0;
var averageScore = 0; 

var startDate = new Date();
var endDate = new Date(1700, 01, 01);
var docDate;
var actDate;

var tlk = new Array();
var av = 0;
var d = new Object();

result2.h.documents.forEach(function(c) {
    averageScore += c.score;
  if(typeof(c.publicationDate) != "undefined"){
    docDate = c.publicationDate.split("-");
    actDate = new Date(docDate[0], docDate[1]-1, docDate[2].split(" ")[0]);
    if(actDate  endDate){
        endDate = actDate;
    }
    if(defined(tlk[actDate])){
        av = tlk[actDate];
        resultTmp[av].docs.push(c);
    }
    else {
        d = new Object();
        d.date = actDate;
        d.docs = new Array();
        d.docs.push(c);
        resultTmp[i] = d;
        tlk[actDate] = i;
        i++;
    }
  }
});

i = 0;
var dates = [];
for(key in tlk){
    if(key )
        d = new Date(key);
    if(isValidDate(d)){
    dates[i] = new Date(key);
    i++;        
    }
}
dates.sort(function (a, b) {
    return a > b;
});

var ii = 0;
i = 0;
var ddocs;
var result = new Array();
for(i=0; i maxDocsPerDate){
            maxDocsPerDate = d.docs.length;
        } 
        result[i] = d;
}


Edit3 il codice di cui sopra sta lavorando ora:

In poche parole: io uso la matrice tlk per riflettere la data per l'indice. Per un indice nella matrice resultTmp I memorizzare la data e l'insieme di oggetti relativi a quella data. La parte successiva di utilizzo codice che ho per ordinare le date dal più vecchio al più nuovo e analogamente sorta la resultTemp. La versione ordinata di resultTemp è nel Array risultato.

I dati presenti in Protovis nel seguente modo:


vis.add(pv.Line)
    .data(result)
    .lineWidth(2)
    .left(function(a) x(a.date))
    .bottom(function(a) y(a.docs.length))
    .add(pv.Dot)
    .lineWidth(function(a) a.docs.length - (a.docs.length-1)/3)
    .radius(function(a) a.docs.length * (a.docs.length/1.2))
    .fillStyle(function(a) color(a.docs.length))
    .event("click", function(a) Popup.show(a.docs))
    .anchor("top").add(pv.Label)
    .text(function(a) a.docs.length)
    .textBaseline("bottom");

vis.render();

Gli sguardi di risultato esemplare come: i.imgur.com / WODYA.png
Non ho incluso il codice per stampare gli assi xey come pure per scalare dalla data alla larghezza grafico. Si possono trovare esempi nella pagina Protovis esempi.

A proposito: Sono confuso perché nella parte:

for(key in tlk){
    dates[i] = new Date(key);
    i++;
}

Come l'ultimo tasto ottengo "contiene"? Ho cercato di trovare risposta su Internet, senza successo. Orsi ha spiegato nel suo commento che il motivo ottengo questo problema soltanto è perché io sono l'iterazione sulle proprietà di matrice.

È stato utile?

Soluzione

matrici JavaScript supportano solo indicizzazione numero. Quando si scrive

ct["me"]= {"name" : "Jakub"};
ct["you"]= {"name" : "stack"};

si sta aggiungendo ad hoc proprietà me e you alla matrice; sei non elementi per la matrice aggiunta. (Anche utilizzando il costruttore new Array() è un po 'strano. Se si desidera un array, utilizzare il letterale [].)

Sembra che si dovrebbe usare un oggetto JavaScript, non un array, ma essere consapevoli che essi supportano solo indici di stringa.

var ct = {};
ct['me'] = {name: 'Jakub'};
ct['you'] = {name: 'stack'};

for (var k in ct) {
    document.getElementById('tmp', appendChild(document.createTextNode(ct[k]));
}

Modifica Se si vuole trattare l'asse orizzontale, come il tempo, davvero non c'è bisogno di fare molto più lavoro. C'è un buon esempio di base qui ; visualizzare il sorgente della pagina per vedere il codice. Il trucco è che, mentre i dati sono davvero un array (di oggetti), l'ascissa è esplicitamente come una proprietà piuttosto che come indice nell'array dati. Ogni elemento della matrice simile a questa:

>>> data[0]
    {x: /* some JavaScript date object */, y: /* some number */ }

Fonti:


Modifica. 2: Hai ancora sembri confuso sugli array contro oggetti

Per quanto riguarda il vostro "BTW": quando si scrive si for(key in tlk) ... Non Sei iterazione delle chiavi che si trovano già nella matrice. Questo è il trattamento della matrice come un oggetto, e che non è quello che vuoi! Si vede contains perché l'iterazione siete oltre le proprietà di una matrice, e contains è una funzione collegata ad ogni array (stai usando prototipo, o un'altra libreria simile?).

Il problema di fondo, tuttavia, è che sei l'indicizzazione in un array (tlk) utilizzando un Data. Questo è un grande no-no; anche se tlk è un oggetto, perché si può solo indice oggetti utilizzando stringhe . Io davvero non capisco quello che stai facendo con tlk, ma non credo che ne avete bisogno a tutti. Qual è la forma dei dati di ingresso? Se potete darmi un piccolo esempio di ingresso, posso probabilmente mostrerà che cosa fare con esso.

Inoltre, si dovrebbe davvero usare array e di oggetto letterali piuttosto che i costruttori Array e Object. Ad esempio, l'uso var tlk = [] piuttosto che var tlk = new Array();, e var d = {}; piuttosto che var d = new Object();.

Altri suggerimenti

JavaScript non ha array associativi, il par se. Gli oggetti hanno chiamato proprietà, però, che è simile. foreach () solo iterare sopra indicizzati proprietà. Un ciclo for...in vi aiuterà a qui, anche se in generale si dovrebbe evitare di utilizzare for...in su array perché si itera proprietà nel nome troppo.

for (var c in ct) {
    if (ct.hasOwnProperty(c)) {
        // do something
    }
}

Vedi anche:

Il metodo Array.prototype.forEach attraversa la matrice su relativi indici numerici.

Gli array non sono 'associative', se si vuole avere proprietà denominate con valori si dovrebbe usare un oggetto semplice, e utilizzare l'istruzione for-in per enumerare le proprietà esistenti:

var ct = {};
ct["me"]= {"name" : "Jakub"};
ct["you"]= {"name" : "stack"};

for (var prop in ct) {
  if (ct.hasOwnProperty(prop)) {
    alert(ct[prop]);
  }
}

Il metodo hasOwnProperty viene chiamato perché le proprietà di traslazione dichiarazione for-in che sono ereditati, in che modo sarà elencare solo le proprietà che esistono fisicamente sull'oggetto (proprie caratteristiche).

È possibile utilizzare if (Object.prototype.hasOwnProperty.call(ct, prop)) invece di if (ct.hasOwnProperty(prop)) per una maggiore sicurezza, perché se l'oggetto ha una proprietà denominata "hasOwnProperty", non sarà il metodo che si desidera eseguire.

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