Avatar billede madeindk Nybegynder
27. oktober 2009 - 22:23 Der er 12 kommentarer og
2 løsninger

WITH, UNION ALL og ORDER BY - virker ikke :(

Jeg har følgende SQL sætning:

-- Loop menuitems
WITH temp_entries (page_id, pagename, deactive, hidden, startpage, page_level) AS (
            SELECT TOP 10000 s.id AS page_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, 1 AS page_level
            FROM cms_menuitems s
            WHERE
                s.parent_id = 0
                AND
                s.language_id = @language_id
            ORDER BY s.page_order
           
        UNION ALL
       
            SELECT s.id AS page_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, page_level + 1 AS nivaeu
            FROM cms_menuitems s, temp_entries t
            WHERE
                s.parent_id = t.page_id
                AND
                s.language_id = @language_id
)
-- Print menuitems
SELECT page_id, pagename, deactive, hidden, startpage, page_level FROM temp_entries

Når jeg prøver at tilføje 's.page_order' i min ORDER BY i anden SELECT, så siger den at det må man ikke - hvad er løsningen på dette?

Mvh Søren
27. oktober 2009 - 22:51 #1
Saa vidt jeg har forstaaet saa skal ORDER BY komme sidst.  Altsaa foerst din foerste SELECT, saa UNION ALL, saa din anden SELECT og derefter ORDER BY.

Teorien er (vist nok) at ORDER BY ikke er en relational operation men udelukkende en lay-out operation.  Foerst skal maskinen have alle instruktioner om HVAD der skal soeges, og derefter skal den have instruktion om HVORDAN det skal vises, altsaa ORDER BY.
Avatar billede madeindk Nybegynder
27. oktober 2009 - 23:08 #2
Ok - har du evt. et eksempel på hvordan det kunne komme til at se ud? Har godt læst noget om det rundt omkring, men synes ikke lige jeg kunne finde ud af hvor jeg skulle sætte det ind henne :-)
Avatar billede madeindk Nybegynder
27. oktober 2009 - 23:13 #3
Jeg har skrevet den lidt om, så nu ser den sådan her ud - men det spiller sgu stadig ikke rigtig :(

-- Loop menuitems
    WITH temp_entries (page_id, parent_id, pagename, deactive, hidden, startpage, p_order, page_level) AS
    (
            SELECT TOP 10000 s.id AS page_id, s.parent_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, s.page_order, 1 AS page_level
            FROM cms_menuitems s
            WHERE
                s.parent_id = 0
                AND
                s.language_id = @language_id
            ORDER BY s.page_order
                           
        UNION ALL
       
            SELECT s.id AS page_id, s.parent_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, s.page_order+p_order, t.page_level+1
            FROM cms_menuitems s, temp_entries t
            WHERE
                s.parent_id = t.page_id
                AND
                s.language_id = @language_id
    )
    -- Print menuitems
    SELECT page_id, parent_id, pagename, deactive, hidden, startpage, p_order, page_level FROM temp_entries ORDER BY p_order
28. oktober 2009 - 04:29 #4
Jeg proevede at dobble-checke min mening som foelger, men jeg fandt kun et eksempel paa "WITH temp_entries" paa Google.  Jeg kan heller ikke proeve det af paa mit system fordi jeg ikke har resten af din kode saa som din tabel.  Men det jeg mente var:

-- Loop menuitems
    WITH temp_entries (page_id, parent_id, pagename, deactive, hidden, startpage, p_order, page_level) AS
    (
            SELECT TOP 10000 s.id AS page_id, s.parent_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, s.page_order, 1 AS page_level
            FROM cms_menuitems s
            WHERE
                s.parent_id = 0
                AND
                s.language_id = @language_id
                           
        UNION ALL
       
            SELECT s.id AS page_id, s.parent_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, s.page_order+p_order, t.page_level+1
            FROM cms_menuitems s, temp_entries t
            WHERE
                s.parent_id = t.page_id
                AND
                s.language_id = @language_id

      ORDER BY s.page_order
    )
    -- Print menuitems
    SELECT page_id, parent_id, pagename, deactive, hidden, startpage, p_order, page_level FROM temp_entries
29. oktober 2009 - 08:11 #5
madeindk, hvad er din reaktion?  Var mit svar til nogen hjaelp?  Forventer du flere inputs?  Hvis ikke, saa beder jeg dig at lukke svaret.  Saa staar det ikke laengere som aabent paa min liste af indlaeg.  Hvis jeg har vaeret til hjaelp saa giv mig points, ellers luk svaret ved at give pointene til dig selv.
Avatar billede madeindk Nybegynder
29. oktober 2009 - 09:37 #6
Det du skrev i indlæg 4, er jo lige præcis det der IKKE kan lade sig gøre, og som jeg skriver i mit spørgsmål. Det kan ikke lade sig gøre at lave ORDER på anden SELECT :(
29. oktober 2009 - 11:59 #7
Jeg vil vaedde paa at du ikke har fjernet ORDER BY fra dit foerste SELECT!
ORDER BY skal hverken vaere i det foerste eller i det andet select.  ORDER BY skal komme efter at du er faerdig med at selecte og unionere.

Jeg har afproevet det paa min egen database (paa Hollandsk, men det er mysql ligeglad med.)  Jeg viser nedenfor min query og den resulterende tabel.

Dette link http://dev.mysql.com/doc/refman/5.0/en/union.html goer det tydeligere ved at placere foerst og andet select i paranteser, saaledes:

(SELECT a FROM t1 WHERE a=10 AND B=1)
UNION
(SELECT a FROM t2 WHERE a=11 AND B=2)
ORDER BY a

men paranteserne er ikke noedvendige.

Jeg har lavet dette som et svar fordi jeg gerne vil slutte spoergsmaalet nu.  Hvis mit svar har hjulpet (efter du fjerner ORDER BY fra det foerste SELECT) saa giv mig points og derved luk spoergsmaalet.  Hvis mit svar ikke har hjulpet saa luk venligst alligevel spoergsmaalet (ved at give dig selv points) saa det ikke laengere staar som aabent i min liste af indlaeg.

Her er min query:

SELECT persoonId, geboortedatum, geschlacht
FROM Persoon
WHERE geschlacht = 'v'
UNION
SELECT persoonId, geboortedatum, geschlacht
FROM Persoon
WHERE geschlacht = 'm'
ORDER BY geschlacht, geschlacht

og her er den resulterende tabel:

persoonId    geboortedatum    geschlacht 
392         1918-07-17     v
257         1925-12-21     m
259         1925-12-21     m
256         1927-08-08     v
129         1940-03-15     m
127         1946-07-17     v
388         1948-09-03     m
258         1955-12-05     m
128         1972-01-31     v
135         1976-04-04     v
498         1976-11-01     m
500         1980-04-12     v
Avatar billede madeindk Nybegynder
29. oktober 2009 - 12:20 #8
Argh, på den måde - det var ikke sådan jeg forstod det.

Men vil den så komme til at sortere som flg.:

Hovedside (1)
- Underside 1 (1)
- Underside 2 (2)
- Underside 3 (3)
Hovedside 2 (2)
Hovedside 3 (3)
- Underside 1 (1)
- Underside 2 (1)

Det tal der står i parentes er sorteringstallet.
Avatar billede madeindk Nybegynder
29. oktober 2009 - 12:21 #9
Hov, det skulle naturligvis komme til at se sådan her ud:

Hovedside (1)
- Underside 1 (1)
- Underside 2 (2)
- Underside 3 (3)
Hovedside 2 (2)
Hovedside 3 (3)
- Underside 1 (1)
- Underside 2 (2)
Avatar billede madeindk Nybegynder
29. oktober 2009 - 12:27 #10
Sådan her ser min query ud nu, og det spiller ikke.

BEGIN
    -- Loop menuitems
    WITH temp_entries (page_id, parent_id, pagename, deactive, hidden, startpage, page_level) AS
    (
            (SELECT TOP 10000 s.id AS page_id, s.parent_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, 1 AS page_level
            FROM cms_menuitems s
            WHERE
                s.parent_id = 0
                AND
                s.language_id = @language_id
            )
                           
        UNION ALL
       
            (SELECT s.id AS page_id, s.parent_id, s.pagename, s.is_deactive, s.is_hidden, s.is_startpage, t.page_level+1
            FROM cms_menuitems s, temp_entries t
            WHERE
                s.parent_id = t.page_id
                AND
                s.language_id = @language_id
            )
            ORDER BY page_order
    )
    -- Print menuitems
    SELECT page_id, parent_id, pagename, deactive, hidden, startpage, page_level FROM temp_entries
END
29. oktober 2009 - 12:45 #11
Saa har jeg udtoemt min ekspertise.  Maaske har det noget at goere med "WITH_TEMP" som jeg ikke har laert.  Jeg gaar ud fra at det er noget tilsvarende til VIEW, du laver, i princippet, en ny tabel (temporary) som du saa bruger i en query, den sidste saetning.

Det faldt mig ind at en mulighed kunne vaere slet ikke at bruge ORDER BY in WITH_TEMP.  Det er i virkeligheden foerst naar du kalder WITH_TEMP i "SELECT page_id, parent_id, pagename, deactive, hidden, startpage, page_level FROM temp_entries" at du skal have det orderet, saa ingen ORDER BY overhovedet i WITH_TEMP men SELECT page_id, parent_id, pagename, deactive, hidden, startpage, page_level FROM temp_entries ORDER BY page_order.

Hvis det heller ikke hjaelper saa maa jeg melde pas, og fordi dette spoergsmaal er et par dage gammelt er det usandsynligt at andre skal finde det, saa luk det venligtst saa det ikke laengere staar som aabent i min liste af indlaeg.  (Jeg ville foreslaa at stille et nyt spoergsmaal saa som det foelgende:  "Jeg har denne SQL saetning [din kode med alle ORDER BY fjernet.]  Hvordan faar jeg resultatet ordnet i page_order raekkefoelge.)
Avatar billede madeindk Nybegynder
29. oktober 2009 - 12:57 #12
Ok, fint - jeg har prøvet at gøre det du foreslår men den sorterer stadig ikke korrekt, på den måde som mine sorteringstal er skrevet ind her:

Hovedside (1)
- Underside 1 (1)
- Underside 2 (2)
- Underside 3 (3)
Hovedside 2 (2)
Hovedside 3 (3)
- Underside 1 (1)
- Underside 2 (2)
29. oktober 2009 - 13:40 #13
Saa kan jeg ikke hjaelpe.  Maa jeg bede dig om at lukke spoergsmaalet?
Avatar billede madeindk Nybegynder
29. oktober 2009 - 14:01 #14
Ja, jeg lukker her.
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Computerworld tilbyder specialiserede kurser i database-management

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester