Ottieni l'ultimo elemento in un array


1142

Ecco il mio codice JavaScript finora:

var linkElement = document.getElementById("BackButton");
var loc_array = document.location.href.split('/');
var newT = document.createTextNode(unescape(capWords(loc_array[loc_array.length-2]))); 
linkElement.appendChild(newT);

Attualmente richiede il penultimo elemento dell'array dall'URL. Tuttavia, voglio fare un controllo per l'ultimo elemento dell'array "index.html"e, in tal caso, afferrare invece il terzo all'ultimo elemento.

Risposte:


1226
if (loc_array[loc_array.length - 1] === 'index.html') {
   // do something
} else {
   // something else
}

Nel caso in cui il server serve la stessa lima per "index.html" e "index.html" è anche possibile utilizzare: .toLowerCase().

Tuttavia, potresti prendere in considerazione l'idea di fare questo lato server, se possibile: sarà più pulito e funzionerà per le persone senza JS.


se hai solo bisogno dell'ultimo articolo puoi Array.pop ()
— Badri Derakhshan

1052

Non sono sicuro che ci sia un inconveniente, ma questo sembra abbastanza conciso:

arr.slice(-1)[0] 

o

arr.slice(-1).pop()

Entrambi restituiranno undefinedse l'array è vuoto.


32
anche usare la destrutturazione è bello:const [lastItem] = arr.slice(-1)
— diachedelico l'

@diachedelic questo è il modo più elegante! Eccezionale!
— Trufa,

2
.pop()rimuove l'ultimo elemento che modifica l'array originale. Non è lo stesso del semplice recupero di quel valore.
— Badrush,

4
@Badrush slice () crea un nuovo array con una copia di un singolo elemento e pop modifica solo quella copia. l'array originale rimane illeso
— kritzikratzi

Ma dovresti evitare di creare nuove matrici a meno che questo codice non venga chiamato spesso. Altrimenti metterà a dura prova la raccolta dei rifiuti e / o farà utilizzare più memoria al browser.
— mvmn

259

Usa Array.pop :

var lastItem = anArray.pop();

Importante : questo restituisce l'ultimo elemento e lo rimuove dall'array


165

Una versione più breve di ciò che ha pubblicato @chaiguy:

Array.prototype.last = function() {
    return this[this.length - 1];
}

La lettura dell'indice -1 ritorna undefinedgià.

MODIFICARE:

In questi giorni la preferenza sembra usare i moduli ed evitare di toccare il prototipo o utilizzare uno spazio dei nomi globale.

export function last(array) {
    return array[array.length - 1];
}

8
Se non è ovvio come questo è da effettivamente utilizzato, ecco un esempio: var lastItem = [3,2,1,5].last();. Il valore di lastItemè 5.
— user128216

7
Questa risposta è corretta e anche abbastanza pulita MA (!!!) Una regola empirica che usa Javascript è quella Do NOT modify objects you Do NOT own. È pericoloso a causa di molte ragioni, come ad esempio 1. Altri sviluppatori che lavorano nel tuo team potrebbero confondersi in quanto questo metodo non è standard 2. con qualsiasi aggiornamento nelle librerie o anche utilizzando una versione ECMAScript inferiore o superiore potrebbe facilmente perdere PERSO!
— Farzad YZ,

1
Per chiunque si chieda, questo rompe Array.forEach (). Sono ancora d'accordo sul fatto che la modifica dei prototipi non è la cosa peggiore in circolazione, ma questa è negativa.
— Seph Reed,

1
Imo non c'è un grosso problema con la modifica Array.prototype, ma dovresti usare Object.assign(Array.prototype, 'last', { value: function () { … } });. Altrimenti la proprietà sarà enumerabile.
— 黄 雨伞


70

Ecco come ottenerlo senza alcun effetto sull'ARRAY originale

a = [1,2,5,6,1,874,98,"abc"];
a.length; //returns 8 elements

