Uvod u svijet LINQ-a

thumb image

Uvod u LINQ

LINQ (language integrated query) je .NET Framework komponenta koja .NET jezicima (C#, VB.NET) dodaje standardne operatore za zadavanje upita. Postoji puno toga što bi se moglo reći o LINQ-u, ali  zašto je on bolji od SQL-a? Zašto nešto što dobro radi treba poboljšavati? Zašto bi netko tko već dobro rukuje SQL-om trebao prijeći na LINQ? Početnik sam, je li bolje da prvo naučim SQL pa onda LINQ? Pokušat ću na sva ova pitanja odgovoriti u ovom članku.

Za početak ćemo usporediti SQL i LINQ u ovoj tablici:

   SQL    LINQ 

Uči se uz programski jezik

Podržava ga IntelliSense

Debuggira se prije kompiliranja

Jednostavno postavljanje parametara pri upitima

Jednostavno kreiranje funkcija iz postojećih upita

Čitljivost koda

Jako se lako može potkrasti greška koju ćemo
teško uočiti i vjerojatno na nju izgubiti puno
vremena i živaca

Očito je da je LINQ bolji od SQL-a. Početnici ne trebaju učiti SQL jezik da bi stvarali upite i dohvaćali podatke iz baza podataka, a poznavatelji SQL-a će vidjeti da se LINQ puno lakše čita i shvaća te da osim jednostavnosti donosi i jako korisne dodatke kao podršku za debuggiranje. Ako nam se potkrade greška u upitu, kompajler će je prepoznati i prikazati dok kod SQL-a to ne bi tako lako uočili, nego tek pri izvršavanju kada bi dobili čudne rezultate. Za razliku od SQL-a, LINQ je podržan u IntelliSense-u pa će nam pri pisanju naredbi Visual Studio dodatno ubrzati posao.

No LINQ nije rezerviran samo za baze podataka i XML datoteke. Njime možemo zadavati upite bilo kojoj listi, nizu stringova, brojeva ili posebnih objekata te bilo kojem izvoru podataka. Područje gdje možemo primijeniti LINQ široko je i kad se naviknemo na njega, svugdje ćemo ga htjeti koristiti.

Dosta teorije, idemo vidjeti kako to izgleda u praksi. Sad ćemo napisati naš prvi program u kojem ćemo koristiti LINQ!

Par primjera korištenja LINQ-a

Za ovu demonstraciju koristio sam C#, no sintaksa za VB.NET je slična. Ako niste upoznati sa C#, na ovom linku odličan je uvod u jezik. Kreirao sam polje od 10 stringova s markama automobila. Kada bi htjeli izdvojiti samo automobile koji počinju sa slovom „A“, bez LINQ-a bismo trebali stvoriti novi niz te s for ili foreach petljom dodavati u novi niz elemente prvog niza koji bi odgovarali uvjetu. Ovdje imamo samo 10 elemenata pa je to rješenje prihvatljivo, ali da imamo na tisuće ili stotine tisuća elemenata, to rješenje bi se izvodilo presporo:

            string[] popisAuta = new string[10] { "Audi", "BMW", "Fiat", "Alfa Romeo",
"Škoda", "Ford", "Suzuki", "Toyota",
"Citroen", "Aston Martin" };
string[] noviPopis = new string[10];
int brojac = 0;
for (int i = 0; i < popisAuta.Length; i++)
{
if (popisAuta[i].StartsWith("A"))
{
noviPopis[brojac] = popisAuta[i];
brojac++;
}
}
for (int j = 0; j < brojac; j++)
{
Console.WriteLine(noviPopis[j]);
}

Zato rješenje s LINQ-om izgleda puno elegantnije i čitljivije:

            string[] popisAuta = new string[10] { "Audi", "BMW", "Fiat", "Alfa Romeo",
"Škoda", "Ford", "Suzuki", "Toyota",
"Citroen", "Aston Martin" };
IEnumerable<string> odabraniAuti = from x in popisAuta
where x.StartsWith("A")
select x;
foreach (var auto in odabraniAuti)
{
Console.WriteLine(auto);
}

Oba koda daju isti ispis na konzolu, a razlika u duljini koda je velika. No osim u duljini, razlika je u tipu novog niza. Prvim rješenjem dobili smo polje stringova, dok smo sa LINQ upitom dobili IEnumerable niz stringova. S tim nizom možemo puno toga raditi jer imamo dostupne sve LINQ funkcije (a ima ih mnogo), kao na primjer funkcija Take() s kojom možemo reći koliko elementa želimo uzeti. Kod brojevnih nizova možemo koristiti funkcije Sum() ili Average() koje će nam bez pisanja dodatnog koda vratiti zbroj elemenata ili prosječnu vrijednost:

            IEnumerable<int> brojevi = { 1, 2, 3, 4, 5, 6 };
int suma = brojevi.Sum();
int prosjek = brojevi.Average();

Analizirajmo ovaj dio koda:

            IEnumerable<string> odabraniAuti = from x in popisAuta
where x.StartsWith("A")
select x;

Crvenom bojom sam označio operatore, ovako se najčešće piše LINQ upit. Ovako bi to izgledalo na hrvatskom:

            IEnumerable<string> odabraniAuti = iz varijable x koja je u popisAuta
gdje x počinje sa "A"
odaberi x;

Jedini obavezni operatori su from, in i select. Operator where koristimo ako želimo postaviti neke uvjete. Ova linija koda bi nam vratila isti početni niz samo tipa IEnumerable<string>:

            IEnumerable<string> odabraniAuti = from x in popisAuta select x;

Možemo koristiti i više uvjeta kod where operatora:

            IEnumerable<string> odabraniAuti = from x in popisAuta
where x.StartsWith("A")
|| x.StartsWith("F")
&& x.EndsWith("d")
select x;

Ovaj LINQ upit vratit će niz automobilskih marki koje počinju sa “A” ili počinju sa “F” i završavaju sa “d”. Prilično jednostavno, zar ne? Sad zamislite da s minimalnim promjenama ovaj kod možete koristiti za filtriranje podataka iz baze podataka s milijun zapisa, koristeći više uvjeta i vraćajući samo određene podatke koji su vam potrebni – moguće je!

Ovo je samo mali prikaz što se sve može sa LINQ-om. Ako želite preuzeti ovaj kod, možete ga preuzeti ovdje. Ako želite naučiti više o LINQ na MSDN-u ima puno materijala i primjera. Isto tako preporučam jedan vrlo koristan program za eksperimentiranje s LINQ-om, a to je LINQPad. Besplatan je i vrlo malen, a ima mnogo mogućnosti. U njemu možete isprobavati LINQ upite i odmah vidjeti što se zbiva bez da komplilirate program. A za vas koji programirate u VB.NET-u imam link na seriju video-predavanja s kojima možete vidjeti kako LINQ izgleda u VB.NET jeziku.

Nadam se da sam vas zainteresirao za LINQ i da sam uspio prilično dosadno područje učiniti zanimljivim smiley

Pin It