Eu tenho o seguinte para o loop e, quando uso splice()
para remover um item, obtenho que 'segundos' é indefinido. Eu poderia verificar se está indefinido, mas acho que provavelmente há uma maneira mais elegante de fazer isso. O desejo é simplesmente excluir um item e continuar.
for (i = 0, len = Auction.auctions.length; i < len; i++) {
auction = Auction.auctions[i];
Auction.auctions[i]['seconds'] --;
if (auction.seconds < 0) {
Auction.auctions.splice(i, 1);
}
}
javascript
loops
dzm
fonte
fonte
Auction.auctions[i]['seconds']--
vez deauction.seconds--
?Respostas:
A matriz está sendo indexada novamente quando você faz um
.splice()
, o que significa que você pulará um índice quando um for removido e seu cache.length
estiver obsoleto.Para corrigi-lo, você precisa decrementar
i
após a.splice()
ou simplesmente iterar ao contrário ...Dessa forma, a reindexação não afeta o próximo item na iteração, pois a indexação afeta apenas os itens do ponto atual até o final da Matriz, e o próximo item na iteração é menor que o ponto atual.
fonte
Esse é um problema bastante comum. A solução é fazer um loop para trás:
Não importa se você os está retirando do final, porque os índices serão preservados à medida que você retrocede.
fonte
Recalcule o comprimento de cada vez através do loop em vez de apenas no início, por exemplo:
Dessa forma, você não excederá os limites.
EDIT: adicionado um decremento na instrução if.
fonte
Embora sua pergunta seja sobre a exclusão de elementos da matriz que está sendo iterada e não sobre a remoção eficiente de elementos (além de algum outro processamento), acho que se deve reconsiderá-lo se estiver em situação semelhante.
A complexidade algorítmica dessa abordagem é
O(n^2)
como função de emenda e o loop for itera sobre a matriz (a função de emenda muda todos os elementos da matriz no pior caso). Em vez disso, você pode simplesmente enviar os elementos necessários para a nova matriz e, em seguida, atribuir essa matriz à variável desejada (que foi iterada).Desde o ES2015, podemos usar
Array.prototype.filter
tudo isso em uma linha:fonte
fonte
Se você estiver usando o ES6 + - por que não usar o método Array.filter?
Observe que a modificação do elemento da matriz durante a iteração do filtro funciona apenas para objetos e não para a matriz de valores primitivos.
fonte
Outra solução simples para digerir os elementos de uma matriz uma vez:
fonte
Aqui está outro exemplo para o uso adequado de emenda. Este exemplo está prestes a remover 'attribute' de 'array'.
fonte
Para todas as pessoas que responderam a essa pergunta muito básica com código splice () em um loop, que tenha o tempo de execução O (n 2 ), ou que tenha votado positivamente nessa resposta, durante os sete anos desde que essa pergunta foi publicada: você deve tenha vergonha .
Aqui está uma solução de tempo linear simples para esse problema de tempo linear simples.
Quando executo esse snippet, com n = 1 milhão, cada chamada para filterInPlace () leva 0,013 a 0,016 segundos. Uma solução quadrática (por exemplo, a resposta aceita) levaria um milhão de vezes mais ou menos.
Observe que isso modifica a matriz original no lugar, em vez de criar uma nova matriz; fazê-lo no lugar como esse pode ser vantajoso, por exemplo, no caso em que a matriz é o gargalo de memória única do programa; nesse caso, você não deseja criar outra matriz do mesmo tamanho, mesmo que temporariamente.
fonte
Array.splice(i,1)
que criaria uma nova instância de matriz a cada vez. Estou muito envergonhado.Já existem muitas respostas maravilhosas neste tópico. No entanto, eu queria compartilhar minha experiência ao tentar resolver "remover o enésimo elemento da matriz" no contexto do ES5.
As matrizes JavaScript têm métodos diferentes para adicionar / remover elementos do início ou do fim. Esses são:
Essencialmente, nenhum dos métodos acima pode ser usado diretamente para remover o enésimo elemento da matriz.
Isso basicamente nos deixa com apenas um método de matriz
Array.splice
para executar a remoção do enésimo elemento (há outras coisas que você poderia fazer com esses métodos também, mas no contexto desta pergunta, estou focando na remoção de elementos):Aqui está o código copiado da resposta original (com comentários):
Outro método digno de nota é
Array.slice
. No entanto, o tipo de retorno desse método são os elementos removidos. Além disso, isso não modifica a matriz original. Fragmento de código modificado da seguinte maneira:Dito isto, ainda podemos usar
Array.slice
para remover o enésimo elemento, como mostrado abaixo. No entanto, é muito mais código (portanto ineficiente)fonte
Tente retransmitir uma matriz para newArray ao fazer um loop:
fonte
Dois exemplos que funcionam:
fonte
Faça uma tentativa
fonte
fonte
Você pode apenas olhar e usar
shift()
fonte