Ajutați-on-sql (dml) cum să îmbinați datele din două coloane într-una fără să folosiți uniunea și să vă alăturați

Astfel de întrebări cu o regularitate de invidiat apar pe paginile diferitelor forumuri. Apropo, pentru mine este încă un mister de ce este o condiție suplimentară de a nu utiliza UNIUNEA și / sau JOIN. Nu pot decât să presupun că acestea sunt întrebări care sunt solicitate în timpul interviului.

Lipsa lirică. Cred că, așa cum Joe Selko ar răspunde la această întrebare: există o eroare de proiectare, că un atribut este împărțit în două. Cu toate acestea, lăsăm la o parte problemele de proiectare și trecem la această sarcină.

Creați un tabel de testare și adăugați câteva date la acesta:

Deci, există un tabel T, care conține două coloane cu date de același tip:

Este necesar să se obțină următorul rezultat:

Știu trei moduri implementate de instrumentele standard ale limbajului interactiv SQL.

1. UNIUNEA TOATE

2. COMPLETE FULL

Pentru a nu pierde duplicatele în diferite coloane, vom efectua o conexiune completă (FULL JOIN) pe un predicat fals, spunem 1 = 2:

Apoi, utilizați funcția COALESCE. care ne va oferi tot ce aveți nevoie:

3. UNPIVOT

Valorile din coloanele col1 și col2 sunt colectate într-o coloană colă a tabelului auxiliar unpvt. Cu toate acestea, există o particularitate în utilizarea operatorilor PIVOT și UNPIVOT: nu iau în considerare valorile NULL. Rezultatul ultimei solicitări va fi:

Acest obstacol în calea rezolvării problemei noastre poate fi depășit prin înlocuirea valorii NULL la intrarea operatorului UNPIVOT cu o valoare pseudo, adică valoare care, evident, nu poate fi în datele originale și apoi efectuați transformarea inversă:

Aici, COALESCE (colx, 777) înlocuiește valorile NULL în coloana colx cu 777, iar funcția NULLIF (col, 777) efectuează transformarea inversă.

Ultima soluție ne dă rezultatul dorit, dar conține un defect - valoarea 777 poate apărea mai devreme sau mai târziu în date, ceea ce va duce la rezultate incorecte. Pentru a elimina această defecțiune, puteți utiliza o valoare de alt tip pe care nu o puteți înțelege într-o coloană întregă, de exemplu, caracterul "x". În mod natural, pentru a aplica această abordare, pentru compatibilitatea tipurilor, tipul întreg al coloanelor ar trebui convertit la un tip de caracter, efectuând transformarea inversă a rezultatului final dacă este necesar:

Câteva cuvinte despre eficacitatea soluțiilor prezentate. Conform planului de executare a interogării, costurile principale se datorează citirii datelor (operațiunea de scanare a tabelului). Pentru primele două soluții, scanarea este efectuată de două ori, în timp ce pentru ultima (UNPIVOT) - o singură dată, datorită avantajului dublu de performanță.

Există o altă opțiune pe care o folosesc:

Produsul cartezian al tabelului T cu un eșantion de 2 linii dă o "dublare" (fiecare rând din tabel este repetat de 2 ori - pentru a = 1 și a = 2). Pentru primul caz, luați valoarea de la col1, iar pentru al doilea - de col2.

Aici, desigur, există atât uniune cât și uniune, dar, în opinia mea, singura scanare a tabelului prezintă interes în această problemă.


Crearea de site-uri în Tyumen
Creăm site-uri de înaltă calitate și ieftine, site-uri de cărți de vizită, corporative
professor-labs.ru
Calculul bucătăriei
Bucătării, holuri, fațade de mobilier. Saloane de bucătărie italiană
hanak.ru
fantezie
filme-online-anschauen.com

Exerciții SELECT (etapele de rating)