Se usi pop (), modificherà l'array

a.pop();  // will return "abc" AND REMOVES IT from the array 
a.length; // returns 7

Ma puoi usarlo in modo che non abbia alcun effetto sull'array originale:

a.slice(-1).pop(); // will return "abc" won't do modify the array 
                   // because slice creates a new array object 
a.length;          // returns 8; no modification and you've got you last element 

6
dovresti fare slice (-1) .pop (), altrimenti copi l'intero array (devi solo copiare l'ultimo elemento).
— kritzikratzi,

Non è necessario pop()quindi: bastaarr.slice(-1)[0]
— Christophe Marois,

56

Il modo più pulito di ES6 (IMO) sarebbe:

const foo = [1,2,3,4];
const bar = [...foo].pop();

Questo evita la mutazione foo, come .pop()avremmo fatto, se non avessimo utilizzato l'operatore di diffusione.
Detto questo, mi piace anche la foo.slice(-1)[0]soluzione.


1
È inoltre possibile utilizzare l'array destructuring per renderlo più ES6;) stackoverflow.com/a/46485581/31671
— alex

36
Si noti che questa soluzione esegue una copia dell'intero array.
— Brendan Annable,

4
È tanto illeggibile quanto .slice(-1)[0]ma è più lento. Potrebbe anche usare.slice
— fregante

12
Copiare l'intero array solo per una sintassi "pulita" mi sembra sciocco. Non sembra nemmeno così carino
— Jemar Jones,

43

Preferirei usare gli array.pop()indici.

while(loc_array.pop()!= "index.html"){
}
var newT = document.createTextNode(unescape(capWords(loc_array[loc_array.length])));

in questo modo ottieni sempre l'elemento precedente a index.html (a condizione che l'array abbia isolato index.html come un unico elemento). Nota: tuttavia , perderai gli ultimi elementi dell'array.


38

Penso che se vuoi solo ottenere l'elemento senza rimuoverlo, è più semplice usare questo:

arr.slice(-1)[0]

Nota: se l'array è vuoto (ad es. []) Questo ritornerà undefined.

a proposito ... non ho controllato le prestazioni, ma penso che sia più semplice e pulito da scrivere


Si noti che a) questo non restituisce l'ultimo valore ma un array con l'ultimo elemento ( arr.slice(-1)[0] === arr[arr.length - 1]) eb) è lento perché viene copiato arrin un nuovo array (vedere stackoverflow.com/a/51763533/2733244 per la misurazione delle prestazioni).
— Wortwart,

33

const [lastItem] = array.slice(-1);

Array.prototype.slice con -1 può essere utilizzato per creare un nuovo array contenente solo l'ultimo elemento dell'array originale, quindi è possibile utilizzare Destructuring Assignment per creare una variabile utilizzando il primo elemento di quel nuovo array.

const lotteryNumbers = [12, 16, 4, 33, 41, 22];
const [lastNumber] = lotteryNumbers.slice(-1);

console.log(lotteryNumbers.slice(-1));
// => [22]
console.log(lastNumber);
// => 22


30

È possibile ottenere l'ultimo elemento di un array utilizzando il metodo slice con valori negativi.

Puoi leggere di più a riguardo qui in fondo.

var fileName = loc_array.slice(-1)[0];
if(fileName.toLowerCase() == "index.html")
{
  //your code...
}

L'uso di pop () cambierà l'array, il che non è sempre una buona idea.


1
Slice restituisce un array, tuttavia, quindi usa arr.slice(-1)[0], come questa risposta .
— Cees Timmerman,

4
Se le prestazioni sono un problema, sappi che questo metodo è molto più lento di array[array.length - 1] jsperf.com/get-last-item-from-array/13
— Bruno Peres

29

Puoi usare questo modello ...

let [last] = arr.slice(-1);

