Programiranje

SQL sproščen: 17 načinov za pospešitev poizvedb SQL

Razvijalci SQL na vsaki platformi se trudijo, na videz zataknjeni v NAREDITE zanka, zaradi katere vedno znova ponavljajo iste napake. To je zato, ker je polje baze podatkov še vedno razmeroma nezrelo. Seveda prodajalci nekaj napredujejo, vendar se še naprej spopadajo z večjimi težavami. Sočasnost, upravljanje virov, upravljanje prostora in hitrost še vedno mučijo razvijalce SQL-a, ne glede na to, ali kodirajo na SQL Server, Oracle, DB2, Sybase, MySQL ali kateri koli drugi relacijski platformi.

Del težave je v tem, da ni čarobne krogle in za skoraj vsako najboljšo prakso vam lahko pokažem vsaj eno izjemo. Običajno razvijalec najde svoje priljubljene metode - čeprav običajno ne vključujejo nobenih konstruktov za zmogljivost ali sočasnost - in se ne trudi raziskovati drugih možnosti. Mogoče je to simptom pomanjkanja izobrazbe ali pa so razvijalci preveč blizu procesa, da bi prepoznali, kdaj delajo kaj narobe. Mogoče poizvedba dobro deluje na lokalnem naboru testnih podatkov, vendar v proizvodnem sistemu ne uspe.

Ne pričakujem, da bodo razvijalci SQL postali skrbniki, vendar morajo pri pisanju svoje kode upoštevati produkcijske težave. Če tega ne storijo med začetnim razvojem, jih bodo skrbniki programov za pravice le prisilili, da se vrnejo in to storijo pozneje - uporabniki pa v tem času trpijo.

Obstaja razlog, zakaj pravimo, da je uravnavanje baze podatkov umetnost in znanost. To je zato, ker obstaja zelo malo hitrih pravil, ki veljajo na splošno. Težave, ki ste jih rešili v enem sistemu, niso težave v drugem in obratno. Glede nastavitve poizvedb ni pravega odgovora, vendar to ne pomeni, da bi morali odnehati.

Obstaja nekaj dobrih načel, ki jim lahko sledite, kar bi dalo rezultate v eni ali drugi kombinaciji. Vključil sem jih v seznam SQL-jev in ne, ki jih pogosto spregledamo ali jih je težko opaziti. Te tehnike bi vam morale dati malo večji vpogled v misli vaših DBA-jev, pa tudi sposobnost, da začnete procese razmišljati na proizvodno usmerjen način.

1. Ne uporabljajte NADGRADNJA namesto OVITEK

Ta težava je zelo pogosta in čeprav je ni težko opaziti, jo mnogi razvijalci pogosto spregledajo, ker uporabljajo NADGRADNJA ima naravno lastnost, ki se zdi logična.

Vzemimo na primer ta scenarij: podatke vstavljate v začasno tabelo in jih potrebujete za prikaz določene vrednosti, če obstaja druga vrednost. Mogoče vlečete iz tabele strank in želite, da je vsak, ki ima več kot 100.000 USD naročil, označen kot »Prednostno«. Tako vstavite podatke v tabelo in zaženete datoteko NADGRADNJA izjavo za nastavitev stolpca CustomerRank na »Preferred« za vse, ki imajo več kot 100.000 USD naročil. Težava je v tem, da NADGRADNJA stavek je zapisan, kar pomeni, da mora za vsak zapis v tabelo zapisati dvakrat. Pot okoli tega je seveda uporaba inlinea OVITEK stavek v sami poizvedbi SQL. Ta preizkusi vsako vrstico za pogoje zneska naročila in nastavi oznako »Prednostno«, preden je zapisana v tabelo. Povečanje zmogljivosti je lahko osupljivo.

2. Ne uporabljajte slepo kode

Tudi to vprašanje je zelo pogosto. Kopiranje kode nekoga drugega je zelo enostavno, saj veste, da vnese podatke, ki jih potrebujete. Težava je v tem, da pogosto potegne veliko več podatkov, kot jih potrebujete, razvijalci pa se le redko obremenjujejo, zato na koncu dobijo ogromno podatkov. Običajno je v obliki dodatnega zunanjega spoja ali dodatnega stanja v KJE klavzulo. Če vnovično uporabljeno kodo obrežete na svoje natančne potrebe, lahko dosežete velik napredek.

