ความเท่าเทียมกันของวัตถุ jQuery


151

ฉันจะตรวจสอบได้อย่างไรว่าสองวัตถุ jQuery เท่ากัน? ฉันต้องการที่จะค้นหาอาร์เรย์สำหรับวัตถุ jQuery โดยเฉพาะ

$.inArray(jqobj, my_array);//-1    
alert($("#deviceTypeRoot") == $("#deviceTypeRoot"));//False
alert($("#deviceTypeRoot") === $("#deviceTypeRoot"));//False

คำตอบ:


225

ตั้งแต่ jQuery 1.6 คุณสามารถ.isใช้ได้ ด้านล่างเป็นคำตอบจากเมื่อปีที่แล้ว ...

var a = $('#foo');
var b = a;


if (a.is(b)) {
    // the same object!
}

หากคุณต้องการดูว่าตัวแปรสองตัวเป็นวัตถุเดียวกันจริงหรือไม่เช่น:

var a = $('#foo');
var b = a;

... จากนั้นคุณสามารถตรวจสอบ ID ที่ไม่ซ้ำกันได้ ทุกครั้งที่คุณสร้างวัตถุ jQuery ใหม่มันจะได้รับรหัส

if ($.data(a) == $.data(b)) {
    // the same object!
}

แม้ว่าสิ่งเดียวกันนี้สามารถทำได้ด้วยวิธีง่ายๆa === bแต่อย่างน้อยข้างต้นอาจแสดงนักพัฒนาคนต่อไปว่าคุณกำลังทดสอบอะไรอยู่

ไม่ว่าในกรณีใดนั่นอาจไม่ใช่สิ่งที่คุณต้องการ หากคุณต้องการตรวจสอบว่าวัตถุ jQuery ที่แตกต่างกันสองชุดมีองค์ประกอบชุดเดียวกันหรือไม่คุณสามารถใช้สิ่งนี้:

$.fn.equals = function(compareTo) {
  if (!compareTo || this.length != compareTo.length) {
    return false;
  }
  for (var i = 0; i < this.length; ++i) {
    if (this[i] !== compareTo[i]) {
      return false;
    }
  }
  return true;
};

แหล่ง

var a = $('p');
var b = $('p');
if (a.equals(b)) {
    // same set
}

วิธีการแก้ปัญหานี้ช่วยให้ง่ายขึ้นโดยที่thephpdeveloperเมื่อมีเพียงองค์ประกอบเดียว อีกความหมายหนึ่งที่วัตถุ jQuery ถือได้ว่ามีความเท่าเทียมกันคือพวกมันมีตัวเลือกและบริบทเดียวกันหรือไม่ A.selector === B.selector && A.context === B.contextนี้จะเพียงพอที่ง่ายต่อการทดสอบ: บ่อยครั้งที่บริบทจะเหมือนกันเสมอดังนั้นเราจึงต้องพิจารณาตัวเลือกเท่านั้น
Casebash

2
@Casebash - จริง แต่ให้พิจารณาว่าตัวเลือกหลายตัวสามารถจบลงด้วยชุดผลลัพธ์เดียวกันเช่น: $(':first')และ$('*:first')
nickf

3
ข้อควรระวัง @rampion และ nickf, jQuery คือ () ไม่ได้ตรวจสอบว่าตัวเลือกนั้นเหมือนกันเพียง แต่พวกมันทับซ้อนกัน พยาน: jsfiddle.net/bnhkm/1
Bob Stein

equalsฟังก์ชั่นของคุณดูเหมือนจะเป็นคำสั่งที่อ่อนไหว สิ่งที่ต้องการstackoverflow.com/a/29648479จะทำงานในกรณีอื่น ๆ อีกมากมาย แต่ก็ช้าลง
Jayen

ฟังก์ชั่นเท่ากับใช้งานได้เฉพาะถ้าวัตถุมีหนึ่งระดับ! การเปรียบเทียบ a = b = [{dir: 'test', sort: [{test: {test: 1}}]}] ไม่ทำงาน
DavidDunham

16

หากคุณยังไม่รู้คุณสามารถเรียกคืนวัตถุต้นฉบับได้โดย:

alert($("#deviceTypeRoot")[0] == $("#deviceTypeRoot")[0]); //True
alert($("#deviceTypeRoot")[0] === $("#deviceTypeRoot")[0]);//True

เพราะ$("#deviceTypeRoot")ยังส่งคืนอาร์เรย์ของวัตถุที่ตัวเลือกได้เลือกไว้


1
การแจ้งเตือนสองรายการจะแสดงtrueขึ้นเนื่องจากคุณกำลังเปรียบเทียบการอ้างอิงขององค์ประกอบ DOM และ==VS ===จะให้ผลลัพธ์เดียวกัน (ไม่จำเป็นต้องมีการข่มขู่ประเภทพวกเขาเป็นเพียงการอ้างอิงวัตถุสองครั้ง)
CMS

คำสั่งที่สองของคุณกำลังส่งคืนจริง
Casebash