Mentre legge piuttosto bene, tieni presente che crea un nuovo array, quindi è meno efficiente di altre soluzioni, ma non sarà quasi mai il collo di bottiglia delle prestazioni della tua applicazione.


25

Questa domanda è in sospeso da molto tempo, quindi sono sorpreso che nessuno abbia menzionato il fatto di rimettere l'ultimo elemento dopo un pop().

arr.pop()è esattamente efficiente arr[arr.length-1]ed entrambi hanno la stessa velocità di arr.push().

Pertanto, puoi cavartela con:

--- MODIFICATO [verifica che thePopnon sia undefinedprima di premere] ---

let thePop = arr.pop()
thePop && arr.push(thePop)

--- MODIFICA FINE ---

Che può essere ridotto a questo (stessa velocità [EDIT: ma non sicuro!]):

arr.push(thePop = arr.pop())    //Unsafe if arr empty

Questo è due volte più lento di arr[arr.length-1], ma non è necessario spostarsi con un indice. Vale la pena l'oro in qualsiasi giorno.

Delle soluzioni che ho provato, e in multipli di Execution Time Unit (ETU) di arr[arr.length-1]:

[Metodo] .............. [ETUs 5 elems] ... [ETU 1 milione elems]

arr[arr.length - 1]      ------> 1              -----> 1

let myPop = arr.pop()
arr.push(myPop)          ------> 2              -----> 2

arr.slice(-1).pop()      ------> 36             -----> 924  

arr.slice(-1)[0]         ------> 36             -----> 924  

[...arr].pop()           ------> 120            -----> ~21,000,000 :)

Le ultime tre opzioni, IN PARTICOLARE [...arr].pop(), peggiorano MOLTO molto di più all'aumentare della dimensione dell'array. Su una macchina senza i limiti di memoria della mia macchina, [...arr].pop()probabilmente mantiene qualcosa come il suo rapporto 120: 1. Tuttavia, a nessuno piace un porco di risorse.


3
Se l'array iniziale può essere vuoto, questo approccio risulterà errato e []verrà trasformato in [undefined]. Devi proteggere la spinta all'indietro con un undefinedcontrollo esplicito , qualcosa del generemyPop !== undefined && arr.push(myPop)
— dhilt

23

Se uno vuole ottenere l'ultimo elemento in una volta sola, può usare Array#splice():

lastElement = document.location.href.split('/').splice(-1,1);

Qui, non è necessario archiviare gli elementi divisi in un array, quindi arrivare all'ultimo elemento. Se ottenere l'ultimo elemento è l'unico obiettivo, questo dovrebbe essere usato.

Nota: questo modifica l'array originale rimuovendo il suo ultimo elemento. Pensa splice(-1,1)a una pop()funzione che apre l'ultimo elemento.


5
Questo non restituisce l'ultimo elemento in un array, anziché l'ultimo elemento stesso?

2
@tozazaburo non è la stessa cosa?
— Aram Kocharyan,

5
questo modifica l'array. potresti usare slice (-1) invece di splice (-1) per lasciare intatta la matrice originale. @AramKocharyan su no la sua non, confrontare ["hi"]vs "hi".
— kritzikratzi,

20

Per coloro che non hanno paura di sovraccaricare il prototipo di array (e con il mascheramento di enumerazione non dovresti essere):

Object.defineProperty( Array.prototype, "getLast", {
    enumerable: false,
    configurable: false,
    writable: false,
    value: function() {
        return this[ this.length - 1 ];
    }
} );


18

In genere uso underscorejs , con cui puoi semplicemente farlo

if (_.last(loc_array) === 'index.html'){
  etc...
}

Per me è più semantico di loc_array.slice(-1)[0]


18

Ecco più arte Javascript se sei venuto qui a cercarla

Nello spirito di un'altra risposta che ha usato reduceRight(), ma più breve:

[3, 2, 1, 5].reduceRight(a => a);

