Internet Derazalar Android
Kengaytirmoq

Bo'limning SQL orollari qoldig'i. MySQL ma'lumotnomasi qo'llanmasi

Bu yana bir oddiy vazifa. Asosiy printsip boshqa atribut yoki atributni (buyurtma elementiga) (buyurtma elementi) buyrug'iga binoan, boshqa atribut yoki atributlar (qism elementi) asosida ko'rsatilgan qatorlar mavjud bo'lganda. Bank hisobvaraqlarida qoldiqlarni hisoblash, aktsiyalarda yoki hozirgi savdo raqamlari mavjudligini kuzatish kabi ko'plab natijalarni hisoblashda ko'plab misollar mavjud.

SQL Server 2012 echimlariga voqea natijalarini hisoblash uchun ishlatiladigan va foydalanilgan. Shu sababli, odamlar odatda do'stona ish olib borayotgan Iterativ qarorlarga murojaat qilishdi, ammo ba'zi holatlarda barmoqlar asosida echimlarga qaraganda tezroq. SQL Server 2012-da qo'llab-quvvatlanadigan oynalarning kengaytirilganligi sababli, o'sib borayotgan natijalarni oddiy kvadrat asosida hisoblash mumkin, ularning ishlashi, ikkalasi ham SABS va itorizatsion asosida, ikkalasi ham eski T-SQL asosida echimlarga qaraganda ancha yuqori . Men yangi echimni ko'rsata olaman va keyingi qismga o'tsam; Ammo shunda siz o'zgarishlar ko'lamini chindan ham tushunasiz, men eski usullarni tasvirlab beraman va ularning ishlashini yangi yondashuv bilan solishtiraman. Tabiiyki, siz faqat yangi yondashuvni tasvirlaydigan birinchi qismni o'qish huquqiga egasiz, maqolaning qolgan qismini o'tkazib yuboring.

Turli xil echimlarni namoyish etish uchun hisoblar bo'yicha qoldiqlardan foydalanaman. Bu erda operatsiyalarni ozgina test ma'lumotlari bilan to'ldiradigan va to'ldiradigan kod:

Set-ni yoqing; TSQL2012-dan foydalaning; Agar ob'ektlar ("DBB.TRANASRASRS", "U") null tomchisi dBUTranctionits; Stolni yaratish Dbo.Trrancactions (Acid Int Null emas - Tranid Int Null bo'lmasligi NULL BO'LMAYDI, - Val pulning ustuni NULL, - Qishloq paketining asosiy kaliti (aktid, tranid); Borish - bu dic.trancactions (ACTID, TRANID, VAL) qiymatlari (1, 1, 4.00), (1, 3, - 5.00), (1 , 4, 2.00), (1, 6, 1,00), (1, 7, -4.00), (1, 8, -1.00), (1, 9, -2.00) (1, 9, -2.00) ( 1, 10, --3.00), (2, 2, 1,00), (2, 3, - 0,00), (2, 5, -5.00) (2, 5, -5.00) ( 2, 6, 4,00), (2, 8, -4.00), (2, 9, -5.00), (2, 10, - 4,00), (3, 1, -3.00), (3, 2, 300), (3, 3, - 1,00), (3, 5, 4,00), (3, 6, -1.00), (3, 7, - 5.00), (3, 7, - 5.00), (3, 8, 300), (3, 9, - 5.00), (3, 10, - 8.00);

Har bir satr hisobvaraqda bank operatsiyasini anglatadi. Omonatlar v val ustunida ijobiy qiymat bilan amalga oshiriladi va mablag'larni olib tashlash - tranzakaning salbiy ahamiyati sifatida. Bizning vazifamiz har qanday vaqtda hisobdagi qoldiqni tranid ustunida buyurtma qilishda operatsiyalar to'plash orqali hisobni hisoblash va bu har bir hisob uchun alohida amalga oshirilishi kerak. Kerakli natija quyidagicha ko'rinishi kerak:

Ikkala echimni sinab ko'rish uchun sizga katta miqdordagi ma'lumotlar kerak. Buni bunday so'rov bilan amalga oshirish mumkin:

