200 likes | 446 Views
MPP. Dr. Vasile Cioban. C# – Elemente specifice C# 4.0 Propriet ăţ i implementate automat (1). Fie clasa de mai jos î n care se asociaz ă o proprietate datei camp class Clasa { private int camp; public int Camp {get { return camp; } set { camp = value;} } }
E N D
MPP Dr. Vasile Cioban
C# – Elemente specifice C# 4.0Proprietăţi implementate automat (1) • Fie clasa de mai jos în care se asociază o proprietate datei camp class Clasa { private int camp; public int Camp {get { return camp; } set { camp = value;} } } • Deoarece codul de tipul celui scris mai sus apare foarte des, s-a pus problema simplificarii lui. In C# 4.0 se scrie echivalent: class Clasa { public int Camp {get; set; } }
C# – Elemente specifice C# 4.0Proprietăţi implementate automat (2) • Se foloseste aici mecanismul de implementare automata a unei proprietati care actioneaza asupra unor campuri private autodeclarate; aceasta proprietate returneaza sau acceseaza direct campul asociat. • Particularitatile sunt urmatoarele: • 1.nu se declara campul privat; acesta este creat automat de compilator, pe baza proprietatii auto-implementate; • 2.nu se scriu implementari pentru get si set; corpul lor este caracterul “;”; get acceseaza campul autodeclarat, set seteaza valoarea campului cu ce se afla ın dreapta semnului egal; • 3.nu se poate accesa campul autodeclarat altfel decat prin intermediul proprietatii; • 4. proprietatea nu poate fi read-only sau write-only, ci doar read–write. • Daca ulterior se decide implementarea unui accesor de catre programator, atunci si celalalt trebuie implementat si campul privat trebuie declarat ın mod explicit. Important este ınsa ca se scrie un minim de cod pentru a genera un contract: camp privat accesat prin proprietate publica.
C# – Elemente specifice C# 4.0Initializatori de obiecte (1) • Sa consideram clasa: class Persoana {private string nume; public string Nume {get { return nume; } set { nume= value;} } private string prenume; public string Prenume {get { return prenume;} set { prenume = value; } } private int varsta; public int Varsta {get { return varsta;} set { varsta = value; } } }
C# – Elemente specifice C# 4.0Initializatori de obiecte (2) • Se poate scrie urmatoarea secventa de cod care initializeaza o persoana cu datele cuvenite: Persoana p = new Persoana(); p.Prenume = “Ion"; p.Varsta = 25; p.Nume = "Popescu"; • In C# 4.0 se poate scrie mai succint: Persoana p = new Persoana { Prenume = “Ion",Varsta = 25, Nume = "Popescu" }; cu acelasi rezultat. Intr-un astfel de caz se face mai ıntai apelarea constructorului implicit (indiferent de cine anume ıl scrie - compilatorul sau programatorul) si apoi se face accesarea proprietatilor, ın ordinea scrisa la initializator. Membrii pentru care se face initializare trebuie sa fie publici; ın particular, ei pot fi si campuri, dar acest lucru nu este ıncurajat de principiul ıncapsularii. Putem avea inclusiv proprietati auto-implementate (sectiunea anterioara)
C# – Elemente specifice C# 4.0Initializatori de colectii (1) • Se da secventa de cod: List<String> lista = new List<String>(); lista.Add("a"); lista.Add("b"); lista.Add("c"); In C# 4.0 ea este echivalentacu: List<String> lista = new List<String>(){"a", "b", "c"}; • Initializarea colectiilor vine sa ofere acelasi mecanism ca siın cazul tablourilor. Exemplul poate fi completat cu popularea unei colectii de obiecte compuse: List<Persoana> persoane = new List<Persoana>() {new Persoana {Prenume = “Ion", Nume="Popescu", Varsta=25}, new Persoana {Prenume = “Jon", Nume="Ionescu", Varsta=17} };
LINK Generaliati (1) • Language INtegrated Query (LINQ, pronuntat precum “link”) permite interogarea unor colectii de date folosind o sintaxa integrata ın platforma .NET. • Prin intermediul unor operatori se pot interoga colectii de forma: • tablouri, • colectii, • clase enumerabile, • documente XML, • baze de date relationale. • Datele rezultate sunt vazute ca obiecte; are loc o mapare (asociere, traducere) a unor date neobiectuale ıntr–un format usor de folosit ın limbajele obiectuale din cadrul plaformei. Trebuie mentionat ca sintaxa este unitara, independent de natura sursei de date.
LINK Generaliati (2) • Exemple: • var query = from e in employees where e.id == 1 select e.name • var results = from product in productsCollection where product.UnitPrice < 100 select new {product.ProductName, product.UnitPrice}; foreach (var result in results) { Console.WriteLine (result); }
LINK Generaliati (3) • Este introdusa interfata IQueryable<T>, care permite implementarea unor furnizori de date ın modul specific sursei de date considerate. • Expresia folosita pentru interogare este tradusa ıntr-un arbore de expresie. • Daca colectia implementeaza IEnumerable<T>, atunci se foloseste motorul de executie LINQ local, integrat ın platforma; daca colectia implementeaza IQueryable<T>, atunci se foloseste implementarea bazata pe arborele de expresie; aceasta implementare este data de catre furnizoare de LINQ. • Furnizoarele de LINQ sunt scrise ın mod specific fiecarei surse de date, dar datorita respectarii unor interfete specificate, detaliile de implementare sunt irelevante pentru cel care foloseste cod LINQ ın interogare.
LINK Generaliati (4) • LINQ a fost introdus ın versiunea 3.5 a lui .NET Framework. Consta ıntr–un set de unelte care sunt folosite pentru lucrul cu date si extensii aduse limbajului. Este alcatuit din: • LINQ to Objects – se aduc date din colectii care implementeaza IEnumerable<T>; datele interogate sunt deja ın memoria procesului; • LINQ to XML – converteste documentele XML ıntr–o colectie de obiecte de tip XElement; • LINQ to SQL – permite convertirea interogarilor LINQ ın comenzi SQL; • LINQ to DataSets – spre deosebire de LINQ to SQL care a venit initial doar cu suport suport pentru SQL Server, LINQ to DataSets foloseste ADO.NET pentru comunicarea cu baze de date; • LINQ to Entities – solutie Object/Relational Mapping de la Microsoft ce permite utilizarea de Entities – introduse ın ADO.NET 3.0 – pentru a specifica declarativ structura obiectelor ce modeleaza domeniul si foloseste LINQ pentru interogare.
LINK Generaliati (5) • Exista urmatorii furnizori de date LINQ: 1. LINQ to MySQL, PostgreSQL, Oracle, Ingres, SQLite si Microsoft SQL Server 2. LINQ to CSV 3. LINQ to Google 4. LINQ to NHibernate 5. LINQ to System Search • Este dezvoltat si PLINQ, (Parallel LINQ), un motor ce foloseste paralelizarea de cod pentru executare mai rapida a interogarilor, ın cazul unui sistem multi-nucleu sau multiprocesor. • Exista doua motive pentru care LINQ este util: • codul stufos, neproductiv utilizat pentru accesarea ın modul clasic a datelor; • nepotrivirea paradigmelor obiectual–relationale.
LINK Codul clasic ADO.NET(1) • Pentru accesarea datelor dintr-o baza de date relationala, folosind ADO.NETse scrie de regula un cod de forma: • using ( SqlConnection connection = new SqlConnection (“…” ) ) {connection.Open (); SqlCommand command = connection.CreateCommand(); command.CommandText = @"SELECT Name, Country FROM Customers WHERE City = @City"; command.Parameters.AddWithValue(“@City" , "Paris"); using (SqlDataReader reader = command.ExecuteReader ()) {while (reader.Read()) {string name = reader.GetString (0); string country= reader.GetString (1); . . . } } }
LINK Codul clasic ADO.NET(2) • Se remarca urmatoarele: • cantitatea de cod scrisa; codul de sus este unul des folosit, scrierea lui ın repetate randuri este contraproductiva; • interogarile sunt exprimate prin intermediul unei fraze scrise ıntre ghilimele, ca sir de caractere, deci automat nu se poate verifica prin compilarea corectitudinea codului SQL continut; este adevarat, ınsa, ca se pot folosi aici proceduri stocate care sunt compilate deja pe server; • slaba tipizare a parametrilor: daca tipul acestora nu coincide cu ce se afla ın baza de date daca numarul de parametri este incorect (asta se semnaleaza numai la rulare, ca eroare; de preferat ar fi fost sa se depisteze acest lucru la compilare); • de cele mai multe ori trebui folosit un dialect de SQL specific producatorului serverului de baze de date; codul SQL nu este portabil; totodata: mixarea de limbaje – C# si SQL – face codul greu de urmarit.
LINK Codul clasic ADO.NET(3) O expresie LINQ care care demonstreaza depasirea acestor probleme este: • from customer in customers where customer.Name.StartsWith ( "A" ) && customer.Orders.Count > 10 orderby customer.Name select new { customer.Name, customer.Orders }
LINK Nepotrivirea de paradigme (1) • Paradigma este “o constructie mentala larg acceptata, care ofera unei comunitati sau unei societati pe perioada ındelungata o baza pentru crearea unei identitati de sine (a activitatii de cercetare de exemplu) si astfel pentru rezolvarea unor probleme sau sarcini”. • Exista o diferenta sesizabila ıntre programarea orientata pe obiecte, utilizata ın cadrul limbajelor folosite pentru implementarea aplicatiilor si modul de stocare si reprezentare a datelor: XML sau baze de date relationale. • Translatarea unui graf de obiecte din reprezentarea obiectuala ıntr–o alta reprezentare este greoaie: programatorul trebuie sa ınteleaga si particularitatile structurilor de date folosite pentru persistarea lor, pe langa cunoasterea limbajului ın care lucreaza.
LINK Nepotrivirea de paradigme (2) • Problema pe care LINQ o abordeaza este “rezolvarea” urmatoarelor inegalitati: •“Data != Objects” • “Relational data != Objects” • “XML data != Objects” • “XML data != Relational data”
LINK Nepotrivirea de paradigme (3) • Toate aceste nepotriviri necesita efort de adaptare din partea programatorului. Modelarea obiectual– relationala este problema cea mai des ıntalnita, cu urmatoarele aspecte: 1. tipurile de date folosite de catre modelele relationale si modelele obiectuale nu sunt aceleasi; de exemplu, multitudinea de tipuri sir de caractere folosite ın specificarea coloanelor, ın timp ce ın .NET exista doar tipul String; 2. modelele relationale folosesc normalizarea (pentru eliminarea redundantei si a anomaliilor de inserare, stergere, modificare), ın timp ce modelarea obiectuala nu trebuie sa treaca prin asa ceva; ın schimb, modelarea obiectuala foloseste agregarea sau mostenirea, mecanisme care nu ısi au un echivalent direct ın modelarea relationala 3. modele de programare diferite: pentru SQL se foloseste un limbaj declarativ care specifica ce se doreste, ın timp ce limbajele de programare folosite sunt de regula imperative – arata cum se face prelucrarea 4. ıncapsulare – ascunderea detaliilor si legarea impreuna a datelor cu metodele care prelucreaza datele; • Toate aceste probleme se manifesta ıncepand cu maparea ıntre obiecte si datele persistate. Aceeasi problema apare daca ne referim la XML, care favorizeaza un model ierarhic, semistructurat. Programatorul trebuie sa scrie mereu un cod care sa faciliteze legarea acestor universuri diferite. LINQ vine cu o propunere de rezolvare.