Si basa sul fatto che, nel caso in cui non si fornisca un valore iniziale, l'ultimo elemento viene selezionato come quello iniziale (controllare i documenti qui ). Poiché il callback continua a restituire il valore iniziale, l'ultimo elemento sarà quello restituito alla fine.

Attenzione che questo dovrebbe essere considerato arte Javascript e non è affatto il modo in cui lo consiglierei, soprattutto perché funziona in tempo O (n), ma anche perché danneggia la leggibilità.

E ora per la risposta seria

Il modo migliore che vedo (considerando che lo vuoi più conciso di array[array.length - 1]) è questo:

const last = a => a[a.length - 1];

Quindi basta usare la funzione:

last([3, 2, 1, 5])

La funzione è effettivamente utile nel caso in cui tu abbia a che fare con un array anonimo come [3, 2, 1, 5]usato sopra, altrimenti dovresti istanziarlo due volte, il che sarebbe inefficiente e brutto:

[3, 2, 1, 5][[3, 2, 1, 5].length - 1]

Ugh.

Ad esempio, ecco una situazione in cui hai un array anonimo e dovresti definire una variabile, ma puoi usare last()invece:

last("1.2.3".split("."));

16

Metto solo un'altra opzione qui.

loc_array.splice(-1)[0] === 'index.html'

Ho trovato l'approccio sopra più pulito e breve onliner. Per favore, sentiti libero di provare questo.

Nota: modificherà l'array originale, se non si desidera modificarlo, è possibile utilizzarlo slice()

loc_array.slice(-1)[0] === 'index.html'

Grazie @VinayPai per averlo segnalato.



13

Diversi modi per trovare l'ultimo valore di un array in javascript

  • Senza influire sull'array originale

var arr = [1,2,3,4,5];

console.log(arr.slice(-1)[0])
console.log(arr[arr.length-1])
const [last] = [...arr].reverse();
console.log(last)
console.log(arr.reverse()[0])

  • Modifica l'array originale

var arr = [1,2,3,4,5];

console.log(arr.pop())
arr.push(5)
console.log(...arr.splice(-1));

  • Creando il proprio metodo di supporto

let arr = [1, 2, 3, 4, 5];

Object.defineProperty(arr, 'last', 
{ get: function(){
  return this[this.length-1];
 }
})

console.log(arr.last);


Se il tuo primo esempio in cui dichiari "Senza influire sull'array originale" e facendo come suggerito: console.log(arr.reverse()[0]) - congratulazioni, hai appena modificato l'array originale.
— Roko C. Buljan,

12
const lastElement = myArray[myArray.length - 1];

Questa è la migliore opzione dal punto di vista delle prestazioni (~ 1000 volte più veloce di arr.slice (-1)).


10

Personalmente vorrei dare una risposta a kuporific / kritzikratzi. Il metodo array [array.length-1] diventa molto brutto se si lavora con array nidificati.

var array = [[1,2,3], [4,5,6], [7,8,9]]
​
array.slice(-1)[0]
​
//instead of 
​
array[array.length-1]
​
//Much easier to read with nested arrays
​
array.slice(-1)[0].slice(-1)[0]
​
//instead of
​
array[array.length-1][array[array.length-1].length-1]


10

Per impedire la rimozione dell'ultimo elemento dall'array di origine che è possibile utilizzare

Array.from(myArray).pop()

Principalmente supportato da tutti i browser (ES6)


1
buona fortuna con grandi array di almeno 100.000 elementi.
— Soldeplata Saketos,

9

È possibile aggiungere una last()funzione al Arrayprototipo.

Array.prototype.last = function () {
    return this[this.length - 1];
};

9

Qualunque cosa tu faccia, non usare soloreverse() !!!

Alcune risposte menzionano reversema non menzionano il fatto che reversemodifica l'array originale e che non restituisce una copia (come in altri linguaggi o framework).

var animals = ['dog', 'cat'];

animals.reverse()[0]
"cat"

animals.reverse()[0]
"dog"

