ฉันกำลังพยายามคิดว่าจะต้องใช้อินเทอร์เฟซใดต่อไปนี้ ทั้งคู่ทำสิ่งเดียวกันเป็นหลัก ฉันจะใช้อันอื่นเมื่อไหร่
ฉันกำลังพยายามคิดว่าจะต้องใช้อินเทอร์เฟซใดต่อไปนี้ ทั้งคู่ทำสิ่งเดียวกันเป็นหลัก ฉันจะใช้อันอื่นเมื่อไหร่
คำตอบ:
ดีที่พวกเขาไม่ได้ค่อนข้างเป็นสิ่งเดียวกับIComparer<T>
ที่จะดำเนินการกับชนิดที่มีความสามารถของการเปรียบเทียบสองวัตถุที่แตกต่างกันในขณะที่IComparable<T>
มีการใช้งานเกี่ยวกับประเภทที่มีความสามารถที่จะเปรียบเทียบตัวเองกับกรณีอื่น ๆ ประเภทเดียวกัน
ฉันมักจะใช้IComparable<T>
เป็นบางครั้งเมื่อฉันต้องการทราบว่าอินสแตนซ์อื่นเกี่ยวข้องกับthis
อินสแตนซ์อย่างไร IComparer<T>
มีประโยชน์สำหรับการจัดเรียงคอลเลกชันเป็นฐานIComparer<T>
นอกการเปรียบเทียบ
IComparable
เป็นผมเทียบเคียง ซึ่งหมายความว่าฉันสามารถเปรียบเทียบกับอย่างอื่นได้ และอ่านIComparer
ว่าฉันเป็นตัวเปรียบเทียบฉันแค่เปรียบเทียบซึ่งหมายความว่าฉันเปรียบเทียบบางสิ่ง
ใช้IComparable<T>
เมื่อคลาสมีการเปรียบเทียบภายใน
ใช้IComparer<T>
เมื่อคุณต้องการวิธีการเปรียบเทียบที่นอกเหนือจากการเปรียบเทียบที่แท้จริงของคลาสหากมี
ขึ้นอยู่กับนิติบุคคล ตัวอย่างเช่นต่อไปนี้สำหรับชั้นเรียนเช่น "นักเรียน" จะเหมาะสมที่จะมี IComparable ตามชื่อ
class Student : IComparable
{
public string Name { get; set; }
public int MathScore { get; set; }
public int EnglishScore { get; set; }
public int TotalScore
{
get
{
return this.MathScore + this.EnglishScore;
}
}
public int CompareTo(object obj)
{
return CompareTo(obj as Student);
}
public int CompareTo(Student other)
{
if (other == null)
{
return 1;
}
return this.Name.CompareTo(other.Name);
}
}
แต่ถ้าครู "A" ต้องการเปรียบเทียบนักเรียนตาม MathScore และครู "B" ต้องการเปรียบเทียบนักเรียนตาม EnglishScore จะเป็นการดีที่จะใช้ IComparer แยกกัน (เหมือนรูปแบบกลยุทธ์)
class CompareByMathScore : IComparer<Student>
{
public int Compare(Student x, Student y)
{
if (x.MathScore > y.MathScore)
return 1;
if (x.MathScore < y.MathScore)
return -1;
else
return 0;
}
}
ทุกอย่างขึ้นอยู่กับว่าประเภทของคุณไม่แน่นอนหรือไม่ คุณควรเพียงใช้ IComparable เกี่ยวกับประเภทที่ไม่แน่นอน โปรดทราบว่าหากคุณใช้ IComparable คุณต้องลบล้าง Equals พร้อมด้วยตัวดำเนินการ ==,! =, <และ> (ดูคำเตือนการวิเคราะห์โค้ด CA1036)
อ้างถึง Dave G จากโพสต์บล็อกนี้ :
แต่คำตอบที่ถูกต้องคือการใช้ IComparer แทน IComparable หากวัตถุของคุณไม่แน่นอนและส่งผ่านอินสแตนซ์ของ IComparer ไปยังฟังก์ชันการเรียงลำดับเมื่อจำเป็น
เนื่องจาก IComparer เป็นเพียงวัตถุที่ใช้แล้วทิ้งที่ใช้สำหรับการจัดเรียง ณ เวลานั้นวัตถุของคุณจึงมีความหมายที่ไม่แน่นอนที่คุณต้องการได้ นอกจากนี้ยังไม่ต้องการหรือแนะนำให้ใช้ Equals, GetHashCode หรือ == - คุณมีอิสระที่จะกำหนดมันในแบบที่คุณต้องการ
สุดท้ายคุณสามารถกำหนด IComparer หลายรายการสำหรับประเภทของคุณสำหรับการจัดเรียงในฟิลด์ต่างๆหรือด้วยกฎที่แตกต่างกัน สิ่งนี้มีความยืดหยุ่นมากกว่าการจมอยู่กับคำจำกัดความเดียว
กล่าวโดยย่อ: ใช้ IComparable สำหรับประเภทมูลค่าและ IComparer สำหรับประเภทอ้างอิง
คำอธิบายง่ายๆผ่านเรื่องราว
บาสเก็ตบอลมัธยม. เป็นการเลือกสนามของโรงเรียนสำหรับทีม ฉันต้องการได้คนที่สูงที่สุด / ดีที่สุด / เร็วที่สุดในทีมของฉัน ฉันจะทำอย่างไร?
IComparer Interface - เปรียบเทียบคนสองคนแยกคน
Compare(Fred, John)
และพ่นออกมาว่าใครดีกว่ากันแล้ว IComparable ล่ะ? - เปรียบเทียบตัวเองกับคนอื่น
เมื่อเร็ว ๆ นี้คุณอยู่บน FB หรือไม่? คุณเห็นคนอื่น ๆ ทำสิ่งที่ยอดเยี่ยม: เดินทางไปทั่วโลกสร้างสิ่งประดิษฐ์ในขณะที่ฉันกำลังทำบางอย่างที่ไม่ค่อยดีนัก แต่สิ่งที่เราทำคือการใช้อินเทอร์เฟซ IComparable
แล้ว Comparer Class ล่ะ?
คลาส Comparer เป็นคลาสพื้นฐานนามธรรมที่ใช้อินเตอร์เฟส IComparer คุณควรได้รับจากคลาสนี้เพื่อนำไปใช้อย่างเป็นรูปธรรม อย่างไรก็ตาม Microsoft ขอแนะนำให้คุณใช้คลาส Comparer แทนที่จะใช้อินเทอร์เฟซ IComparer:
เราขอแนะนำให้คุณได้รับมาจากคลาส Comparer แทนที่จะใช้อินเทอร์เฟซ IComparer เนื่องจากคลาส Comparer มีการใช้อินเทอร์เฟซที่ชัดเจนของเมธอด ICompare เปรียบเทียบและคุณสมบัติดีฟอลต์ที่ได้รับตัวเปรียบเทียบดีฟอลต์สำหรับอ็อบเจ็กต์
หวังว่าเรื่องราวต่างๆจะช่วยให้คุณจำได้
อย่างที่คนอื่นบอกพวกเขาไม่ได้ทำแบบเดียวกัน
ไม่ว่าในกรณีใดทุกวันนี้ฉันมักจะไม่ใช้ IComparer ทำไมฉัน? ความรับผิดชอบ (เอนทิตีภายนอกที่ใช้ในการเปรียบเทียบวัตถุสองชิ้น) สามารถจัดการได้สะอาดกว่าด้วยนิพจน์แลมบ์ดาซึ่งคล้ายกับวิธีการทำงานของ LINQ ส่วนใหญ่ เขียนแลมบ์ดาอย่างรวดเร็วซึ่งจะนำวัตถุมาเปรียบเทียบเป็นอาร์กิวเมนต์และส่งคืนบูล และถ้าออบเจ็กต์กำหนดการดำเนินการเปรียบเทียบภายในของตัวเองก็สามารถใช้ IComparable แทนได้
IComparable กล่าวว่าวัตถุสามารถเปรียบเทียบกับวัตถุอื่นได้ IComparer คือวัตถุที่สามารถเปรียบเทียบสิ่งของสองชิ้นได้
IComparer เป็นอินเทอร์เฟซที่ใช้ในการจัดเรียง Array อินเทอร์เฟซนี้จะบังคับให้คลาสใช้เมธอด Compare (T x, T y) ซึ่งจะเปรียบเทียบอ็อบเจ็กต์ทั้งสอง อินสแตนซ์ของคลาสที่ใช้อินเทอร์เฟซนี้ถูกใช้ในการเรียงลำดับของ Array
IComparable เป็นอินเทอร์เฟซที่ใช้งานในประเภทที่ต้องการเปรียบเทียบวัตถุทั้งสองชนิดเดียวกันอินเทอร์เฟซที่เปรียบเทียบได้นี้จะบังคับให้คลาสใช้วิธีการต่อไปนี้ CompareTo (T obj)
IEqualityComparer เป็นอินเทอร์เฟซที่ใช้ในการค้นหาวัตถุไม่ว่าจะเป็น Equal หรือไม่ตอนนี้เราจะเห็นสิ่งนี้ในตัวอย่างที่เราต้องหาความแตกต่างของวัตถุในคอลเล็กชัน อินเทอร์เฟซนี้จะใช้วิธีการเท่ากับ (T obj1, T obj2)
ตอนนี้เราใช้ตัวอย่างเรามีคลาสพนักงานจากคลาสนี้เราต้องสร้างคอลเล็กชัน ตอนนี้เรามีข้อกำหนดดังต่อไปนี้
เรียงลำดับ Array โดยใช้ Array class 2 ต้องการคอลเลกชันโดยใช้ Linq: Remove the Duplicate เรียงลำดับตามสูงไปต่ำลบ ID พนักงานหนึ่งคน
abstract public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public string Address { set; get; }
}
public enum SortType
{
ByID,
BySalary
}
ระดับสาธารณะ EmployeeIdSorter: IComparer {public int Compare (Employee x, Employee y) {if (x.Id <y.Id) return 1; อื่นถ้า (x.Id> y.Id) ส่งกลับ -1; อื่นกลับ 0; }}
public class EmployeeSalarySorter : IComparer<Employee>
{
public int Compare(Employee x, Employee y)
{
if (x.Salary < y.Salary)
return 1;
else if (x.Salary > y.Salary)
return -1;
else
return 0;
}
}
สำหรับข้อมูลเพิ่มเติมอ้างอิงด้านล่าง http://dotnetvisio.blogspot.in/2015/12/usage-of-icomparer-icomparable-and.html