อ่าใช่มันเป็นเรื่องจริง คัดลอกและวางผิดพลาด = D
mauris

14

$.fn.equals(...)ทางออกที่น่าจะเป็นที่สะอาดและสง่างามมากที่สุดคนหนึ่ง

ฉันลองทำอะไรที่รวดเร็วและสกปรกเช่นนี้:

JSON.stringify(a) == JSON.stringify(b)

อาจมีราคาแพง แต่สิ่งที่สะดวกสบายคือการเรียกซ้ำโดยปริยายในขณะที่โซลูชันที่สง่างามไม่ใช่

แค่ 2 เซ็นต์ของฉัน


1
มันไม่ดีสำหรับการตรวจสอบความเท่าเทียมกันระหว่างสองวัตถุ jQuery แต่สำหรับวัตถุมาตรฐาน เช่น "{a: 'x', b: 'y', c: 'z'} == {a: 'x', b: 'y', c: 'z'}" ฉันสงสัยว่าไม่มี jQuery.isEqual (a, b) ...
iRaS

13
นี่เป็นสิ่งที่ผิด ลำดับของคุณสมบัติวัตถุมีความสำคัญ ดังนั้นถ้าคุณมี{a: 1, b: 2}และ{b: 2, a: 1}นี้จะกลับมาเมื่อมันควรจะกลับfalse true
Eric Alberson

3
@EricAlberson คุณมีข้อเสนอแนะเกี่ยวกับเครื่องมือเปรียบเทียบหรือสคริปต์ที่สามารถจัดการกับสถานการณ์นี้ได้หรือไม่?
Neil Monroe

8

โดยทั่วไปแล้วการพูดความคิดที่ไม่ดีในการเปรียบเทียบ $ (foo) กับ $ (foo) นั้นเทียบเท่ากับการเปรียบเทียบดังต่อไปนี้:

<html>
<head>
<script language='javascript'>
    function foo(bar) {
        return ({ "object": bar });
    }

    $ = foo;

    if ( $("a") == $("a") ) {
        alert ("JS engine screw-up");
    }
    else {
        alert ("Expected result");
    }

</script>

</head>
</html>

แน่นอนว่าคุณไม่เคยคาดหวังว่า "JS engine screw-up" ฉันใช้ "$" เพียงเพื่อทำให้ชัดเจนว่า jQuery กำลังทำอะไร

เมื่อใดก็ตามที่คุณเรียก $ ( "# foo") คุณเป็นจริงทำ jQuery ( "# foo") ซึ่งผลตอบแทนที่วัตถุใหม่ ดังนั้นการเปรียบเทียบพวกเขาและคาดหวังว่าวัตถุเดียวกันจะไม่ถูกต้อง

อย่างไรก็ตามสิ่งที่คุณสามารถทำได้อาจเป็นเช่น:

<html>
<head>
<script language='javascript'>
    function foo(bar) {
        return ({ "object": bar });
    }

    $ = foo;

    if ( $("a").object == $("a").object ) {
        alert ("Yep! Now it works");
    }
    else {
        alert ("This should not happen");
    }

</script>

</head>
</html>

ดังนั้นจริงๆแล้วคุณควรเปรียบเทียบองค์ประกอบ ID ของวัตถุ jQuery ในโปรแกรมจริงของคุณ

... 
$(someIdSelector).attr("id") == $(someOtherIdSelector).attr("id")

มีความเหมาะสมมากขึ้น


1
เพื่อให้ชัดเจน jQuery ไม่มีแอตทริบิวต์ของวัตถุ ดูเหมือนว่า Elf King จะใช้สิ่งนี้เป็นรหัสปลอม
Casebash


4

ก่อนสั่งซื้อวัตถุของคุณตามคีย์โดยใช้ฟังก์ชั่นนี้

function sortObject(o) {
    return Object.keys(o).sort().reduce((r, k) => (r[k] = o[k], r), {});
}

จากนั้นเปรียบเทียบเวอร์ชันที่เป็นวัตถุของวัตถุของคุณโดยใช้ funtion นี้

function isEqualObject(a,b){
    return JSON.stringify(sortObject(a)) == JSON.stringify(sortObject(b));
}

นี่คือตัวอย่าง

สมมติว่าคีย์วัตถุนั้นเรียงลำดับแตกต่างกันและมีค่าเหมือนกัน

var obj1 = {"hello":"hi","world":"earth"}
var obj2 = {"world":"earth","hello":"hi"}

isEqualObject(obj1,obj2);//returns true

-1

หากคุณต้องการตรวจสอบเนื้อหาเท่ากันหรือไม่ก็เพียงแค่ใช้ JSON.stringify (obj)

เช่น - var a = {key: val};

var b = {key: val};

JSON.stringify (a) == JSON.stringify (b) -----> หากเนื้อหาเหมือนกันคุณจะได้รับจริง


คุณต้องเรียงลำดับคีย์ก่อนเช่นเดียวกับคำตอบของ Kareem
reggaeguitar
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.