3. Povlecite le toliko stolpcev, kot jih potrebujete

Ta številka je podobna številki št. 2, vendar je značilna za stolpce. Vse vaše poizvedbe je preveč enostavno kodirati IZBERI * namesto da bi posamezno naštevali stolpce. Težava je spet v tem, da povleče več podatkov, kot jih potrebujete. To napako sem videl že desetkrat in večkrat. Razvijalec naredi IZBERI * poizvedba proti tabeli s 120 stolpci in milijoni vrstic, vendar se konča z uporabo le treh do petih. Takrat obdelate toliko več podatkov, kot jih potrebujete, je čudno, da se poizvedba sploh vrne. Ne obdelujete samo več podatkov, kot jih potrebujete, ampak tudi drugim procesom odvzemate vire.

4. Ne dvojno potapljajte

Tu je še ena, ki sem jo videl večkrat, kot bi jo moral: Shranjena procedura je napisana tako, da potegne podatke iz tabele s sto milijoni vrstic. Razvijalec potrebuje stranke, ki živijo v Kaliforniji in imajo dohodek več kot 40.000 USD. Zato poizveduje za stranke, ki živijo v Kaliforniji, in rezultate postavi v začasno tabelo; nato poizveduje za stranke z dohodki nad 40.000 USD in te rezultate postavi v drugo začasno tabelo. Končno se pridruži obema tabelama, da dobi končni izdelek.

Ali se hecate? To je treba storiti z eno samo poizvedbo; namesto tega dvakrat potapljate izjemno veliko mizo. Ne bodite bedaki: poiščite velike tabele le enkrat, kadar koli je to mogoče - ugotovili boste, kako boljši so vaši postopki.

Nekoliko drugačen scenarij je, ko je v več korakih v procesu potrebna podmnožica velike tabele, zaradi česar je treba vsako mizo povprašati po veliki tabeli. Temu se izognite tako, da povprašate po podnaboru in ga vztrajate drugje, nato pa usmerite nadaljnje korake na manjši nabor podatkov.

6. Naredite podatke pred fazo

To je ena mojih najljubših tem, ker gre za staro tehniko, ki jo pogosto spregledamo. Če imate poročilo ali postopek (ali še bolje, nabor od njih), ki bo naredil podobne združitve z velikimi tabelami, vam lahko koristi, če podatke predhodno pripravite tako, da se predčasno pridružite tabelam in jih vztrajate. v mizo. Zdaj se lahko poročila zaženejo proti tej vnaprej postavljeni tabeli in se izognejo velikemu združevanju.

Te tehnike ne morete vedno uporabljati, toda ko boste lahko, boste ugotovili, da je to odličen način za prihranek strežniških virov.

Upoštevajte, da se mnogi razvijalci te težave z združevanjem rešijo tako, da se osredotočijo na samo poizvedbo in ustvarijo samo pogled okoli združevanja, tako da jim ni treba vedno znova vnašati pogojev združevanja. Toda težava tega pristopa je, da se poizvedba še vedno izvaja za vsako poročilo, ki ga potrebuje. S predhodnim uprizoritvijo podatkov združitev zaženete samo enkrat (recimo 10 minut pred poročili), vsi ostali pa se izognejo velikemu združevanju. Ne morem vam povedati, kako zelo imam rad to tehniko; v večini okolij obstajajo priljubljene tabele, ki se ves čas združujejo, zato ni razloga, da jih ne bi bilo mogoče predpripraviti.

7. Brisanje in posodabljanje v serijah

Tu je še ena enostavna tehnika, ki jo veliko spregledamo. Brisanje ali posodabljanje velike količine podatkov iz ogromnih tabel je lahko nočna mora, če tega ne storite pravilno. Težava je v tem, da se oba stavka izvajata kot ena transakcija in če jih morate ubiti ali če se sistemu kaj zgodi, ko delujejo, mora sistem povrniti celotno transakcijo. To lahko traja zelo dolgo. Te operacije lahko blokirajo tudi druge transakcije za čas njihovega trajanja, kar v bistvu povzroči ozko grlo sistema.

