Kogud on OOP-is oluline kontseptsioon ning täielik tugi C# kogudele on üks parimaid selles keeles.
Miks kasutada üldisi komplekte? Enne C# 2.0 sai kogumikke rakendada kahel peamisel viisil: a. Kasuta ArrayListi Objektide otse ArrayListi panemine on intuitiivne, kuid kuna kogu elemendid on tüüpi Object, pead iga kord selle kasutamisel tegema tüütut tüübi teisendamist. b. Kasuta kohandatud kollektsiooniklasse Levinud praktika on pärida kohandatud klass CollectionBase abstraktsest klassist ja rakendada tugev tüübikogu, kapseldades IList objekti. See meetod nõuab iga kogumitüübi jaoks vastava kohandatud klassi kirjutamist, mis on palju tööd. Üldiste kogude tekkimine lahendab ülaltoodud probleemid hästi ning ainult ühte koodirida saab kasutada kindla tüübi komplekti loomiseks. Mis on geneeriline? Üldised on uued elemendid C# 2.0-s (C++ keeles nimetatakse mallideks), mida kasutatakse peamiselt sarnaste probleemide lahendamiseks. See mehhanism võimaldab klassi nime edastada argumendina üldisele tüübile ning vastav objekt genereeritakse. Võib-olla on parem mõelda üldistele (sealhulgas klassidele, liidestele, meetoditele, delegaatidele jne) kui mallidele, kus variant asendatakse argumendina edastatud klassinimega, mille tulemusena tekib uus tüübi definitsioon. Üldine teema on suhteliselt lai ja ma ei hakka seda siin üksikasjalikult analüüsima, ning huvilised saavad vastavat infot kasutada. Kuidas ma saan luua üldise kollektsiooni? List generic klass System.Collections.Generic nimeruumi <T>all kasutatakse kogude loomiseks ning süntaks on järgmine: [mw_shl_code=csharp,true] List<T> OfT = uus List<T>(); [/mw_shl_code] "T" on kasutatav tüüp, mis võib olla lihtsad tüübid, nagu string, int või kasutaja määratud tüübid. Vaatame konkreetset näidet.
Isiku klass on defineeritud järgmiselt: [mw_shl_code=csharp,true]klass Isik
{ privaatne string _name; Nimi privaatne intellekt _age; Vanus
Loo Inimese objekt avalik isik (stringi nimi, intellekt vanus) { this._name= Nimi; this._age = Vanus; }
Nimi avaliku stringi nimi { get { return _name; } }
Vanus public int Age { get { return _age; } }
}
//创建Person对象 Isik p1 = uus isik ("Zhang San", 30); Isik p2 = uus isik ("Li Si", 20); Isik p3 = uus isik ("Wang Wu", 50);
//创建类型为Person的对象集合 List<Person> persons = uus List<Person>();
//将Person对象放入集合 isikud. Add(p1); isikud. Add(p2); isikud. Add(p3);
//输出第2个人的姓名 Console.Write(persons[1]. Nimi); [/mw_shl_code] Nagu näha, lihtsustavad üldised kogud oluliselt kogude rakenduskoodi, mille kaudu saab hõlpsasti luua kindlat tüüpi kollektsioone. Lisaks pakuvad üldised kogud ka võimsamaid funktsioone, vaatame nende sorteerimist ja otsimist. Üldiste kogude sorteerimine Sorteerimine põhineb võrdlusel ja sorteerimiseks tuleb esmalt võrrelda. Näiteks, kui on kaks arvu 1 ja 2, siis nende sorteerimiseks peame esmalt neid kahte arvu võrdlema ja sorteerima vastavalt võrdlustulemustele. Kui tahad objekte võrrelda, on olukord veidi keerulisem, näiteks kui võrdled isiku objekte, saad võrrelda nime või vanuse järgi, mis nõuab võrdlusreeglite määramist. Objektil võib olla mitu võrdlusreeglit, kuid ainult üks vaikimisi reegel, mis asub klassis, mis objekti määratleb. Vaikimisi võrdlusreeglid on määratletud CompareTo meetodis, mis kuulub IComparable <T>üldise liidesega. Vaata allolevat koodi: [mw_shl_code=csharp,true]klass Isik :IComparable<Person>
{ Võrdle vanuse järgi public int Võrdle (isik p) { Anna see tagasi. Vanus - p.Vanus; } }[/mw_shl_code] CompareTo meetodi parameetrid on võrreldav teine sama tüüpi objekt, tagastusväärtus on int tüüp, kui tagastusväärtus on suurem kui 0, tähendab see, et esimene objekt on suurem kui teine objekt, kui tagastusväärtus on väiksem kui 0, tähendab see, et esimene objekt on väiksem kui teine objekt, ja kui tagastatakse 0, on need kaks objekti võrdsed. Pärast vaikimisi võrdlusreeglite määratlemist saad kogu sorteerimismeetodiga ilma parameetriteta sorteerida järgmiselt: [mw_shl_code=csharp,true]// Sorteeri kogu vaikimisi reeglite järgi isikud. Sort();
//输出所有人姓名 foreach (isik p isikutes)
{ Console.WriteLine(p.Name); Väljundi järjekord on "Li Si", "Zhang San" ja "Wang Wu" }[/mw_shl_code] Praktikas on sageli vajalik sorteerida kogu erinevate reeglite järgi, mis nõuab teiste võrdlusreeglite defineerimist, mida saab määratleda Võrdlusmeetodis, mis kuulub ICompareri <T>üldisesse liidesesse – vt järgmist koodi: [mw_shl_code=csharp,true]klassi NimiVõrdleja : IComparer<Person>
{ Salvestussekvenseri instantsid public static NameComparer Default = new NameComparer();
Võrdle nime järgi public int Võrdle (isik lk 1, isik lk 2) { return System.Collections.Comparer.Default.Compare(p1. Nimi, lk 2. Nimi); } }[/mw_shl_code] Võrdlusmeetodi parameetrid on kaks sama tüüpi objekti, mida tuleb võrrelda, tagastusväärtus on int tüüpi ning tagastusväärtuse töötlemise reeglid on samad mis CompareTo meetodil. Comparer.Default tagastab sisseehitatud võrdleja objekti kahe sama tüüpi objekti võrdlemiseks. Siin on, kuidas sorteerida kogu selle äsja määratletud võrdlejaga: [mw_shl_code=csharp,true]//Sorteeri kogu nime järgi isikud. sort(NameComparer.Default);
//输出所有人姓名 foreach (isik p isikutes)
{ Console.WriteLine(p.Name); Väljundi järjekord on "Li Si", "Wang Wu" ja "Zhang San" }[/mw_shl_code] Saad ka kollektsiooni sorteerida, delegeerides esmalt meetodi, mida delegaat kutsub võrdlusreeglite salvestamiseks, ning kasutada staatilist meetodit. Vaata allolevat koodi: [mw_shl_code=csharp,true]klass IsikVõrdlus
{ Võrdle nime järgi avalik staatiline intellekt Nimi (isik p1, isik l2) { return System.Collections.Comparer.Default.Compare(p1. Nimi, lk 2. Nimi); } }[/mw_shl_code] Meetodi parameetrid on võrreldavad kaks sama tüüpi objekti: tagastusväärtus on int tüüpi ning tagastusväärtuse töötlemise reegel on sama mis CompareTo meetodil.Seejärel sorteeri kogu sisseehitatud üldise delegaatisüsteemi kaudu. Võrdlus<T>: [mw_shl_code=csharp,true] System.Comparison<Person> NameComparison = uus System.Comparison<Person>(PersonComparison.Name); isikud. Sort(NimiVõrdlus);
//输出所有人姓名 foreach (isik p isikutes)
{ Console.WriteLine(p.Name); Väljundi järjekord on "Li Si", "Wang Wu" ja "Zhang San" }[/mw_shl_code] On näha, et viimased kaks meetodit suudavad kogumikku sorteerida vastavalt määratud reeglitele, kuid autor eelistab kasutada delegeerimismeetodit ning võib kaaluda erinevate võrdlusreeglite paigutamist ühte klassi ja seejärel neid paindlikult nimetada. Otsi üldisi kogusid Otsing seisneb selles, et leida kogumikust konkreetseid tingimusi, ning vajadusel saab määratleda ja kutsuda mitmeid otsingutingimusi. Esiteks määratlege otsingukriteeriumid järgmiselt: [mw_shl_code=csharp,true]klass Isik Predikaat
{ Leia keskealised inimesed (üle 40) avalik staatiline bool Midage (isik p) { kui (lk Vanus >= 40) return true; else tagasta vale; } }[/mw_shl_code] Ülaltoodud otsingukriteeriumid on paigutatud staatilisse meetodisse, millel on Boole'i tagastustüüp, ning kogus olevad üksused, mis vastavad teatud tingimustele, tagastavad tõesed, muidu väärad.Seejärel otsi kogumikku sisseehitatud üldise delegaadi System.Predicate <T>kaudu: [mw_shl_code=csharp,true] System.Predicate<Person> MidAgePredicate = uus System.Predicate<Person>(Isik) Predicate.MidAge); Loend<Person> MidAgePersons = isikud. FindAll(MidAgePredicate);
//输出所有的中年人姓名 foreach (isik p keskealiste inimeste seas)
{ Console.WriteLine(p.Name); Väljund "Wang Wu" }[/mw_shl_code] Generiliste kogude laiendamine Mis siis, kui tahad saada kõigi komplektis olevate inimeste nimed, eraldatuna komaga? Arvestades, et ühe klassi pakutav funktsionaalsus on piiratud, on loomulik <T>mõelda List-klassi laiendamisele, mis on samuti klass ja seetõttu saab seda pärilikkuse kaudu laiendada. Vaata allolevat koodi: [mw_shl_code=csharp,true]// Defineeri Isikute kollektsiooni klass klassi isikud : nimekiri<Person>
{ Hangi kõigi kollektsiooni liikmete nimed avalik string GetAllNames() { kui (see. Loendus == 0) return "";
string val = """; foreach (isik p selles) { val += p.Name + ","; }
Tagasta Val. Alamstring(0, val. Pikkus - 1); }
}
//创建并填充Persons集合 Isikud PersonCol = uued isikud(); PersonCol.Add(p1); PersonCol.Add(p2); PersonCol.Add(p3);
//输出所有人姓名 Console.Write(PersonCol.GetAllNames()); Väljund "Zhang San, Li Si, Wang Wu"[/mw_shl_code] Kokkuvõte: See artikkel keskendub üldikute kasutamisele C# 2.0-s kogude rakendamiseks ning kogumisfunktsiooni laiendamiseks ning üldiste kogude õige kasutamine võib vähendada töö dubleerimist ja oluliselt parandada arenduse efektiivsust. Tegelikult on komplektid lihtsalt tüüpiline üldkirjade rakendus ning kui soovid geneerikute kohta rohkem teada, võid vaadata ka teisi asjakohaseid materjale. Loodan, et see artikkel oli sulle kasulik :-)
|