@Num_parktitsiyani int \u003d 1000 sifatida @Rows_per_Partatient deb e'lon qiling Kesma stol dbo.traning; NP.Stranctions-ni (Plank) qo'shing (Plank) NP.N, RPP.N ni tanlang (ABS (Newid (Newid (Newid (Newid (Newid (Nyutsum) * IRP sifatida DBB.GEGETNUMS dan (1, @num_parktsiyalar) dan IRP sifatida DBBetnum (1, @Rows_PART_PARTIT).

Siz kiritish ma'lumotlarini (hisoblar) va chiziqlar (bitimlar) bo'limida (bitimlar) o'zgartirishingiz mumkin.

Oyna xususiyatlariga asoslangan echim

Men birlashtirish summasining deraza oynasini ishlatadigan to'plamlar asosida men bir hikoyani boshlayman. Bu erda deraza ta'rifi juda aniq: siz ACTID oynasini ajratishingiz kerak, tranzidni va filtrni ekrandagi iplarni ekrandagi iplarni oqimga to'g'rilash uchun. Mana tegishli so'rov:

Db.tranctionsents-dan muvozanat sifatida aktid, tranid, val, summa, summa (val) ni tanlang (Val) ni tanlang

Ushbu kod nafaqat sodda va sodda, balki tezda amalga oshiriladi. Ushbu so'rov rejasi rasmda keltirilgan:

Stolda POC talablariga javob beradigan klasterli indeks mavjud va deraza funktsiyalaridan foydalanish uchun javob beradi. Xususan, indeks kaliti ro'yxati ajralish elementidir (aktidik), undan keyin buyurtma elementi (Tranid) ga asoslangan, shuningdek, buyurtmani qoplash uchun, shuningdek so'rovning boshqa barcha ustunlarini o'z ichiga oladi. Rejada ichki ehtiyojlar uchun chiziq raqamini hisoblash, so'ngra deraza blokini hisoblash orqali kiritilgan. POC indeksi mavjud bo'lganligi sababli, optimerer rejimga tartib qo'shish kerak emas. Bu juda samarali reja. Bundan tashqari, u chiziqli keng tarqalgan. Keyinchalik, men kontseptsiyani taqqoslash natijalarini ko'rsatganimda, ushbu usul eski echimlarga nisbatan qanchalik samarali samarali ekanligini ko'rasiz.

SQL Server 2012 investitsiya qilingan so'rovlar yoki ulanishlardan foydalangan. O'rnatilgan so'rovdan foydalanganda, o'sib borayotgan natijalar barcha qatorlarni tashqi chiziqdagi va tashqi chiziqdagi qiymatga teng bo'lgan barcha satrlarni filtrlash orqali hisoblab chiqiladi. Keyin agregatsiya filtrli qatorlarga qo'llaniladi. Mana tegishli so'rov:

Shunga o'xshash yondashuv aralashmalar yordamida amalga oshirilishi mumkin. Xuddi shu predikat ulanishda ulangan so'rovning qaerda bo'lganida ishlatiladi. Bunday holda, T1 sifatida belgilangan holatda, T1 instantsiyasida ko'rsatilgan misolda, siz 1 dan N gacha bo'lgan hisob-kitoblarni topasiz. T1 chizig'i, ular takrorlanadi, shuning uchun siz hozirgi bitim haqida ma'lumot olish va o'sish natijasini hisoblash uchun T1 va Valli xususiyatlariga komplektsiyalarni T2-ga nisbatan t2-ga yo'naltirish kerak. Tayyor so'rov quyidagicha ko'rinadi:

T1-da T1-da T1-da T1-ga qo'shilgan DBBRUTRANASTRASTRASES-dan CBBRUTRANASTRASTRASICE-ni tanlang<= T1.tranid GROUP BY T1.actid, T1.tranid, T1.val;

Quyidagi rasmda ikkala echimning rejalari ko'rsatilgan:

E'tibor bering, T1 instantsiyada ikkala holatda ham klasterli indeks amalga oshiriladi. Keyin, har bir qator uchun qidiruv operatsiyasi indeksning oxirgi sahifasida, indeksning oxirgi sahifasida, T2.TRANID-ga kam yoki teng bo'lgan barcha bitimlar mavjud. Satrni jamlash sodir bo'lgan joy rejalarda bir oz farq qiladi, ammo satrlar soni bir xil darajada farq qiladi.

Qancha chiziqni ko'rish uchun ma'lumotlar elementlari sonini hisobga olish kerak. P bo'limlari (hisoblar) sonini (hisoblar) va R bo'limdagi qatorlar soni bo'lishi kerak. Keyin stoldagi qatorlar soni taxminan P * R ga teng, agar biz bitimlar orqali teng hisob raqami tarqatiladi deb taxmin qilsak. Shunday qilib, yuqori qismida ko'rsatilgan nuqta p * r qatorlarini qamrab oladi. Ammo barchaning asosiysi iteratorda sodir bo'layotgan narsalarga qiziqamiz.

Har bir bo'limda, rejani o'qish uchun 1 + 2 + 2) / R + R * 2) / 2. Rejalarda ko'rib chiqilgan qatorlarning umumiy soni p * r + p. * (R + R2) / 2. Bu rejadagi operatsiyalar soni kvadratning ko'payishi bilan o'sasangiz, demak, bu qismning o'lchamini ko'paytirsangiz ishning 2 baravar ko'payadi. Bu yomon. Masalan, 100 qator 10 ming qatorga to'g'ri keladi va million qator millionga to'g'ri keladi va hk. Shunchaki, bu shunchaki ajratishning keskin pasayishiga olib keladi, chunki kvadratik funktsiya juda tez o'sadi. Bunday echimlar bir nechta bo'lim uchun bir necha o'nlab chiziqlarda qoniqarli ishlaydi, ammo ko'pi bilan emas.

Kursor echimlari

Kursor asosidagi echimlar "peshonada" amalga oshiriladi. Kursor so'rov asosida, aktid va tranid haqidagi ma'lumotlarni buyurtma asosida e'lon qilinadi. Shundan so'ng, kursor yozuvlarining iterativ o'tishi amalga oshiriladi. Yangi hisob topilsa, jihozni o'z ichiga olgan o'zgaruvchan qayta tiklanadi. Har bir dasturda yangi bitim summasi o'zgaruvchiga qo'shiladi, shundan so'ng satr jadval o'zgaruvchisiga joriy bitim to'g'risida ma'lumot bilan saqlanadi va o'sish natijasining hozirgi qiymatini keltiradi. ITERERATIV parchadan keyin, jadvalning natijasi qaytariladi. Tayyor qarorning kodi:

@Result stol sifatida e'lon qiladi (aktid int, Tranid int, VIL, VIL, pul mablag'lari); @Akt sifatida int, @tranid int, @tranid sifatida int, @val sifatida pul, @batance pul sifatida; Aktidiya, Tranid tomonidan ACTID, Tranid, valni tanlash uchun C kursorini DBBUTRANASTRASIDS-dan DBBITRANARASIDS-ni tanlang; C @akte, @Tranid, @val; @Pracacid \u003d @acid, @Balance \u003d 0; @@ fitch_status \u003d 0 @aktitilgan bo'lsa<> @Pvatactid-ni tanlang @Pracact \u003d @acid, @Balance \u003d 0; @Balance \u003d @valce + @val; @RECTUCT qiymatlarini (@TRANID, @val, @batance) ga qo'shing; CR @ActiD, @Tranid, @valdan keyingi keyingi fayllar; Oxiriga yaqin c; C taqsimoti; @RESECT-ni tanlang;

Kursordan foydalangan holda so'rov rejasi rasmda keltirilgan:

Ushbu reja juda keng tarqaldi, chunki indeksdagi ma'lumotlar faqat ma'lum bir tartibda ko'rib chiqiladi. Bundan tashqari, har bir qatorda kursordan bir qatorda bir xil xarajatlarni olishning har bir operatsiyasi. Agar siz G ga teng bo'lgan bitta kursor qatorini qayta ishlashda yaratilgan yukni olsangiz, ushbu eritmaning narxi P * R + P * R * R * g - bu bo'limlar soni va R Bo'limda qatorlar soni). Shunday qilib, agar f martada har bir bo'limda olib keladigan satrlar sonini ko'paytirsangiz, tizimdagi yuk p * r * p * f * f * g, ya'ni u chiziqcha o'sadi. Satrga qarab ishlov berish narxi yuqori, ammo ushbu echimlarning kvadrat squaliting tufayli ushbu echimlarga qaraganda, ushbu echimlarga qaraganda, bu echimlarga qaraganda, bu echimlarga qaraganda eritmalar va birikmalarga qaraganda yaxshiroq echimlarni namoyish etadi . Men ko'rsatgan holda namoyish etilishicha, kursor bilan echim tezroq ishlaydi, bu bo'lim uchun bir necha yuz donaga teng ishlaydi.

Kursor asosidagi echimlar umumiy ishlashiga qaramay, ulardan qochish kerak, chunki ular amalda emas.

CLR-ga asoslangan echimlar

Mumkin bo'lgan bitta eritma CLR (umumiy tilning ishlash vaqti) Aslida, kursordan foydalangan holda hal qilish shakllaridan biridir. Farqi shundaki, keyingi satrni va ijro etuvchi iteratsiyani olish uchun ko'plab resurslarni sarflaydigan T-SQL kursoridan foydalanishning o'rniga, I.Net SQDATRADER I.NET, bu juda tez ishlaydi. Ushbu parametrni tezroq qiladigan slimning xususiyatlaridan biri bu vaqtinchalik stolda paydo bo'ladigan satr kerak emas - natijalar to'g'ridan-to'g'ri qo'ng'iroq jarayoniga yuboriladi. Klr asosidagi echim mantig'i kursor va T-SQL yordamida echimlarning mantiqqa o'xshash. Bu erda saqlanadigan echim protsedurasini aniqlaydigan C # kod:

Tizimdan foydalanish; Tizimdan foydalanish. System.Data.SQLCRingdan foydalanish; System.Data.SQLTypes; Microsoft.SQLServer.serverdan foydalanish; Davlatning qisman sinfi saqlangan (jamoat statik hisobvarag'lari) (SQLENCONE CHLOCKOMDORE (yangi Sqlonnektsiya (yangi kllonnektsiya \u003d yangi kvloconnektsiya) ("Kontekstika "+" Aktid, tranid, "Aktexit," + "" + "" + "" + "Buyurtmadan" + "" + "buyurtma" + "" + "" + "" + "" + "" + "" + "" + "" + "" + "" + "" + "" + "buyurtma" + "" + "-ni tanlang. Sqlmetdatata ("Tranid", kvdbtype.int); lolds \u003d yangi SQLetsbyPe.Money); SqdbyPe.Money); SqdbyPe.Money); SqdbyPe.Money PAPE.SendResulsStart (Yozish); ulash.open (); SqdatReader Reader \u003d 0; Sqlmont32 PRVALDER \u003d 0 (o'quvchi.read32 aktid \u003d o'quvchi.getqlint32 (0) ; Kvlemoney Val \u003d Reader.getsqlmoney (2); agar (ACTID \u003d\u003d val;) ■ (balans + val;) practiced \u003d aktid; reg ord.Setsqlint32 (0, o'quvchi.getsqlint32 (0)); yozuv.setsqlint32 (1, o'quvchi.getsqlint32 (1)); Yozuv.setsqlmoney (2, val); Yozuv.setsqlmoney (3, muvozanat); Kvlcontext.pipe.sendresrou (yozuv); ) Sqlcontext.pipe.SendResultsend (); )))

SQL SQL-serverda ushbu barcha protsedurani amalga oshirish imkoniyatiga ega bo'lish uchun siz avval CHQLAL2012 Ma'lumotlar bazasida hisob-kitoblar va joylashtirish uchun montaj nomini yaratishingiz kerak. Agar siz SQL serverda qurilishlarni joylashtirish bilan tanish bo'lmagan bo'lsangiz, "Saqlangan protseduralar" maqolasida "Saqlangan protseduralar va Clr Atrof-muhit" bo'limini o'qishingiz mumkin.

Agar siz hisob-kitob faylini yig'ish deb nomlagan bo'lsangiz va yig'ish faylining yo'li "C: \\ Loyihalar \\ Bank hisob-kitoblari \\ Ingug \\ Ko'rsatmalarBalles.dll", shuningdek, Assambleyani ma'lumotlar bazasiga yuklab oling va saqlangan protsedurani quyidagicha ro'yxatdan o'ting:

"C: \\ Loyihalar \\ hisobullilliyalar \\ bin \\ burilishBallenciols.dll" dan; DBU. Tashqi nomi hisobultkazmalar.stededProcemates.AcountBalantlar kabi tartib-qoidalarni yarating;

Jadvalni yig'ish va ularni ro'yxatdan o'tkazgandan so'ng, uni quyidagicha bajarishingiz mumkin:

DBU.ACTBALITLARINING;

Aytganimdek, SQDATRADER - bu kursorning yana bir shakli, ammo ushbu versiyada o'qish satrlarining narxi T-SQL-da an'anaviy kursordan foydalanganda ancha kam. Shuningdek, v.net iteratsiyalari T-SQL-ga qaraganda tezroq amalga oshiriladi. Shunday qilib, Clr asosidagi echimlar ham kengroq chiziqli. Sinov shuni ko'rsatadiki, ushbu eritmaning ishlashi, sektsiyalar va ulanishlar soni 15 dan oshganida, skiues va ulanishlardan foydalangan holda echimlarning ishlashidan yuqori bo'ladi.

Tugatgandan so'ng, quyidagi tozalash kodini bajarishingiz kerak:

DBO. Yig'ish hisobvarag'ining yig'indisi;

ITeratsiyalar

Shu paytgacha men to'plamlar asosida iTererativ echimlar va echimlarni ko'rsatdim. Quyidagi echim, Iererativ gibridi bo'lgan va yondashuvlar to'plamiga asoslangan holda, o'rnatilgan iteratsiyalarga asoslangan. G'oya satrlarni dastlabki jadvaldan oldindan nusxalash (bizning holatda, bu bank hisobvaraqlari) vaqtinchalik stolda vaqtinchalik stolda, powumber funktsiyasidan foydalanib hisoblab chiqiladi. Satr raqamlari aktid tomonidan ajratiladi va Tranid tomonidan buyuriladi, shuning uchun har bir bankdagi birinchi raqam 1-raqam, ikkinchi bitim - 2 va boshqalar. Keyin vaqtinchalik stolda kalitlar ro'yxati (Ropeum, Actid) bo'lgan klasterli indeksni yaratadi. Rezursiv CTE ifodai barcha hisoblarni qayta ishlash uchun maxsus yaratilgan tsikl ishlatiladi yoki maxsus yaratilgan tsikl. Keyin o'sish natijasi oldingi satr bilan bog'liq qiymat bilan joriy chiziqqa mos keladigan qiymatni sarhisob qilish bilan hisoblanadi. Ushbu mantiqiy CTE-dan foydalanib:

Actiid, Tranid, VL, Roc_Number () ni Tranid tomonidan bo'linishi bo'yicha qisman DBBRANASTRASTRS-dan #TRSITRASRASRASS-ga ko'tarishni tanlang; #Traning'siyalari (Rowum, Actid) da noyob klasterli indeksli ind_ruhum_actidni yarating; C kabi (1-sonli Sountum, Actsid, Tranid, Roundencial Sumqy sifatida # Sumqy sifatida # Sumqy sifatida Sumqy sifatida # SPV.TRANID, CR.Val, PRV.Sumqin + CR.Val CR.VALdan PRV-ga qo'shiling. Cur.Rawum \u003d PRV.Acy \u003d PRV.AceMid) C vacty-dan (MaxRecurskari 0); #Tranishlar jadvali;

Va bu aniq tsikl yordamida amalga oshirish:

Db.tranctions-dan #TRSRANASTRASSE & Sumqin sifatida (Valning burchagi bo'yicha qism) Roequm, aktid tartibi, CRBRINACT (VILcha) sifatida ajratish; #Traning'siyalari (Rowum, Actid) da noyob klasterli indeksli ind_ruhum_actidni yarating; @Roundumni int; @Rowum \u003d 1; 1 \u003d 1-ni o'rnatishni boshlang @rowum \u003d @rowum + 1; Yangilash SIT SEMQTY \u003d PRV.Sumqy +Val #RancaRactions-dan #Raw.rowum va PRV.R.Rowum \u003d @Roundum-ga qo'shiling - 1 va CRV.AceDid; Agar @@ Rupcount \u003d 0 tanaffus; # Condid, Tranid, VL, Sumqinni #TRSRANARSES-dan tanlang; #Tranishlar jadvali;

Ushbu echimda bir nechta qatorlar qatorida qator qatorlar mavjud bo'lganda yaxshi ishlashni ta'minlaydi. Keyin iteratsiyalar kichikroq va asosiy ish bir qator raqam bilan bog'liq bo'lgan satrlar bilan bog'langan qatorlar bilan bog'laydigan to'plamlar tomonidan amalga oshiriladi.

O'zgaruvchilar bilan ko'p chiziqli yangilanish

Ushbu nuqtai nazardan ko'rinib turibdiki, voqea natijalarini hisoblash uchun qabul qilish to'g'ri natijaga olib keladi. Ushbu bo'limda tasvirlangan usul noaniq, chunki u kuzatilgan va tizimning hujjatlashtirilgan xatti-harakatlariga asoslangan, qo'shimcha ravishda qarindoshlarning tamoyillariga zid keladi. Uning yuqori jozibadorligi katta ish bilan bog'liq.

Ushbu usulda parametrlar bilan yangilanish qo'llanmasi ishlatiladi. Yanglash bo'yicha ko'rsatmalar ustun qiymatiga asoslangan ifoda o'zgaruvchini belgilash, shuningdek o'zgaruvchan bo'lgan ustunlarda qiymatlarni belgilashi mumkin. Yechim tranzaktsiyalar nomini aktid, tranid, val va balans va kalitlar ro'yxati va kalit, tranid) bilan vaqtincha jadval yaratishdan boshlanadi. Vaqt jadvali, keyinchalik bitimlar manbai ma'lumotlar bazasidan barcha satrlar bilan to'ldiriladi va 0,00 ning qiymati barcha qatorlarning qoldiqlariga kiritiladi. So'ngra vaqt jadvallari bilan bog'liq bo'lgan o'zgaruvchilar bilan yangilanish bo'yicha ko'rsatma natijalar ortib borayotgan natijalarni hisoblash va qoldiq ustunda hisoblangan qiymatni kiritish uchun chaqiriladi.

@PrevcAcunt va @Prbalement o'zgaruvchilar ishlatiladi va qoldiq ustunidagi qiymat quyidagi iborada keltirilgan:

@Prevballement \u003d balans \u003d ACID \u003d @Preveccace Country-da @PrRebalce + Valning Val oxirida

Agar oldingi va oldingi qayd yozuvlari aniqlanmasa, ishning ifodasi amalga oshirilmasa, balans ustunidagi oldingi va joriy qiymatlar miqdorini qaytaradi. Agar hisob-kitob identifikatorlari boshqacha bo'lsa, joriy bitimning miqdori qaytariladi. Keyinchalik, bu holatning natijasi balans ustuniga kiritilgan va @PrRBALLECT o'zgaruvchisiga tayinlangan. O'zgaruvchining alohida ifodasida, joriy hisob qaydnomasi identifikatoriga taqdim etiladi.

Yangilanish ifodaidan so'ng, yechim vaqt jadvalidan qatorlarni anglatadi va oxirgisini o'chiradi. Tayyor qarorning kodi:

#TRSRANASTRASTRS (ACTIDR IN, TRANID IN, VIL, pul mablag'lari, pul mablag'lari) yaratish; #Trancings (Acid, Tranid) da klasterli indeks ID_ACTICID_TRANID-ni yarating; Oktid, Tranid, Tranid tomonidan DBBRANID, Tranidlar tartibidan ACTID, Tranid, VL, 0.00 ni tanlang; @Prevccccaunt Int, @PrRBALALNI PUL sifatida e'lon qiling; @Prevballement \u003d CARID \u003d @PrevRaccounte-ning yangilanishi (indeks (1), planshogi) variantini (MakdDOp 1) yoqilgan bo'lsa; #Trancings-dan * ni tanlang; #Tranishlar jadvali;

Ushbu echimning rejasi quyidagi raqamda keltirilgan. Birinchi qism boshqa joylashtirilgan, ikkinchis yangilanishi va uchinchi - -

Ushbu qarorda, yangilanishning bajarilishini optimallashtirish har doim amalga oshiriladi va echim bunga to'sqinlik qiladigan holatlarning oldini olish uchun bir qator ko'rsatmalarni taqdim etadi, masalan, parallelizmni oldini olish uchun bir qator ko'rsatmalar mavjud. Muammo shundaki, Rasmiy kafolat mavjud emaski, optimizator har doim klasterli indeks tartibiga qarab turadi. Kodeksning mantiqiy to'g'riligini ta'minlash kerak bo'lganda jismoniy hisoblash xususiyatlariga ishonish mumkin emas, agar aniq bo'lsa, bu xatti-harakatni kafolatlashi mumkin emas. Ushbu xatti-harakatning mantiqiy xususiyatlari yo'q, bu xatti-harakatlar kafolatlanishi mumkin. Tabiiyki tanlov, foydalanish yoki undan foydalanmaslik, vijdoningizga butunlay yotadi. Ishonchim komilki, bu minglab marta tekshirib ko'rsangiz ham, "hamma narsa kerak bo'lsa, hamma narsa ishlayotganga o'xshaydi" deb o'ylayman.

Yaxshiyamki, SQL Server 2012 yilda bu tanlov deyarli keraksiz bo'ladi. Deraza funktsiyalaridan foydalanib, juda samarali echim bo'lsa, yig'ish boshqa echimlar haqida o'ylashi shart emas.

Ishlash o'lchovi

Men turli xil texnikaning ishlashini o'lchash va taqqoslashda olib bordim. Natijalar Quyidagi rasmlarda keltirilgan:

Ilova qilingan so'rov yoki aralashmadan foydalanish usuli men uchun yana bir o'lchovdan foydalanishim kerak bo'lgan narsadan ancha sekinroq ekanligi sababli, natijalarni ikki grafikka sindirdim. Qanday bo'lmasin, echimlarning aksariyati bo'lim hajmidagi ish hajmining chiziqli qaramligini namoyish etadi va faqat joylashtirilgan so'rov yoki aralashmaga asoslangan echim kvadrat bog'liqlik. Shuningdek, yangi echim yig'ishning deraza funktsiyasi asosida qanchalik samarali samarali samarali bo'ladi. O'zgaruvchilar bilan yangilanish asosida echim ham juda tez, ammo siz allaqachon tasvirlangan sabablarga ko'ra, men undan foydalanishni maslahat bermayman. Cls yechimi ham juda tez, ammo bu barcha ushbu kodni yozishi kerak .Net va ma'lumotlar bazasida yig'ishni joylashtirish kerak. To'plamlarga qanchalik qarab bo'lishidan qat'i nazar, derazalarning agregatlari yordamida echim eng afzal ko'radi.

Xatolik yuzaga kelganda barcha matematik funktsiyalar.

Yuariy minus. Argum belgisini o'zgartiradi: MySQL\u003e Tanlang - 2; -\u003e -2 Agar ushbu operator kattaligi turida ishlatilsa, qaytish qiymati kattakon turdagi katta turiga ega bo'lishi kerakligini hisobga olish kerak! Bu shuni anglatadiki, operatorni sonlar uchun ishlatishni oldini olish mumkin, bu -2 ^ 63 bo'lishi mumkin! ABS (x) X: MySQL-ni mutlaq qiymatni qaytaradi: MySQL\u003e ABS (2); -\u003e 2 MySQL\u003e ABR (-32); -\u003e 32 Ushbu xususiyat katta hajmdagi katakli qiymatlar uchun ishonchli tarzda ishlatilishi mumkin. Belgisi (x) Nol yoki musbat degan munozakni -1, 0 yoki 1 shaklida argument belgisini qaytaradi: MySQL\u003e Belgini (-32) -ni tanlang; -\u003e -1 Mysql\u003e Belgini tanlang (0); -\u003e 0 MySQL\u003e Belgini (234) tanlang; -\u003e 1 MOD (N, M)% qiymati modul bilan (% c). N-ni m istalashdan saqlaydigan qoldiqni qaytaradi: MySQL\u003e Mod (234, 10); -\u003e 4 MySQL\u003e 253% 7; -\u003e 1 MySQL\u003e MOD (29,9); -\u003e 2 Ushbu xususiyat katta harflar uchun ishonchli foydalanilishi mumkin. Pol (x) X: mysql\u003e polni tanlash uchun (1.23) dan oshmaydigan eng katta butun sonni qaytaradi; -\u003e 1 MySQL\u003e Polni tanlang (-1.23); -\u003e -2 Qaytarilgan qiymat kattaroq ko'rinishga aylanishini yodda tutish kerak! Shife (x) eng kam sonni qaytaradi, eng kam emas, mysql\u003e Shife-ni tanlang (1.23); -\u003e 2 MySQL\u003e Shiftni tanlang (-1.23); - 1 Shuni yodda tutish kerakki, qaytarilgan qiymat kattalashmaga aylantirilmoqda! Dumaloq (x) X argumentni qaytaradi, eng yaqin butun songa yaxlitlanadi: MySQL\u003e Davra (-1.23); -\u003e -1 Mysql\u003e Davra (-1.58) ni tanlang; -\u003e -2 MysQL\u003e Seight (1.58); -\u003e Ikki butun butun butun son orasidagi tortishuv qiymati C kutubxonaning o'ziga xos amalga oshirilishiga bog'liq bo'lganda, yaxlit () ning funktsiyasining xatti-harakatlarining xatti-harakati C kutubxonaning o'ziga xos amalga oshirilishiga bog'liqligini yodda tutish kerak. Yugurish amalga oshirilishi mumkin: eng yaqin tomonga Hatto raqam, har doim yaqinroq, har doim eng yaqin kichikroq, har doim nolga yo'naltirilgan. Shunday qilib, yaxlitlash har doim bir yo'nalishda yuz berdi, buning o'rniga kesilgan kesish () yoki pol () kabi yaxshi funktsiyalardan foydalanish kerak. Dumal (x, d) x o'nlik belgilari bo'lgan raqamga aylantirilgan argumentni qaytaradi. Agar D 0 bo'lsa, natijada kasr belgisi yoki kasr qismisiz taqdim etiladi: MySQL\u003e Davra tanlang (1.298, 1); -\u003e 1.3 MySQL\u003e Select (1.298, 0); -\u003e 1 Exc (x) qiymatni qaytaradi (MySQL\u003e MySQL-ni tanlang (2); -\u003e 7.389056 MySQL\u003e EXP (-2); -\u003e 0.135335 Jurnal (X) X ning tabiiy logaritmini qaytaradi: MySQL\u003e Kirish Kirish (2) ni tanlang; -\u003e 0. 693147 MySQL\u003e Kirish (-2) ni tanlang; - XNOGITMS B logarifms b logarifm-larini uchun xultifmni olish uchun siz jurnal (X) / log (b) formuladan foydalanishingiz kerak. Log10 (x) X-ning o'nlik logaritmini ushlab turadi: MySQL\u003e Log10 (2) -ni tanlang; -\u003e 0.301030 MySQL\u003e Kirish Lentyabr (100) ni tanlang; -\u003e 2.000000 mysql\u003e Log10 (-100) ni tanlang; -\u003e Null Pow (x, y) Y: MySQL darajasiga o'rnatilgan x argumentining qiymatini qaytaradi (mysql\u003e ni tanlang (2.2); -\u003e 4.000000 mysql\u003e Tanlash (2, -2); -\u003e 0.250000 SQRT (x) X ning salbiy bo'lmagan kvadrat ildizini qaytaradi: MySQL\u003e SQRT (4) ni tanlang; -\u003e 2.000000 mysql\u003e SQRT (20) -ni tanlang; -\u003e 4.472136 pi () "PI" raqamining qiymatini qaytaradi. Standart 5 o'nlik reja tuzadi, ammo MySQL-da ichki hisob-kitoblar bilan "pi" raqamini ifodalash, to'liq ovozli aniqlik ishlatiladi. MySQL\u003e PI (); -\u003e 3.141593 MySQL\u003e PI () + 0.00000000000000-ni tanlang; - 3.141592653589793116 Cos (x) x raqamining kosinasini qaytaradi, u erda x rentgenlar: MySQL\u003e CO (PI (PI)); -\u003e -1.000000 Gunt (x) X raqamining Sinusini qaytaradi, u erda x Radiana-ni o'rnatadi: mysql\u003e Gunoh (Pi ()); -\u003e 0.000000 tanni (x) x raqamini qaytaradi, u erda x rentgenlar: MySQL\u003e Tan (Pi () + 1); -\u003e 1.557408 ACOS (X) X, I.E. Arkosine raqamini qaytaradi Kosine miqdori x. Agar x 1 dan 1 gacha bo'lgan oralig'ida bo'lmasa, nullni qaytaradi: mysql\u003e Acos (1); -\u003e 0.000000 MySQL\u003e Acos-ni tanlang (1.0001); -\u003e Null MySQL\u003e Acos-ni tanlang (0); -\u003e 1.570796 ASIN (X) Arxinus raqamini X, I.Ee-ni qaytaradi X ning kattaligi x. Agar x 1 dan 1 gacha bo'lgan oralig'ida bo'lmasa, nullni qaytaradi: mysql\u003e Asin-ni tanlang (0,2); -\u003e 0.201358 mysql\u003e ASIN ("FOO"); -\u003e 0.000000 Ostan (x) Arctannx raqamini x, i.e-ni qaytaradi Qaysi qiymat X: MySQL\u003e Oranda (2); - 1.107149 MySQL\u003e Overl (-2); -\u003e -1.107149 Atan2 (y, x) ATAN2 (y, x) x va Y o'zgaruvchisining Arctannxni qaytaradi. Hisob-kitob archangent y / x hisob-kitobi bilan bir xil tarzda amalga oshiriladi, ammo natijaning kvadrantini aniqlash uchun ishlatiladi: MySQL\u003e Ovozni tanlang (-2.2); -\u003e -0.785398 MySQL\u003e Otan2 (Pi (), 0); -\u003e 1.570796 Cot (x) X: MySQL\u003e KOT (12) kot-ni tanlang; -\u003e -1.57267341 MySQL\u003e KOT (0); -\u003e Nel Rand () rand (n) 0 dan 1,0 gacha bo'lgan tasodifiy suzuvchi nuqta qiymatini qaytaradi. Agar butun son n argumentida ko'rsatilgan bo'lsa, u ushbu qiymatning boshlang'ich qiymati sifatida ishlatiladi: mysql\u003e RAND (); -\u003e 0. 9233482386203 MySQL\u003e RAND (20); -\u003e 0.15888861251047 MySQL\u003e RAND (20); -\u003e 0.158888261211047 MySQL\u003e RAND (); -\u003e 0.63553050033332 MySQL\u003e RAND (); -\u003e 0.701004694486881 Buyurtma turida siz Rand () qiymatlari bilan ustundan foydalanmaslik kerak, chunki bu ustunda buyurtma berish tartibda bir nechta hisob-kitoblarga olib kelishi kerak. MySQL 3.23 versiyasida quyidagi Operatorni bajaring: * Tasvir buyurtmasini Rand () -ni tanlang: C \u003d B-B jadvalidan va T

  • Agar qaytarilgan qiymat butun sonli kontekstda (butun sonlar) yoki barcha dalillar butun son bo'lib, butun sonlar sifatida taqqoslanadi.
  • Agar qaytarilgan qiymat haqiqiy raqamlar (haqiqiy) kontekstida ishlatilsa yoki barcha dalillar haqiqiy raqamlar bo'lsa, unda ular haqiqiy turdagi raqam sifatida taqqoslanadi.
  • Agar biron bir dalillardan biri reestrga bog'liq bo'lgan satr bo'lsa, unda ma'lumotlar argumenti registr bilan taqqoslanadi.
  • Boshqa hollarda, dalillar reestrdan mustaqil chiziqlar sifatida taqqoslanadi. MySQL\u003e Kamtar (2.0); -\u003e 0 MySQL\u003e Kamtar (34.0.3.0,767,0); -\u003e 3.0 MySQL\u003e Kamtar ("B", "a", "c"); -\u003e AMSQL versiyalarida 3.22.5 ga, siz kamida o'rniga min () foydalanishingiz mumkin. Eng buyuk (x, y, ...) eng yuqori (maksimal qiymatga ega) argumentni qaytaradi. Dalillarni taqqoslash kamida bir xil qoidalarga muvofiq: Mysql\u003e Eng katta (2.0); -\u003e 2 MySQL\u003e Eng katta (34.0.3.0,767,0); -\u003e 767.0 MysQL\u003e Eng katta ("B", "a", "c" ni tanlang; -\u003e MySQL versiyalarida "C" 3.22.5 ga, siz eng katta o'rniga max () foydalanishingiz mumkin. Daraja (x) RRASS tomonidan darajalarga aylantirilgan argumentni qaytaradi: MySQL\u003e Sinovlar (pi ()); -\u003e 180.000000 Radiangi (x) r argumentni qaytaradi, rentgenlar uchun aylantiriladi: mysql\u003e ni Radianglar (90) -\u003e 1.570796 kesish (x, d) x raqamini d nigi o'nlik belgilariga qaytaradi. Agar D 0 bo'lsa, natijada kasr belgisi yoki kasr qismisiz taqdim etiladi: MySQL\u003e Trifatani tanlang (1.223.1); -\u003e 1.2 MySQL\u003e kesish-ni tanlang (1.999.1); -\u003e 1.9 MySQL\u003e kesish-ni tanlang (1.999.0); - 1 Shuni yodda tutish kerakki, odatda kompyuterlarning o'nlik raqamlari soniya emas, balki suzuvchi o'nlik belgisi (ikki tomonlama) bilan ikki aniqlikdagi aniqlangan. Shuning uchun, ba'zida natija adashtirishi mumkin, chunki quyidagi misolda: mysql\u003e Trunkate (10.28 * 100.0); -\u003e 1027 Bu sodir bo'ladi, chunki 10.28 aslida 10,2799999999999ga o'xshash narsa sifatida saqlanadi.
  • Ushbu maqola omborxonalarda qoldiqlarni hisoblash uchun SQL vazifalarini hisob-kitob qilish uchun tranka to'lovlarini optimallashtirishni ta'minlaydi. Amaliyot: Jadvallarning va vakolatli vakolatxonalar ishtirokida ishtirok etish.

    Muammoni shakllantirish

    Vazifa SQL Server-2014 nashrida hal qilinishi kerak (X64). Kompaniya ko'plab omborlarga ega. Har bir omborda har kuni bir necha ming marta jo'natish va qabul qilish. Omborga etib borish / iste'mol qilishda tovarlarning harakatlari jadvali mavjud. Amalga oshirish kerak:

    Tanlangan sana va vaqt ichida (bir soatgacha) har bir mahsulot uchun barcha / har qanday omborxonalarda hisobni hisoblash. Tahlil uchun siz tanlangan sanalar oralig'ida, barcha omborlar va mahsulotlar, ushbu manba jadvali va qo'shimcha hisoblangan ustunni - pozitsiyaning holatida qoldiq.

    Ushbu hisob-kitoblar jadvalda har xil sana oralig'ida bajarilishi va arzon vaqtlarda ishlashi kerak deb taxmin qilinadi. Ular. Agar siz oxirgi soat yoki kun davomida qoldiqlar bilan stolni olib qo'yishingiz kerak bo'lsa, ijro vaqti iloji boricha tezroq bo'lishi kerak, shuningdek, oxirgi 3 yil davomida, keyingi 3 yil davomida tahliliy ravishda yuklab olish uchun. Ma'lumotlar bazasi.

    Texnik ma'lumotlar. Stolning o'zi:

    Stolni yarating DBB.Turnover (ID AD SHDUFICRININED (ID AD SHDETRIVNOLN, NULL, NULL EMAS, NULL EMAS NOLD (-1.1)). Raqamli raqamli ombordan (20,2) nolga teng emas, pul nolga teng emas)

    DT - omborni olish muddati / hisoblash sanasi.
    Mahsulotni ishlab chiqarish
    Storletid - omborxona
    Ishlash - 2 qadriyatlar kelishi yoki iste'mol qilish
    Miqdor - omborda mahsulot miqdori. Agar mahsulot bo'laklarda bo'lmasa, u haqiqiy bo'lishi mumkin, ammo, masalan, kilogrammda.
    Narx - mahsulot partiyasi narxi.

    Tadqiqot vazifasi

    Tugallangan jadval yarating. Meni men bilan birga sinab ko'rishingiz va hosil bo'lgan natijalaringizni tomosha qilish uchun men Db.Turhifhover stolini skript bilan yaratishni va to'ldirishni taklif qilaman:

    Agar ob'ekt_id ("DBB.TURNAN", "U") null tomchisi dB.turner emas; Ba'zan boring (1 II II II IDBUM ID raqamini tanlang)< 10*365*24*60 -- 10 лет * 365 дней * 24 часа * 60 минут = столько минут в 10 лет) , storehouse as (select 1 id union all select id+1 from storehouse where id < 100 -- количество складов) select identity(int,1,1) id, dateadd(minute, t.id, convert(datetime,"20060101",120)) dt, 1+abs(convert(int,convert(binary(4),newid()))%1000) ProductID, -- 1000 - количество разных продуктов s.id StorehouseID, case when abs(convert(int,convert(binary(4),newid()))%3) in (0,1) then 1 else -1 end Operation, -- какой то приход и расход, из случайных сделаем из 3х вариантов 2 приход 1 расход 1+abs(convert(int,convert(binary(4),newid()))%100) Quantity into dbo.Turnover from times t cross join storehouse s option(maxrecursion 0); go --- 15 min alter table dbo.Turnover alter column id int not null go alter table dbo.Turnover add constraint pk_turnover primary key (id) with(data_compression=page) go -- 6 min
    Menda kompyuterda SSD diski bor, taxminan 22 daqiqa va stolning o'lchami qattiq diskda taxminan 8GB ni qabul qildi. Jadvalni yaratish va to'ldirish uchun vaqtni kamaytirish uchun siz yillar sonini va omborlar sonini kamaytirishingiz mumkin. Ammo men so'rov rejasini baholash uchun biron bir yaxshi hajmni, kamida 1-2 gigabaytni baholashni maslahat beraman.

    Bir soatgacha guruhlangan ma'lumotlar

    Bundan tashqari, vaqtni o'rganish davrida biz bir soatlik mahsulotni tashkil etishimiz kerak, bu bizning vazifamizni shakllantirishda bir soat (bir daqiqaga, 15 daqiqaga, kungacha, kungacha, bu millisekundlar uchun aniq. kimdir hisobotga muhtoj bo'lishi uchun). Sessiyada taqqoslash uchun (Oyna) biz strater statistik vaqtini bajarishda biz so'rovimizni bajaradigan joyni bajaramiz; Keyin biz so'rovlarni o'zlari bajaramiz va so'rov rejasini ko'rib chiqamiz:

    DT dan yuqori bo'lgan eng yaxshi (1000) konvert (Datar (13), DT, 120) + "Varar (13), 120) DB (foydalanish * miqdorini) ni tanlang. .Tinder Group (Datame, o'zgartiring (4), DT, 120) + "Varra, 120) +": 00 ", 120), Produced, omborxona

    So'rov narxi - 12406
    (Qatorlar qayta ishlangan: 1000)
    SQL Serverni ochish soatlari:
    Vaqt CPU \u003d 2096594 ms, vaqt sarflangan \u003d 321797 ms.

    Agar biz natijada biz bizning sonimizning o'sishi vujudga keladi, bu bizning sonimizning o'sishi vujudga keladigan muvozanat, so'rov va so'rov rejasi quyidagicha bo'ladi:

    TOP (1000) konvert (Datetime, Convert (13), DT, 120) + "MARTAR (14), 120), summani, summa, summa, summani tanlang. (Sumhasi (jarayoni * miqdorini) (Datar (Soat nomi (13), DTH 120) + konvertatsiya orqali (00) (00) (00) (00) ( Datetime, konvertatsiya (Varra (13), DT, 120) + ": 00", 120), 120), Produced, Do'laxid


    So'rov narxi - 19329
    (Qatorlar qayta ishlangan: 1000)
    SQL Serverni ochish soatlari:
    Vaqt CPU \u003d 2413155 ms, vaqtni sarfladi \u003d 344631 ms.

    Guruhlarni optimallashtirish

    Bu erda juda oddiy. Talabning o'zi o'sib borayotgan natijasiz, ishlab chiqariladigan vakillik (indeks ko'rinishi) bilan optimallashtirilishi mumkin. Muvaffaqiyatli ko'rinishni qurish uchun, bu NOLL qiymatiga ega bo'lmasligi kerak (foydalanish * miqdorini) yoki har bir soha ISNULL / Billcellni ifoda etmaymiz. Men ishlab chiqariladigan vakolatxonani yaratishni taklif qilaman.

    DTRABBABDING (DATART, CUTRAR (13), DTH 120) + DT, 120) DT, DTHaxhid, sumkagacha (ISNULD)-ni tanlang. * Miqdori, 0)) Db.thifhifurover guruhidan (Datch), DTARTRINT guruhidan (Datch), DTH 120) + "Varra 120) +" Varra 120) + "Varra 120) +" Varra 120) + "Varar (00), 120", Do'laxon ekish orqali
    Va unga klaster indeksini yarating. Indeksda biz guruhlarni guruhlashda ko'rsatamiz (masalan, ancha ko'p buyurtma muhim emas, barcha guruhli maydonlar indeksda bo'lganligi va ortib borayotgan natijasi (buyurtma juda muhimdir) - Bo'limda nima deyish mumkin?

    Db.Turnororururda (Sathressid, Prodcressiv, DT) bilan noyob klasterli indeksini yarating (ma'lumotlar_compressionpressiya \u003d sahifasi) - 19 min

    Endi klaster indeksini qurgandan so'ng, biz hisobni jamlashni hisobga olgan holda, hisobni o'zgartirish orqali qayta bajaramiz:

    TOP (1000) konvertatsiya (Datetime, aylantirish, DTRAR (13), DT, 120) + "MARTAR (13), 120) ni bir soatlik hunarmand, sumka, summani (ISNUL)-ni tanlang. ) Db.thifurnover guruhidan (Datar (2 (2), DT, 120) + "Varar (1), 120), 120), TOPERTID (Datare, o'zgartiring) ), Dt, 120) + ": 00", 120) DT, sumh (ISNULD, 0) miqdorida, sumh (ISNULD (ISNULT (ISNULT), sumka, sumka, sumka, summa (ISNUL) , 0)) tugashi) (Varra (13), dt, 120) + ": 00", 120), 120), Produced, Storletid

    So'rov rejalari:

    0.008 narxi.

    0,01 narxi

    SQL Serverni ochish soatlari:
    Vaqt cp \u003d 31 ms, sarflangan vaqt \u003d 116 ms.
    (Qatorlar qayta ishlangan: 1000)
    SQL Serverni ochish soatlari:
    Vaqt cp \u003d 0 ms, sarflangan vaqt \u003d 151 ms.

    Umuman olganda, biz indekslangan ko'rinishga ega ekanligini ko'ramiz, so'rov jadvallarni guruhlash ma'lumotlarini, ammo hamma narsa allaqachon guruhlangan klaster indekslarini tekshiradi. Va shunga ko'ra, bajarilish vaqti 321797 millisekunddan 116 ms gacha pasaydi., I.00 2774 marta.

    Tanlangan oralig'ida biz stol (ko'rinishi) va uning qismi biz uchun butun stol (ko'rinishi) va uning qismi bo'lmaganligimiz uchun optimallashtirishni tugatish mumkin edi.

    Oraliq balans

    Natijada, biz tezda quyidagi so'rovni amalga oshirishimiz kerak:

    Sewformate YMD-ni o'rnating; Deklaratsiya @start DateTime \u003d "2015-01-02", @FINISH DATTIME \u003d "2015-01-03" (dt, stustid, summa, sumka, yuk tashish tartibi) Dt) DBB.Turnhour-dan (NOEXPDAND) balansi (NOEXPDAND)<= @finish) as tmp where dt >\u003d @start


    Reja narxi \u003d 3103. Agar u noto'g'ri vakillik qilmasa, nima bo'lishini tasavvur qiling, u stolning o'zida o'tdi.

    Sana bo'yicha bir soat davomida aylanib o'tgan kundan boshlab har bir mahsulotda amalga oshiriladigan taqdim etilgan taqdimot va balansni ishlab chiqarish. Hisobni hisoblash uchun - bu oxirgi sanadan oldin (@finish) dan oldin (@FINISH) va allaqachon birlashtirilgan qisqartirishdan oldin, boshlang'ich parametrdan keyin ma'lumotlarni kesib tashlang .

    Bu shubhasiz oraliq hisoblangan muvozanatlarga yordam beradi. Masalan, har oyda yoki har yakshanba kuni 1 sonida. Bunday qoldiqlarga ega bo'lish - ilgari hisoblangan balanslarni umumlashtirishingiz va balansni boshidan emas, balki oxirgi hisoblangan kundan boshlab hisoblashingiz kerak. Tajribalar va taqqoslash uchun biz sana bo'yicha qo'shimcha emas, balki qo'shimcha klaster indeksini quramiz:

    Ix_dt indeksini DBB.Turnhour / (ma'lumotlar) bilan (ma'lumotlar_compressionpressiya \u003d sahifa) bilan qo'shing; --7 min va bizning so'rovimiz turi bo'ladi: Seadormat YMD; deklaratsiya @start DateTime \u003d "2015-01-02", "2015-01-03" deb e'lon qiling @Start_month ma'lumotlar sexati \u003d "Varchar (9), @ Boshlanish, 120) +" 1 ", 120) dan tanlang (DT, Staxtaxid, Raqamli, miqdorini (miqdorini) DB @SHINTHOD va @finlishi-ni DT-ni boshqarish uchun DTH, u erda DT ning @/month va @finie-ning qismida bo'linadi) \u003e
    Umuman olganda, barcha ta'sirlangan barcha maydonlarni to'liq qamrab olgan sana bo'yicha ushbu so'rov bizning indeksimiz klasterini tanlaydi va skanerlash. Va keyingi saralash bilan sana bo'yicha qidirmang. Men quyidagi 2 ta so'rovni bajarishni taklif qilaman va qilgan ishlarimizni taqqoslashni taklif qilaman, so'ngra hali yaxshiroq ekanligini tahlil qilaman:

    Sewformate YMD-ni o'rnating; deklaratsiya @start DateTime \u003d "2015-01-02", "2015-01-03" deb e'lon qiling @Start_month ma'lumotlar sexati \u003d "Varchar (9), @ Boshlanish, 120) +" 1 ", 120) dan tanlang (DT, Staxtaxid, Raqamli, miqdorini (miqdorini) DB @SHINTHOD va @finlishi-ni DT-ni boshqarish uchun DTH, u erda DT ning @/month va @finie-ning qismida bo'linadi) \u003e \u003d @Start buyurtmasi DTBEHID, DT ni tanlang (DTHELDED, MARTIDENDENT, RAFTID, MAHSULLAR, MAHSULOTNI SETACTION-ni tanlang (NoExpand, indeks) \u003d ix_dt) dt pmp, dt\u003e \u003d @start buyrug'i bilan DTHaxoid, PromeDid, DT buyurtmasi

    SQL Serverni ochish soatlari:
    Vaqt CP \u003d 33860 ms, vaqt sarflangan \u003d 24247 ms.

    (Atroflar qayta ishlangan: 145608)

    (Qatorlar qayta ishlangan: 1)

    SQL Serverni ochish soatlari:
    Vaqt cpu \u003d 6374 ms, vaqt sarflangan \u003d 1718 ms.
    Vaqt cp \u003d 0 ms, muddati o'tgan vaqt \u003d 0 ms.


    Vaqt o'tishi bilan indeks sana bo'yicha juda tez bajarilishi aniq. Ammo taqqoslashda so'rov rejasi:

    1-chi so'rovning narxi avtomatik ravishda tanlangan klaster indeksi \u003d 2752, lekin indeks bilan so'rovi-so'rov qilingan sanaga binoan qiymatga ega qiymat.

    Bu erda bo'lgani kabi, indeksdan bu erda ikkita vazifa yo'q edi: saralash va namunaviy diapazon. Ushbu vazifaning bitta indeksi biz qaror qila olamiz. Ushbu misolda 1 kunlik ma'lumotlar oralig'i, lekin boshqa bir davr mavjud bo'lsa, masalan, 2 oy davomida saralash xarajatlari tufayli indeksni qidiradi.

    Mana, ko'rinadigan optimal echimlardan, men quyidagilarni ko'rmoqdaman:

    1. Bir oylik maydonni yaratish va indeksni yaratish (yil oyi, klaster indeksining qolgan qismlari). @SStart_month orasidagi dt va Yil oyidagi almashtirish [Elektron pochta bilan himoyalangan]oy va undan keyin siz allaqachon kerakli sanalarga filtrni qo'llang.
    2. Filtrlangan ko'rsatkichlar - indeksning o'zi klaster, ammo sana uchun filtr kerakli oy uchun filtr. Va bunday indekslar bizda bo'lgani kabi. Fikr echimga yaqin, ammo agar sharoitlar doirasi 2 FILED indeksidan bo'lsa, ulanish talab qilinadi va saralash hali ham muqarrar.
    3. Biz klaster indeksi, shunda har bir bo'limda faqat bir oy ichida.
    Loyihada men 3-variantni amalga oshirdim. Taqdim etilgan taqdimotning klaster indeksining ajralishi. Va agar namuna bir oyning vaqt oralig'ida bo'lsa, unda optimizator faqat bitta bo'limga ta'sir qiladi, uni saralashsiz skanerlash. Foydalanilmagan ma'lumotlar uzilish ishlatilmagan bo'limlarning kesilgan darajasida sodir bo'ladi. Agar 10 dan 20 gacha bo'lgan tintuv bo'lsa, biz ushbu sanalarni aniq qidiruvga ega emasmiz va oyning oxirgi kunidan boshlab 1-yilning birinchi kunidan boshlab ma'lumotlarni qidirish jarayonida tartiblangan indeksni qidirish xurmo skanerdan o'tkaziladi.

    Biz boshlang'ich reel indeksi klaster indeksi. Avvalo, biz boshimlarning barcha indekslarini olib tashlaymiz:

    Dr_dt indeks ix.th.turnhourtour-da; DBb.th.turnhour-da UIX_TIROLYHOURNI O'RNATISH;
    Va funktsiya va qismni ajratish sxemasini yarating:

    Sewformate YMD-ni o'rnating; Pf_tnnhothour (DateDeMeTime) Bitim qiymatlari ("2006-01-01", "2006-03-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01", "2006-04-01". 01 "," 2006-06-01 "," 2006-07-01 "," 2006-08-01 "," 2006-09-01 "," 2006-10-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 "," 2006-11-01 ". "2006-12-01", "2007-01-01", "2007-03-01", "2007-04-01", "2007-05-01", "," 2007-06-01 "," 2007-08-01 "," 2007-09-01 "," 2007-111-01 "," 2007- 12-01 "," 2008-02-01 "," 2008-03-01 "," 2008-04-01 "," 2008-05-01 ", 2008-06 01 "," 2008-08-01 "," 2008-08-01 "," 2008-10-01 "," 2008-11-01 "," 2008-12-01 "," 2008-12-01 "," "2009-01-01", "2009-03-01", "2009-04-01", "2009-05-01", "2009 yil", "2009 yil "2009-08-01", "2009-09-01", "2009-11-01", "2009-12-01", "2012 yil", "2012 yil ",", "2010-03-01", "2010-03-01", "2010-05-01", "2010-07 - 01 "," 2010-08-01 "," 2010-09-01 "," 2010-10-01 "," 2010-11-01 "," 2010-12-01 "," 2010-12-01 "," 2011 yil "," 2010-01-01 ", "2011-02-01", "2011-03-01", "2011-04-01", "", - 2011 yil ",", ",", "2011 yil," "", "2011 yil", "2011 yil", 2011 yil ", 2011 yil", 2011 yil "," 2011 yil "," 2011 yil ", - deb "2012-01-01", "2012-03-01", "2012-04-01", "2012-06-01", "2012 yil ",", "2012-08-01", "2012-09-01", "2012-11-01", "2012-12-01", "2013-01", "" ",", "," 2013-03-01 "," 2013-04-01 "," 2013-06-01 "," 2013-07-01 ", - deb ",", "," 2013-08-01 "," 2013-09-01 "," 2013-11-01 "," 2013-12-01 "," 2014-01-01 ", "2014-02-01", "2014-03-01", "2014-04-01", "2014-06-01", "2014-07-01", "2014 yil", "2014 yil", " ",", "," "", "2014-09-01", "2014-11-01", "2014-12-01", "2015-02", "2014-02 "2015-03-01", "2015-05-01", "2015-06-01", "2015-07-01", 2015-08-01 "," 2015-09-01 "," 2015-10-01 "," 2015-11-01 "," 2015-12-01 "," 2016-01-01 "," 2016-02-01 ", "2016-03-01" 2016-04-01 "," 2016-06-01 "," 2016-07-01 "," 2016 " "2016-10-01", "2016-11-01", "2016-12-01", "2017-01-01", 2017-03 "," 2017-04-01 "," 20 17-06-01 "2017-07-01", "2017-09-01", "2017-10-01", "2017-11-01", "2017- 12-01 "2018-01-01", "2018-03-01", "2018-04-01", "2018-05-01", "2018-06- 01 "," 2018-07-01 "," 2018-09-01 "," 2018-10-01 "," 2018-11-01 "," 2018-12-01 "," 2018-12-01 "," 2018-12-01 "," 2018-12-01 ". , "2019-01-01", "2019-03-01", "2019-04-01", "2019-05-01", "2019-06-01", " 2019-07-01 "2019-08-01", "2019-09-01", "2019-10-01", "2019-11-01", "2019-12-01"); Pf_turnoororehourni () qismlarga ajratish sxee ps_turnoororhourni ajratish sxee-ni yarating (); Yaxshi, yaxshi o'ting, klaster indeksi biz bilan faqat yaratilgan qismlarni yaratgan sxemada ma'lum: Db UIX_TANNORORURURNURI UIX_TURORNORURURNURIZNI YANGI. PS_TURORNORORURURIDA (DT) (DT) bilan Skajershour (Storletid, dt) (DATE_compressiya \u003d sahifa) bilan; --- 19 minut va endi nima bo'lganini ko'rib chiqaylik. O'zidan so'rov: sof sana YMD; deklaratsiya @start DateTime \u003d "2015-01-02", "2015-01-03" deb e'lon qiling @Start_month ma'lumotlar sexati \u003d "Varchar (9), @ Boshlanish, 120) +" 1 ", 120) dan tanlang (DT, Staxtaxid, Raqamli, miqdorini (miqdorini) DB @SHINTHOD va @finlishi-ni DT-ni boshqarish uchun DTH, u erda DT ning @/month va @finie-ning qismida bo'linadi) \u003e \u003d @Start buyurtmasi StoreHhid, Prothid, DT variant (Taraqam);


    SQL Serverni ochish soatlari:
    Vaqt CPU \u003d 7860 ms, vaqt \u003d 1725 ms.
    SQL-server vaqti va kompilyatsiya sintaktik tahlili:
    Vaqt cp \u003d 0 ms, muddati o'tgan vaqt \u003d 0 ms.
    So'rov rejasining narxi \u003d 9.4

    Aslida, bir xil bo'limdagi ma'lumotlar tanlangan va klasterli indeksi tezda tezda. Shuni qo'shimcha qilish kerakki, so'rov parametrlashtirilgan bo'lsa, yoqimsiz parametrlar paydo bo'ladi, parametrlar (qayta ishlash) variantga ishlov beriladi.

    SQL 2003 sintaksisi barcha platformalarni qo'llab-quvvatlaydi.

    Qavat (ibor)

    Agar siz ijobiy raqamni funktsiyaga o'tkazsangiz, funktsiya o'nlik kasrdan keyin turgan barcha narsalarni olib tashlashi mumkin.

    Ikki tomonlama (100.1) ikki tomonlama tanlang;

    Biroq, esda tutingki, salbiy raqamlar bo'lsa, kichikroq tomonga yaxlitlash mutlaq qiymatning oshishiga to'g'ri keladi.

    Ikki tomonlama (-100.1) ikki tomonlama;

    Pol funktsiyasiga teskari ta'sir ko'rsatish uchun CEil funktsiyasidan foydalaning.

    Ln.

    LN funktsiyasi raqamning tabiiy logaritmini qaytaradi, ya'ni matematik doimiy e (taxminan 2.718881) natijada berilgan raqamni olish kerak.

    SQL 2003 sintaksis

    Ln (ifoda)

    DB2, Oracle, Postgresql

    Db2, Oracle va Postgresql platformalari SQL 2003 sinyxorxi uchun SQL-ni qo'llab-quvvatlaydilar. Db2 va Postgresql xususiyati ham ln funktsiyasini Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sin-Sindonim sifatida qo'llab-quvvatlaydi.

    MySQL va SQL Server

    MySQL va SQL server tabiiy logaritmni hisoblash uchun o'z funktsiyasiga ega.

    Jurnal (ifoda)

    Keyingi misolda, Oracle raqamning tabiiy logarifmasi, taxminan matematik doimiy ravishda hisoblab chiqiladi.

    Ikkilamchi (2.718281) ni tanlang;

    Qarama-qarshi operatsiyani bajarish uchun, ekskursiya funktsiyasidan foydalaning.

    Mod.

    Mod funktsiyasi ajratilgan bo'linmaga ajratishdan muvozanatni qaytaradi. Barcha platformalar SQL 2003 MOD standart 2003 sintaksisini qo'llab-quvvatlaydi.

    SQL 2003 sintaksis

    Mod (bo'linadigan, bo'linuvchi)

    Standart MOCT funktsiyasi bo'linuvchiga bo'linishning muvozanatini olish uchun mo'ljallangan. Agar bo'linma nol bo'lsa, unda Delimi qaytariladi.

    Quyida Mod funktsiyasidan qanday qilib tanlangan bayonotda foydalanishingiz mumkin.

    2-raqamlardan MOC (12, 5) -ni tanlang;

    Pozitsiya

    Joylashuv funktsiyasi Qidiruv panelida chiziqning boshlang'ich holatini ko'rsatadigan butun sonni qaytaradi.

    SQL 2003 sintaksis

    Lavozimi (1-qatorda 1-qatorda)

    Standart holat funktsiyasi Qidiruv panelida ko'rsatilgan satrni birinchi kiritish (satr!) Birinchi yozuvini olish uchun mo'ljallangan (satr!). Agar string bo'lsa, funktsiya 0 ni qaytaradi! Qatorda !, va null - agar biron bir dalillar null bo'lsa.

    DB2.

    DB2 ekvivalent oralig'i mavjud.

    Mysql

    MySQL platformasi SQL 2003 standartiga muvofiq pozitsiyani qo'llab-quvvatlaydi.

    Kuch

    Quvvat funktsiyasi belgilangan darajaga raqamni qurish uchun ishlatiladi.

    SQL 2003 sintaksis

    Quvvat (bazaviy, indikator)

    Ushbu funktsiya natijasi indikator tomonidan belgilanadigan darajaga o'rnatilgan fonddir. Agar baza salbiy bo'lsa, indikator butun son bo'lishi kerak.

    DB2, Oracle, Postgresql va SQL serveri

    Ushbu ishlab chiqaruvchilarning barchasi SQL 2003 sintaksisini qo'llab-quvvatlaydi.

    Orol

    Oracle ekvivalent angi funktsiyasiga ega.

    Postgresql

    Postgresql platformasi SQL 2003 standartiga muvofiq pozitsiyani qo'llab-quvvatlaydi.

    Mysql

    MySQL platformasi ushbu kalit so'zni emas, balki ushbu funktsiyani qo'llab-quvvatlaydi.

    P0w (baza, indikator)

    Ijobiy sonning qurilishi juda aniq.

    Ikki tomonlama quvvatni (10.3) tanlang;

    0 darajaga o'rnatilgan har qanday raqam 1 ga teng.

    Ikkilamchi quvvatni tanlang (0.0);

    Salbiy ko'rsatkichi o'nlik kasrni chapga siljitadi.

    Ikki tomonlama quvvat (10, --3) ni tanlang;

    Saralash.

    SQRT funktsiyasi raqamning kvadrat ildizini qaytaradi.

    SQL 2003 sintaksis

    Barcha platformalar SQL 2003 sintaksisini qo'llab-quvvatlaydi.

    Saralash (ifoda)

    Ikki tomonlama SQRT (100) ni tanlang;

    Kenglik chelak.

    Kenglik chelakka teng gistogramma ustunlarining qiymatlarini belgilaydi.

    SQL 2003 sintaksis

    Quyidagi sintaksisda ifoda - bu gistogramma ustuni tayinlangan qiymat. Qoida tariqasida, ibora so'rov bilan qaytarilgan jadvalning bir yoki bir nechta ustunlariga asoslanadi.

    Kenglik chelak (ifoda, min, max, kolonogramm)

    Gistogramma ustun parametrlari mina qiymatlari oralig'ida yaratilgan gistogramma ustunlari sonini ko'rsatadi. Min parametrining qiymati diapazonda yoqilgan va Maks parametrining qiymati yoqilmaydi. Shaklning qiymati gistogramma ustunlaridan biriga tayinlanadi, shundan so'ng funktsiya tegishli gistogramma ustunining sonini qaytaradi. Agar ifoda belgilangan ustun doirasiga kirmasa, funktsiya 0 yoki Maks + 1 ni qaytarsa, ibora min yoki katta yoki maksimal darajaga teng ekanligiga bog'liq.

    Keyingi misolda, 1 dan 10 gacha bo'lgan butun sonlar gistogrammaning ikki ustuni o'rtasida taqsimlanadi.

    Quyidagi misol yanada qiziqarli. 1 dan 10 gacha bo'lgan 11 qiymatlar diapegrammaning uch ustuni o'rtasida taqsimlanadi, bu oraliqda yoqilgan va masofadan turib o'girilmagan mikal qiymat o'rtasidagi farqni tasvirlash uchun.

    Pivotdan X, kenglik_buket (X, 1.10.3) ni tanlang;

    CX \u003d, X \u003d 9.9 va x-10 natijalariga alohida e'tibor bering. Ularning ushbu misolida - 1, bu oraliqning pastki chegarasini ko'rsatadigan birinchi ustunga tushadi , 1-sonli ustun X\u003e \u003d min. Biroq, Maks parametrining kirish qiymati maksimal qiymatlar bilan ustunga kiritilmagan. Ushbu misolda 10 raqami toshib ketgan ustunga kiradi. 9,9 raqami 3-sonli qiymati 3-ustunga kiradi va bu r doirasining yuqori chegarasi X sifatida belgilanadi< max.