Usuń obiekt z tablicy za pomocą JavaScript


547

Jak mogę usunąć obiekt z tablicy? Życzę, aby usunąć obiekt, który zawiera nazwę Kristianod someArray. Na przykład:

someArray = [{name:"Kristian", lines:"2,5,10"},
             {name:"John", lines:"1,19,26,96"}];

Chcę osiągnąć:

someArray = [{name:"John", lines:"1,19,26,96"}];


3
Do Twojej wiadomości cofnąłem edycję tego pytania, więc składnia tablicy jest znowu niepoprawna i wszystkie te odpowiedzi są w kontekście.
— Dunhamzzz,

2
Następnie składnia tablicy została ponownie „poprawiona” (dwukrotnie), aby odpowiedzi nie były już kontekstowe.
— Teepeemm,

4
W jaki sposób błąd składniowy pomaga nadać sensowi niektóre odpowiedzi?
— Samy Bencherif

1
@SamyBencherif - Niektóre odpowiedzi jednoznacznie odnoszą się do błędu składniowego w oryginalnej wersji pytania, więc jeśli usuniesz ten błąd składniowy, te odpowiedzi mówią teraz o czymś, co nie istnieje.
— nnnnnn

Odpowiedzi:


778

Możesz użyć kilku metod, aby usunąć elementy z tablicy:

//1
someArray.shift(); // first element removed
//2
someArray = someArray.slice(1); // first element removed
//3
someArray.splice(0, 1); // first element removed
//4
someArray.pop(); // last element removed
//5
someArray = someArray.slice(0, a.length - 1); // last element removed
//6
someArray.length = someArray.length - 1; // last element removed

Jeśli chcesz usunąć element na miejscu x, użyj:

someArray.splice(x, 1);

Lub

someArray = someArray.slice(0, x).concat(someArray.slice(-x));

Odpowiedz na komentarz @ chill182 : możesz usunąć jeden lub więcej elementów z tablicy za pomocą Array.filterlub w Array.splicepołączeniu z Array.findIndex(patrz MDN ), np.

// non destructive filter > noJohn = John removed, but someArray will not change
let someArray = getArray();
let noJohn = someArray.filter( el => el.name !== "John" ); 
log("non destructive filter > noJohn = ", format(noJohn));
log(`**someArray.length ${someArray.length}`);

// destructive filter/reassign John removed > someArray2 =
let someArray2 = getArray();
someArray2 = someArray2.filter( el => el.name !== "John" );
log("", "destructive filter/reassign John removed > someArray2 =", 
  format(someArray2));
log(`**someArray2.length ${someArray2.length}`);

// destructive splice /w findIndex Brian remains > someArray3 =
let someArray3 = getArray();
someArray3.splice(someArray3.findIndex(v => v.name === "Kristian"), 1);
someArray3.splice(someArray3.findIndex(v => v.name === "John"), 1);
log("", "destructive splice /w findIndex Brian remains > someArray3 =", 
  format(someArray3));
log(`**someArray3.length ${someArray3.length}`);

// Note: if you're not sure about the contents of your array, 
// you should check the results of findIndex first
let someArray4 = getArray();
const indx = someArray4.findIndex(v => v.name === "Michael");
someArray4.splice(indx, indx >= 0 ? 1 : 0);
log("", "check findIndex result first > someArray4 (nothing is removed) > ",
  format(someArray4));
log(`**someArray4.length (should still be 3) ${someArray4.length}`);

function format(obj) {
  return JSON.stringify(obj, null, " ");
}

function log(...txt) {
  document.querySelector("pre").textContent += `${txt.join("\n")}\n`
}

function getArray() {
  return [ {name: "Kristian", lines: "2,5,10"},
           {name: "John", lines: "1,19,26,96"},
           {name: "Brian", lines: "3,9,62,36"} ];
}
<pre>
**Results**

</pre>


2
@Klemzy nie miałeś na myśli, że nie przez indeks? według wartości ...?
— Royi Namir,

328
Pierwotne pytanie dotyczyło sposobu usunięcia obiektu o nazwie = „Kristian” z tablicy. Twoja odpowiedź zakłada, że ​​jest to pierwszy element w tablicy, ale co, jeśli Kristin nie ma w pierwszym elemencie? Twoja odpowiedź nie działa.
— Rochelle C

7
@ chill182: nie jest to konkretna odpowiedź, ale ogólniejsza. Na tej podstawie powinieneś być w stanie wywnioskować metodę usuwania elementów. Jeśli chcesz usunąć element w pozycji x ... może to być wskazówka do usuwania elementów innych niż pierwsze, prawda?
— KooiInc

6
Funkcja łączenia była dla mnie pomocna, ale nie powinieneś był ponownie przypisywać someArray. Spowoduje to, że tablica zawiera usunięty element, a nie tablicę wynikową z usuniętym elementem.
— Kenn Cal

1
Powinieneś sprawdzić findIndexwynik przed użyciem go splice. Jeśli w tablicy nie ma elementów, które pasują, warunek findIndexzostanie zwrócony, -1a umieszczenie tego bezpośrednio w tablicy splicespowoduje arbitralne usunięcie ostatniego elementu w tablicy.
— jdnz

131

Polecam używanie lodash.js lub sugar.js do typowych zadań takich jak to:

// lodash.js
someArray = _.reject(someArray, function(el) { return el.Name === "Kristian"; });

// sugar.js
someArray.remove(function(el) { return el.Name === "Kristian"; });

w większości projektów posiadanie zestawu metod pomocniczych dostarczanych przez takie biblioteki jest dość przydatne.


13
Myślę, że przykład podkreślenia jest nieco wyłączony. Powinien byćsomeArray = _.reject(someArray, function(el) { return el.Name === "Kristian"; });
— Andy Ford

7
Jeśli nie chcesz używać underscore.js lub sugar.js, możesz to zrobićsomeArray = someArray.filter(function(e) { return e.Name !== "Kristian"; });
— BenR

1
Kolejną rzeczą, którą chcę, będą osobne przyciski dla każdego obiektu w tablicy. jeśli chcę usunąć ten konkretny obiekt w klikniętym przycisku tablicy jak to zrobić . Użyłem kątowego js ng-repeat do generowania przedmiotów. czy możesz mi pomóc
— Thilak Raj

5
Idę tu pod prąd; sugerowanie, aby jedna obejmowała całą bibliotekę w prostym celu usuwania elementów z obiektów (co js czysto obsługuje po wyjęciu z pudełka, jak pokazuje zaakceptowana odpowiedź), jest złej formie. Dodaje niepotrzebną wagę i złożoność kodu, chyba że jest on już potrzebny do uzyskania bardziej zaawansowanych funkcji biblioteki.
— Josh Doebbert

4
Dla prostej operacji nigdy nie
— zalecę

130

Czystym rozwiązaniem byłoby użycie Array.filter:

var filtered = someArray.filter(function(el) { return el.Name != "Kristian"; }); 

Problem polega na tym, że nie działa on w przeglądarce IE <9. Można jednak dołączyć kod z biblioteki JavaScript (np. Underscore.js ), która implementuje to w dowolnej przeglądarce.


10
Spowoduje to jednak usunięcie wszystkich znalezionych zdarzeń, nie tylko pierwszego
— Flavien Volken

4
I zwróci nową tablicę zamiast modyfikować oryginalną. W zależności od przypadku użycia może to być lub nie być to, czego chcesz.
— Jochie Nabuurs,

1
@JochieNabuurs to rzeczywiście nowa tablica. Jednak obiekt pozostaje taki sam. Nadal możesz modyfikować wartość każdego obiektu, a będzie on odzwierciedlał obiekt oryginalnej tablicy.
— DriLLFreAK100

2
Do tego stopnia, że ​​zwraca nową tablicę, wystarczy zmienić rozwiązanie na someArray = someArray.filter(function(el) { return el.Name != "Kristian"; }); adresy, które nie, nie?
— hBrent

93

Co powiesz na to?

$.each(someArray, function(i){
    if(someArray[i].name === 'Kristian') {
        someArray.splice(i,1);
        return false;
    }
});

8
Nie spowoduje to błędu, ponieważ $.each()buforuje długość tablicy przed zapętleniem, więc jeśli usuniesz element, $.each()będzie przebiegał poza końcem (teraz krótszej) tablicy. (Więc wtedy someArray[i]będzie undefinedi undefined.namerozbije się.)
— nnnnnn

5
Następnie dodaj „return false” po splocie.
— Allan Taylor

18
to nie jest javascript. -1
— cebulka

20
Należy pamiętać, że ta odpowiedź wymaga jQuery
— Clarkey

68

Twoja „tablica”, jak pokazano, jest niepoprawną składnią JavaScript. Nawiasy klamrowe {}dotyczą obiektów o parach nazwa-wartość, ale nawiasy kwadratowe []dotyczą tablic:

someArray = [{name:"Kristian", lines:"2,5,10"}, {name:"John", lines:"1,19,26,96"}];

W takim przypadku możesz użyć .splice()metody, aby usunąć element. Aby usunąć pierwszy element (indeks 0), powiedz:

someArray.splice(0,1);

// someArray = [{name:"John", lines:"1,19,26,96"}];

Jeśli nie znasz indeksu, ale chcesz przeszukać tablicę, aby znaleźć element o nazwie „Kristian” do usunięcia, możesz to zrobić:

for (var i =0; i < someArray.length; i++)
   if (someArray[i].name === "Kristian") {
      someArray.splice(i,1);
      break;
   }

EDYCJA: Właśnie zauważyłem, że twoje pytanie jest oznaczone jako „jQuery”, więc możesz wypróbować $.grep()metodę :

someArray = $.grep(someArray,
                   function(o,i) { return o.name === "Kristian"; },
                   true);

Dlaczego dodali przeciążenie? Z pewnością mogłeś po prostu wstawić! = "Kristian". Do czego służy przeciążenie?
— markthewizard1234

@ markthewizard1234 - Czy masz na myśli argument „invert” w logice $.grep()? Nie dodaje się wiele w tym przykładzie, w którym tak, mógłbym umieścić !=, ale w innych przypadkach możesz już mieć zdefiniowaną funkcję, która wykonuje test odwrotny do tego, co chcesz grepować, więc zamiast definiować dodatkową funkcję można po prostu użyć tego przeciążenia, aby odwrócić wyniki.
— nnnnnn

Ach, więc jeśli masz funkcję otoki zawierającą grep, możesz ustawić wartość logiczną jako parametr. Mam to, dzieki!
— markthewizard1234

@ markthewizard1234 - Możesz, ale nie o to mi chodziło: wyobraź sobie, że tak function isEven(num) { return num%2===0 }. Możesz użyć, $.grep(someArray, isEven)aby uzyskać tylko liczby parzyste z tablicy, lub $.grep(someArray, isEven, true)zrobić coś przeciwnego i uzyskać wartości nieparzyste.
— nnnnnn

63

ES2015

let someArray = [
               {name:"Kristian", lines:"2,5,10"},
               {name:"John", lines:"1,19,26,96"},
               {name:"Kristian", lines:"2,58,160"},
               {name:"Felix", lines:"1,19,26,96"}
            ];

someArray = someArray.filter(person => person.name != 'John');

To usunie Johna !


4
Człowieku ... Pochodzę z Java, jestem bardzo zdezorientowany, że tak podstawowa rzecz wymaga filtrowania listy ... wtf. To jest najdokładniejsza odpowiedź na pytanie PO, które przeczytałem do tej pory.
— codepleb

Tak, to dobre podejście. Chociaż będzie działał również przed ES2015 (ES6). Funkcja filtrowania jest dostępna od wersji 5.1 (2011) ecma-international.org/ecma-262/5.1/#sec-15.4.4.20
— user3777549

40

Możesz użyć array.filter ().

na przykład

        someArray = [{name:"Kristian", lines:"2,5,10"},
                     {name:"John", lines:"1,19,26,96"}];

        someArray = someArray.filter(function(returnableObjects){
               return returnableObjects.name !== 'Kristian';
        });

        //someArray will now be = [{name:"John", lines:"1,19,26,96"}];

Funkcje strzałek:

someArray = someArray.filter(x => x.name !== 'Kristian')

Kolejną rzeczą, którą chcę, będą osobne przyciski dla każdego obiektu w tablicy. jeśli chcę usunąć ten konkretny obiekt w klikniętym przycisku tablicy jak to zrobić . Użyłem kątowego js ng-repeat do generowania przedmiotów. czy możesz mi pomóc
— Thilak Raj

daCoda co jeśli masz dwa warunki?
— Malcolm Salvador,

@MalcolmSalvador powiedz na przykład, jeśli masz inne warunki, możesz napisać to jak poniżej i kontynuować z różnymi && lub || operator w zależności od potrzeb. someArray = someArray.filter (function (returnableObjects) {return returnableObjects.name! == 'Kristian' && cond2Query.age> = 22;});
— Biswajit Panday

18

Zrobiłem funkcję dynamiczną, która pobiera obiekty Array, Key i value i zwraca tę samą tablicę po usunięciu pożądanego obiektu:

function removeFunction (myObjects,prop,valu)
        {
             return myObjects.filter(function (val) {
              return val[prop] !== valu;
          });

        }

Pełny przykład: DEMO

var obj = {
            "results": [
              {
                  "id": "460",
                  "name": "Widget 1",
                  "loc": "Shed"
              }, {
                  "id": "461",
                  "name": "Widget 2",
                  "loc": "Kitchen"
              }, {
                  "id": "462",
                  "name": "Widget 3",
                  "loc": "bath"
              }
            ]
            };


        function removeFunction (myObjects,prop,valu)
        {
             return myObjects.filter(function (val) {
              return val[prop] !== valu;
          });

        }


console.log(removeFunction(obj.results,"id","460"));

15

Ta funkcja działa dla mnie:

function removeFromArray(array, value) {
    var idx = array.indexOf(value);
    if (idx !== -1) {
        array.splice(idx, 1);
    }
    return array;
}

Kolejną rzeczą, którą chcę, będą osobne przyciski dla każdego obiektu w tablicy. jeśli chcę usunąć ten konkretny obiekt w klikniętym przycisku tablicy jak to zrobić . Użyłem kątowego js ng-repeat do generowania przedmiotów. czy możesz mi pomóc
— Thilak Raj 21.01.16

12

Możesz także spróbować zrobić coś takiego:

var myArray = [{'name': 'test'}, {'name':'test2'}];
var myObject = {'name': 'test'};
myArray.splice(myArray.indexOf(myObject),1);

11
someArray = jQuery.grep(someArray , function (value) {
        return value.name != 'Kristian';
});

10

Użyj funkcji łączenia na tablicach. Określ pozycję elementu początkowego i długość podsekwencji, którą chcesz usunąć.

someArray.splice(pos, 1);


4

Z funkcją strzałki ES 6

let someArray = [
                 {name:"Kristian", lines:"2,5,10"},
                 {name:"John", lines:"1,19,26,96"}
                ];
let arrayToRemove={name:"Kristian", lines:"2,5,10"};
someArray=someArray.filter((e)=>e.name !=arrayToRemove.name && e.lines!= arrayToRemove.lines)

3

Najprostszym rozwiązaniem byłoby utworzenie mapy, która przechowuje indeksy dla każdego obiektu według nazwy, w następujący sposób:

//adding to array
var newPerson = {name:"Kristian", lines:"2,5,10"}
someMap[ newPerson.name ] = someArray.length;
someArray.push( newPerson );

//deleting from the array
var index = someMap[ 'Kristian' ];
someArray.splice( index, 1 );

Podoba mi się ten pomysł, ale muszę również zapytać, jakie są limity wykorzystania pamięci dla takiego pomysłu po dodaniu indeksów? Mam tablicę, którą chciałbym zindeksować na 2 różnych polach w obiekcie, więc oprócz oryginalnej tablicy źródłowej mam 2 mapy. Czy to niewielka cena za szybkość wyszukiwania, czy jest rozwiązanie, które byłoby bardziej wydajne z pamięcią?
— Brad G.

3

Chociaż prawdopodobnie nie jest to odpowiednie w tej sytuacji, dowiedziałem się innego dnia, że ​​możesz również użyć deletesłowa kluczowego, aby usunąć element z tablicy, jeśli nie musisz zmieniać rozmiaru tablicy, np.

var myArray = [1,2,3];

delete myArray[1];

console.log(myArray[1]); //undefined

console.log(myArray.length); //3 - doesn't actually shrink the array down

3

Ta odpowiedź

for (var i =0; i < someArray.length; i++)
   if (someArray[i].name === "Kristian") {
      someArray.splice(i,1);
   }

nie działa dla wielu rekordów spełniających warunek. Jeśli masz dwa takie kolejne rekordy, tylko pierwszy jest usuwany, a drugi pomijany. Musisz użyć:

for (var i = someArray.length - 1; i>= 0; i--)
   ...

zamiast .


2

Wygląda na to, że wystąpił błąd w składni tablicy, więc zakładając, że masz na myśli tablicę, a nie obiekt, Array.splice jest tutaj twoim przyjacielem:

someArray = [{name:"Kristian", lines:"2,5,10"}, {name:"John", lines:"1,19,26,96"}];
someArray.splice(1,1)

2

Możesz także użyć funkcji mapy .

someArray = [{name:"Kristian", lines:"2,5,10"},{name:"John",lines:"1,19,26,96"}];
newArray=[];
someArray.map(function(obj, index){
    if(obj.name !== "Kristian"){
       newArray.push(obj);
    }
});
someArray = newArray;
console.log(someArray);

1
Ale jeśli chcesz iterować po tablicy, czy nie lepiej jest użyć dlaEach?
— corse32

2

Możesz również użyć some:

someArray = [{name:"Kristian", lines:"2,5,10"},
             {name:"John", lines:"1,19,26,96"}];

someArray.some(item => { 
    if(item.name === "Kristian") // Case sensitive, will only remove first instance
        someArray.splice(someArray.indexOf(item),1) 
})

2

Tego używam.

Array.prototype.delete = function(pos){
    this[pos] = undefined;
    var len = this.length - 1;
    for(var a = pos;a < this.length - 1;a++){
      this[a] = this[a+1];
    }
    this.pop();
  }

To jest tak proste, jak powiedzenie

var myArray = [1,2,3,4,5,6,7,8,9];
myArray.delete(3);

Zastąp dowolną liczbę zamiast trzech. Po oczekiwanym wyniku powinno być:

console.log(myArray); //Expected output 1,2,3,5,6,7,8,9

2

Jeśli chcesz usunąć wszystkie wystąpienia danego obiektu (na podstawie pewnych warunków), użyj metody łączenia javascript wewnątrz pętli for.

Ponieważ usunięcie obiektu wpłynęłoby na długość tablicy, należy zmniejszyć licznik o jeden krok, aby kontrola długości pozostała nienaruszona.

var objArr=[{Name:"Alex", Age:62},
  {Name:"Robert", Age:18},
  {Name:"Prince", Age:28},
  {Name:"Cesar", Age:38},
  {Name:"Sam", Age:42},
  {Name:"David", Age:52}
];

for(var i = 0;i < objArr.length; i ++)
{
  if(objArr[i].Age > 20)
  {
    objArr.splice(i, 1);
    i--;  //re-adjust the counter.
  }
}

Powyższy fragment kodu usuwa wszystkie obiekty w wieku powyżej 20 lat.



1

splice (i, 1), gdzie i jest przyrostowym indeksem tablicy, usunie obiekt. Pamiętaj jednak, że połączenie zresetuje również długość tablicy, więc uważaj na „niezdefiniowane”. Korzystając z Twojego przykładu, jeśli usuniesz „Kristian”, to w następnym wykonaniu w pętli będę mieć 2, ale someArray będzie miał długość 1, dlatego jeśli spróbujesz usunąć „John”, otrzymasz błąd „niezdefiniowany” . Jednym z rozwiązań tego, choć nie eleganckim, jest posiadanie osobnego licznika do śledzenia indeksu elementu do usunięcia.


1

Zwraca tylko obiekty z tablicy, których właściwość namenie jest „Kristian”

var noKristianArray = $.grep(someArray, function (el) { return el.name!= "Kristian"; });


Próbny:

 var someArray = [
                {name:"Kristian", lines:"2,5,10"},
                {name:"John", lines:"1,19,26,96"},
                {name:"Kristian", lines:"2,58,160"},
                {name:"Felix", lines:"1,19,26,96"}
                ];
			 
var noKristianArray = $.grep(someArray, function (el) { return el.name!= "Kristian"; });

console.log(noKristianArray);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>


0

Te koncepcje za pomocą Kendo Grid

var grid = $("#addNewAllergies").data("kendoGrid");

var selectedItem = SelectedCheckBoxList;

for (var i = 0; i < selectedItem.length; i++) {
    if(selectedItem[i].boolKendoValue==true)
    {
        selectedItem.length= 0;
    }
}

-2

Jeśli chcesz uzyskać dostęp do obiektu tablicy i usunąć go, możesz po prostu spróbować czegoś takiego.

// inside some function

let someArray = [ {"ColumnName" : "a", "PropertySerno" : 100005,"UpdateType" : 1},
                  {"ColumnName" : "b", "PropertySerno" : 100202,"UpdateType" : 1,
        "ShowRemoveButton" : true} ];
        
        for (let item of someArray) {
          delete item.ShowRemoveButton;
        }
        console.log(item.outputMappingData.Data);
        
//output will be like that = [ {"ColumnName" : "a", "PropertySerno" : 100005,"UpdateType" : 1},
//                             {"ColumnName" : "b", "PropertySerno" : 100202,"UpdateType" : 1 }];
        

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.