animals.reverse()[1]
"dog"

animals.reverse()[1]
"cat"

Questo può essere il peggior tipo di codice per il debug!


4
Se si desidera una copia invertita dell'array, è possibile utilizzare subito l'operatore di diffusione. ad es.[...animals].reverse()
— Josh R

puoi semplicemente copiare l'array prima di usare reverse[1,3,4,5,"last"].slice().reverse()[0]
— Madeo

9

La distruzione degli oggetti ES6 è un'altra strada da percorrere.

const {length, [length-1]: last}=[1,2,3,4,5]
console.log(last)

È possibile estrarre la proprietà della lunghezza dall'array utilizzando la distruzione degli oggetti. Si crea un'altra chiave dinamica utilizzando la chiave già estratta di [lunghezza-1] e la si assegna per durare , tutto in una riga.


un po 'complicato ma intelligente.
— Adrien Castagliola,

Grazie, puoi spiegare cosa fa esattamente?
— Tarun Nagpal,

8

È possibile aggiungere un nuovo getter di proprietà al prototipo di inArray modo che sia accessibile attraverso tutte le istanze di Array.

I Getter ti consentono di accedere al valore di ritorno di una funzione proprio come se fosse il valore di una proprietà. Il valore di ritorno della funzione ovviamente è l'ultimo valore dell'array ( this[this.length - 1]).

Infine lo avvolgi in una condizione che controlla se la lastproprietà è ancora undefined(non definita da un altro script che potrebbe fare affidamento su di essa).

if(typeof Array.prototype.last === 'undefined') {
    Object.defineProperty(Array.prototype, 'last', {
        get : function() {
            return this[this.length - 1];
        }
    });
}

// Now you can access it like
[1, 2, 3].last;            // => 3
// or
var test = [50, 1000];
alert(test.last);          // Says '1000'

Non funziona in IE ≤ 8.


Array.prototype.lastè sempre undefined? L'if non funziona con Chrome 36
— bryc il

7

MODIFICATO:

Di recente ho trovato un'altra soluzione che ora ritengo sia la migliore per le mie esigenze:

function w(anArray) {
  return {
    last() {
      return anArray [anArray.length - 1];
    };
  };
}

Con la definizione sopra in vigore ora posso dire:

let last = w ([1,2,3]).last();
console.log(last) ; // -> 3

Il nome "w" sta per "wrapper". Puoi vedere come aggiungere facilmente altri metodi oltre a "last ()" in questo wrapper.

Dico "il meglio per le mie esigenze", perché ciò mi consente di aggiungere facilmente altri "metodi di supporto" a qualsiasi tipo di JavaScript incorporato. Ciò che viene in mente sono ad esempio car () e cdr () di Lisp.


Perché usare un wrapper? Se devi chiamare una wfunzione, fai semplicemente in modo che la funzione restituisca l'ultimo elemento.
— fregante,

w([1,2,3]).lengthnon è definito. w([1,2,3])[1]non è definito. A me non sembra un involucro. E c'è un errore di sintassi. Hai un extra ';'. Vedere stackoverflow.com/a/49725374/458321 per come scrivere un wrapper di classe (classe SutString) e utilizzare la riflessione per popolare quel wrapper. Tuttavia, imho, i wrapper sono eccessivi. Meglio usare l'incapsulamento, come quasi hai. return { arr: anArray, last() { return anArray[anArray.length - 1]; } };. Inoltre, w è troppo generico. La chiamata è ArrayW o qualcosa del genere.
— TamusJRoyce,

6

Penso che il modo più semplice e super inefficiente sia:

var array = ['fenerbahce','arsenal','milan'];
var reversed_array = array.reverse(); //inverts array [milan,arsenal,fenerbahce]
console.log(reversed_array[0]) // result is "milan".

43
Questa soluzione richiede O (n) più memoria e richiede O (n) tempo. Non è davvero la soluzione ideale.
— hlin117,
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.