简体   繁体   中英

mysql union two queries with order by

I want to union two queries that have different ORDER BY

however the the other query doesn't behave according to it's ORDER BY

I don't know what's causing this bug but it's working fine in my local files. but when I up it on live site the behavior of the second query doesn't work well.

the problem was on sub-query table2 it should display all records order by starting_date descending but the query doesn't sort that way... I don't know what's causing this.

thanks in advance

here's my mysql query.

 SELECT * FROM (
            SELECT 
            events.event_id,
            events.event_name_en,
            events.event_name_ch,
            events.event_description_en,
            events.event_description_ch,
            events.ref,
            events.start_date,
            events.end_date,
            events.venue_id,
            events.organizers_id,
            events.website,
            events.payment_method,
            events.visitors,
            events.display,
            events.booking_form,
            events.map,
            events.lmap,
            events.insurance_offered,
            events.masterhead_img,
            events.icon_img,
            events.event_token,
            events.added_by as event_added_by,
            events.added_date as event_added_date,
            events.updated_by,
            events.updated_date,
            events.active,
            events.allow_ond,
            events.allow_ond_reg,
            events.terms_p,
            events.cancel_p,
            events.no_show_p,
            events.refund_p,
            events.official_desc,
            events.supporting_desc,
            events.participating_desc,
            events.official_title,
            events.supporting_title,
            events.participating_title,
            events.order_number,
            venue.venue_en,
            venue.venue_ch,
            venue.added_by as venue_added_by,
            venue.added_date as venue_added_date,
            venue.updated_by as venue_updated_by,
            venue.updated_date as venue_updated_date,
            countries.country_id,
            countries.country_code,
            countries.country_name

            FROM 
            events 
            INNER JOIN venue
            ON venue.venue_id=events.venue_id
            INNER JOIN countries
            ON countries.country_id=events.country_id
            WHERE events.display = '1' AND events.order_number != ''
            AND events.active = '1' 
            ORDER BY events.order_number ASC) as table1

            UNION ALL

            SELECT * FROM (SELECT 
            events.event_id,
            events.event_name_en,
            events.event_name_ch,
            events.event_description_en,
            events.event_description_ch,
            events.ref,
            events.start_date,
            events.end_date,
            events.venue_id,
            events.organizers_id,
            events.website,
            events.payment_method,
            events.visitors,
            events.display,
            events.booking_form,
            events.map,
            events.lmap,
            events.insurance_offered,
            events.masterhead_img,
            events.icon_img,
            events.event_token,
            events.added_by as event_added_by,
            events.added_date as event_added_date,
            events.updated_by,
            events.updated_date,
            events.active,
            events.allow_ond,
            events.allow_ond_reg,
            events.terms_p,
            events.cancel_p,
            events.no_show_p,
            events.refund_p,
            events.official_desc,
            events.supporting_desc,
            events.participating_desc,
            events.official_title,
            events.supporting_title,
            events.participating_title,
            events.order_number,
            venue.venue_en,
            venue.venue_ch,
            venue.added_by as venue_added_by,
            venue.added_date as venue_added_date,
            venue.updated_by as venue_updated_by,
            venue.updated_date as venue_updated_date,
            countries.country_id,
            countries.country_code,
            countries.country_name

            FROM 
            events 
            INNER JOIN venue
            ON venue.venue_id=events.venue_id
            INNER JOIN countries
            ON countries.country_id=events.country_id
            WHERE events.display = '1' AND events.order_number = ''
            AND events.active = '1' 
            ORDER BY events.start_date DESC) as table2

result:

the first two row is good. result of the table1 sub-query

but when you look at the third row and so on.. the order of starting_date desc doesn't work well... the third row should be world engineer blah.....

在此处输入图片说明

From the MySQL manual pages

http://dev.mysql.com/doc/refman/5.7/en/union.html

However, use of ORDER BY for individual SELECT statements implies nothing about the order in which the rows appear in the final result because UNION by default produces an unordered set of rows . Therefore, the use of ORDER BY in this context is typically in conjunction with LIMIT, so that it is used to determine the subset of the selected rows to retrieve for the SELECT, even though it does not necessarily affect the order of those rows in the final UNION result. If ORDER BY appears without LIMIT in a SELECT, it is optimized away because it will have no effect anyway.

I think you might be able to do what you want by playing around with the ORDER BY clause:-

SELECT events.event_id,
        events.event_name_en,
        events.event_name_ch,
        events.event_description_en,
        events.event_description_ch,
        events.ref,
        events.start_date,
        events.end_date,
        events.venue_id,
        events.organizers_id,
        events.website,
        events.payment_method,
        events.visitors,
        events.display,
        events.booking_form,
        events.map,
        events.lmap,
        events.insurance_offered,
        events.masterhead_img,
        events.icon_img,
        events.event_token,
        events.added_by as event_added_by,
        events.added_date as event_added_date,
        events.updated_by,
        events.updated_date,
        events.active,
        events.allow_ond,
        events.allow_ond_reg,
        events.terms_p,
        events.cancel_p,
        events.no_show_p,
        events.refund_p,
        events.official_desc,
        events.supporting_desc,
        events.participating_desc,
        events.official_title,
        events.supporting_title,
        events.participating_title,
        events.order_number,
        venue.venue_en,
        venue.venue_ch,
        venue.added_by as venue_added_by,
        venue.added_date as venue_added_date,
        venue.updated_by as venue_updated_by,
        venue.updated_date as venue_updated_date,
        countries.country_id,
        countries.country_code,
        countries.country_name
FROM events 
INNER JOIN venue ON venue.venue_id = events.venue_id
INNER JOIN countries ON countries.country_id = events.country_id
WHERE events.display = '1' 
AND events.active = '1' 
ORDER BY IF(events.order_number = '', 1, 0),
        IF(events.order_number = '', NULL, events.order_number) ASC,
        IF(events.order_number = '', events.start_date, NULL) DESC

This will order all the records that would come from your first subquery first, followed by all the records from the 2nd subquery. Within that it will order the first by order_number ASCending and the 2nd by start_date DESCending.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM