ฉันจะลบองค์ประกอบออกจากรายการโดยใช้ lodash ได้อย่างไร


166

ฉันมีวัตถุที่มีลักษณะเช่นนี้:

var obj = {
    "objectiveDetailId": 285,
    "objectiveId": 29,
    "number": 1,
    "text": "x",
    "subTopics": [{
        "subTopicId": 1,
        "number": 1
    }, {
        "subTopicId": 2,
        "number": 32
    }, {
        "subTopicId": 3,
        "number": 22
    }]
}
var stToDelete = 2;

ฉันได้lodashติดตั้งในแอปพลิเคชันของฉันสำหรับสิ่งอื่น ๆ มีวิธีที่มีประสิทธิภาพเพื่อใช้lodashในการลบรายการ: {"subTopicId":2, "number":32}จากobjวัตถุหรือไม่

หรือมีวิธีจาวาสคริปต์ในการทำเช่นนี้?


1
คุณสามารถใช้splice( developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/
......

1
เปลี่ยนชื่อเนื่องจากการลบ 4 ออกจากอาร์เรย์ [1,4,5] ไม่สามารถทำได้เช่นนี้ ใช่ฉันเข้าใจว่าสามารถใช้อาร์เรย์ได้จากแฮช / วัตถุและอาจเป็นไปได้ แต่มีความแตกต่างเล็กน้อยในสองสิ่งนี้ หากต้องการลบออกจากอาเรย์คุณจะใช้result = _.pull(arr, value) ซึ่งจะเป็นการลบค่าที่ตรงกันทั้งหมดออกจากรายการ
boatcoder

คำตอบ:


248

เมื่อ lyyons ชี้ให้เห็นในความคิดเห็นวิธีที่ใช้สำนวนและ lodashy มากขึ้นในการทำเช่นนี้ก็คือการใช้_.removeเช่นนี้

_.remove(obj.subTopics, {
    subTopicId: stToDelete
});

นอกจากนั้นคุณสามารถส่งผ่านฟังก์ชันเพรดิเคตซึ่งจะใช้ผลลัพธ์เพื่อพิจารณาว่าจะลบองค์ประกอบปัจจุบันหรือไม่

_.remove(obj.subTopics, function(currentObject) {
    return currentObject.subTopicId === stToDelete;
});

หรือคุณสามารถสร้างอาร์เรย์ใหม่โดยการกรองอาร์เรย์เก่าด้วย_.filterและกำหนดให้กับวัตถุเดียวกันเช่นนี้

obj.subTopics = _.filter(obj.subTopics, function(currentObject) {
    return currentObject.subTopicId !== stToDelete;
});

หรือ

obj.subTopics = _.filter(obj.subTopics, {subTopicId: stToKeep});

3
เหตุผลที่หินคำตอบนี้เป็นเพราะคุณสามารถใช้ฟังก์ชันเพรดิเคตซึ่งเป็นสิ่งที่ฉันต้องการ การลบองค์ประกอบนั้นไม่สำคัญหากคุณรู้จักดัชนี แต่จะทำอย่างไรเมื่อคุณไม่รู้จักดัชนี
random_user_name

3
อาจจะมีมูลค่าการกล่าวขวัญ_.filterถ้าคุณไม่ต้องการที่จะกลายพันธุ์อาร์เรย์เดิม ....
random_user_name

@cale_b ขอบคุณ :-) อัปเดตคำตอบด้วย_.filterเวอร์ชัน
thefourtheye

7
@thefourtheye _.filter ส่งคืนองค์ประกอบหากเพรดิเคตเป็นจริง การใช้งานของคุณจะส่งคืนองค์ประกอบที่ไม่พึงประสงค์ทั้งหมดแทนที่จะเป็นองค์ประกอบที่คุณต้องการเก็บไว้
Xeltor

5
@thefourtheye คุณควรใช้_.rejectแทน_.filterการใช้คำกริยาเดียวกัน ตรวจสอบคำตอบของฉันสำหรับรายละเอียดเพิ่มเติม!
Xeltor

29

เพียงใช้วานิลลา JS คุณสามารถใช้spliceเพื่อลบองค์ประกอบ:

obj.subTopics.splice(1, 1);

การสาธิต


3
ผู้ใช้ถามIs there an efficient way to use _lodash to delete
semirturgay

7
@Andy คุณพูดถูก แต่ถ้าดัชนีไม่เป็นที่รู้จัก?
thefourtheye

3
splice () เป็นวิธีที่ดีที่สุดถ้าคุณต้องการให้อาเรย์กลายพันธุ์ ถ้าคุณใช้ remove มันจะส่งคืนอาร์เรย์ใหม่และสิ่งนี้จะต้องถูกกำหนดใหม่
omarjebari

หากคุณต้องการที่จะลบรายการออกจากอาเรย์โดยดัชนีในอาเรย์ (เห็นได้ชัดว่าคุณมีดัชนีนี้ถ้าคุณต้องการที่จะดำเนินการลบในลักษณะนี้) จากนั้นใช้วิธีการประกบกันเป็นวิธีที่มีประสิทธิภาพมากที่สุด ที่จะทำมัน ไม่จำเป็นต้องเปรียบเทียบอะไรและทำให้โค้ดมีความซับซ้อนมากขึ้นและมีความเสี่ยงต่อข้อผิดพลาดและข้อผิดพลาด ...
TheCuBeMan

26

_pullคุณสามารถทำมันได้ด้วย

_.pull(obj["subTopics"] , {"subTopicId":2, "number":32});

ตรวจสอบการอ้างอิง


7
ต่อเอกสารที่_.pullใช้ความเท่าเทียมกันอย่างเข้มงวดสำหรับการเปรียบเทียบเช่น === วัตถุธรรมดาสองชนิดที่แตกต่างกันจะไม่มีทางเปรียบเทียบได้เท่ากับ===(หรือ==สำหรับเรื่องนั้น) ดังนั้นโค้ดของคุณด้านบนจะไม่ลบองค์ประกอบใด ๆ ออกจากอาร์เรย์
Mark Amery

1
แต่นั่นเป็นสิ่งเดียวที่ทำงานกับสตริงในอาร์เรย์ _.removeเพียงแค่ล้างอาร์เรย์
Yauheni Prakopchyk

3
ฉันยังคิดว่านี่เป็นคำตอบที่ถูก JS. ตัวกรองลบองค์ประกอบทั้งหมดที่ตรงกัน, JS .splice ต้องการให้ฉันรู้ดัชนี _.remove iterates องค์ประกอบทั้งหมดของอาร์เรย์จึงมีประสิทธิภาพน้อยลง _.pull เป็นสิ่งที่ฉันต้องการ: _.pull (array, itemToRemove)
Judah Gabriel Himango

21

ตอนนี้คุณสามารถใช้_.rejectซึ่งอนุญาตให้คุณกรองตามสิ่งที่คุณต้องการกำจัดแทนที่จะเป็นสิ่งที่คุณต้องการเก็บไว้

ไม่เหมือน_.pullหรือ_.removeว่าการทำงานเฉพาะในอาร์เรย์._rejectคือการทำงานใด ๆ Collection

obj.subTopics = _.reject(obj.subTopics, (o) => {
  return o.number >= 32;
});

2

มีสี่วิธีในการทำสิ่งนี้ตามที่ฉันรู้

const array = [{id:1,name:'Jim'},{id:2,name:'Parker'}];
const toDelete = 1;

ครั้งแรก:

_.reject(array, {id:toDelete})

ประการที่สองคือ:

_.remove(array, {id:toDelete})

ด้วยวิธีนี้อาร์เรย์จะกลายพันธุ์

คนที่สามคือ:

_.differenceBy(array,[{id:toDelete}],'id')
// If you can get remove item 
// _.differenceWith(array,[removeItem])

อันสุดท้ายคือ:

_.filter(array,({id})=>id!==toDelete)

ฉันกำลังเรียนรู้ lodash

ตอบเพื่อสร้างบันทึกเพื่อที่ฉันจะได้พบมันในภายหลัง


ฉันกำลังมองหาreject
Sampgun

2

นอกเหนือไปจาก @thefourtheye คำตอบโดยใช้กริยา แทนของฟังก์ชั่นที่ไม่ระบุชื่อดั้งเดิม:

  _.remove(obj.subTopics, (currentObject) => {
        return currentObject.subTopicId === stToDelete;
    });

หรือ

obj.subTopics = _.filter(obj.subTopics, (currentObject) => {
    return currentObject.subTopicId !== stToDelete;
});


0

นี่คือฟังก์ชั่นแบบเรียบง่ายที่มีอาร์เรย์และลบด้วยหมายเลขดัชนี

index_tobe_delete = 1

fruit = [{a: "apple"}, {b: "banana"}, {c: "choco"}]
_.filter(fruit, (value, key)=> {
return (key !== index_tobe_delete)
})
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.