Rešitev je v brisanju ali posodobitvah v manjših serijah. To rešuje vaš problem na nekaj načinov. Prvič, če se transakcija iz kakršnega koli razloga uniči, ima le malo vrstic, ki jih je mogoče vrniti nazaj, zato se baza podatkov hitreje vrne v splet. Drugič, medtem ko se manjše serije zapisujejo na disk, se druge lahko prikradejo in opravijo nekaj dela, zato je sočasnost močno izboljšana.

V skladu s tem se mnogim razvijalcem zatika v glavi, da je treba te operacije brisanja in posodabljanja končati isti dan. To ni vedno res, še posebej, če arhivirate. To operacijo lahko raztegnete tako dolgo, kot je potrebno, in manjše serije vam to pomagajo. Če lahko za intenzivne postopke vzamete več časa, porabite dodaten čas in ne spuščajte sistema.

8. Za izboljšanje zmogljivosti kazalca uporabljajte začasne tabele

Upam, da že vsi vemo, da se je najbolje držati stran od kazalcev, če je le mogoče. Kazalci ne trpijo samo zaradi težav s hitrostjo, kar je lahko težava pri številnih operacijah, temveč lahko povzroči, da vaše delovanje blokira druge operacije veliko dlje, kot je potrebno. To močno zmanjša sočasnost v vašem sistemu.

Vendar se ne morete vedno izogniti uporabi kazalcev in ko se ti časi pojavijo, se boste morda lahko izognili težavam, ki jih povzročajo kazalci, tako da namesto tega opravite operacije kurzorja v začasni tabeli. Vzemimo na primer kazalko, ki gre skozi tabelo in na podlagi nekaterih rezultatov primerjave posodobi nekaj stolpcev. Namesto primerjave z živo tabelo boste morda lahko te podatke dali v začasno tabelo in namesto tega izvedli primerjavo s to tabelo. Potem imate singla NADGRADNJA izjava proti mizi v živo, ki je veliko manjša in ima ključavnice le kratek čas.

Takšno spreminjanje podatkov lahko močno poveča sočasnost. Na koncu bom rekel, da vam skoraj nikoli ni treba uporabiti kurzorja. Skoraj vedno obstaja rešitev, ki temelji na naboru; se moraš naučiti videti.

9. Ne gnezdi pogledov

Pogledi so lahko priročni, vendar morate biti previdni pri njihovi uporabi. Čeprav lahko pogledi pomagajo prikriti veliko poizvedb uporabnikom in poenotijo ​​dostop do podatkov, se lahko enostavno znajdete v položaju, ko imate poglede, ki kličejo poglede, ki kličejo poglede, ki prikazujejo klice. To se imenuje gnezdenje pogledov, in lahko povzroči resne težave z zmogljivostjo, zlasti na dva načina:

  • Prvič, zelo verjetno se vam bo vrnilo veliko več podatkov, kot jih potrebujete.
  • Drugič, optimizator poizvedb se bo odrekel in vrnil slab načrt poizvedbe.

Nekoč sem imel stranko, ki je rada gnezdila poglede. Stranka je imela en pogled, ki ga je uporabila za skoraj vse, ker je imela dva pomembna združevanja. Težava je bila v tem, da je pogled vrnil stolpec z 2 MB datotek. Nekateri dokumenti so bili še večji. Naročnik je v skoraj vsako posamezno poizvedbo v omrežje potisnil vsaj dodatnih 2 MB v vsako vrstico. Seveda je bila uspešnost poizvedb neskladna.

In nobeno od poizvedb dejansko ni uporabljalo tega stolpca! Seveda je bila kolona zakopana sedem pogledov globoko, zato je bilo celo težko najti. Ko sem stolpec dokumenta odstranil iz pogleda, je čas največje poizvedbe trajal od 2,5 ure do 10 minut. Ko sem končno razvozlal ugnezdene poglede, ki so imeli več nepotrebnih združitev in stolpcev, in napisal navadno poizvedbo, je čas za isto poizvedbo padel na sekunde.