2014-03-04 53 views
0

嘗試搜索類似的東西,但目前爲止沒有運氣。帶自定義值的MySQL GROUP BY

我有一個查詢在包含電話日誌(ID,號碼,來源和電話名稱)的表上執行。其目的是獲取電話名稱上按不同標準分組的電話總數(有四個或五個不同的標準)。目前我正在做這樣的事情:

SELECT COUNT(phones_statistics.id) AS number_of_calls, phones_statistics.calldate 
FROM phones_statistics 
INNER JOIN phones ON phones_statistics.phone_id = phones.id 
WHERE phones.abbr NOT LIKE '@%' 
GROUP BY 
    YEAR(phones_statistics.calldate) 
    + '-' 
    + MONTH(phones_statistics.calldate) 
    + '-' 
    + DAY(phones_statistics.calldate) 
; 

的問題,因爲你可能已經看到,是每個LIKE/NOT LIKE標準,我必須建立一個能與不同的標準另一個查詢,我猜這將很快變得討厭(目前有5個查詢,在返回結果之前總共運行20秒)。

所以我在想,是不是有一些簡單的方法通過構建一個自定義分組這樣避免多次查詢和做的伎倆:

SELECT 
    COUNT(phones_statistics.id) AS number_of_calls, 
    phones_statistics.calldate, 
    (something like a switch - 4 statements, 4 return values, 
    assigned to this field) 
    AS custom_field 
... 
rest of the query 
... 
GROUP BY custom_field, 
    YEAR(phones_statistics.calldate) 
    + '-' 
    + MONTH(phones_statistics.calldate) 
    + '-' 
    + DAY(phones_statistics.calldate) 

回答

1

首先,你group by條款的日期部分不作感。我假設你只想要date(calldate)。但是,您今天正在生成以下值(2014-03-04):

2014 + '-' + 03 + '-' + 04 

MySQL使用'+'來添加數字。它會根據前導數字字符自動將字符串轉換爲數字,如果沒有,則值爲0。在MySQL中,表達式加起來爲:2021。對我而言,這似乎是一件奇怪的事情。

我懷疑你想是這樣的:

SELECT date(ps.calldate) as calldate, 
     SUM(ps.abbr NOT LIKE 'patten1%') as numPattern1, 
     SUM(ps.abbr NOT LIKE 'patten2%') as numPattern2, 
     SUM(ps.abbr NOT LIKE 'patten3%') as numPattern3, 
     SUM(ps.abbr NOT LIKE 'patten4%') as numPattern4, 
     SUM(ps.abbr NOT LIKE 'patten5%') as numPattern5 
FROM phones_statistics ps INNER JOIN 
    phones p 
    ON ps.phone_id = p.id 
WHERE ps.abbr NOT LIKE '@%' 
GROUP BY date(calldate); 

換句話說,使用條件聚集和每個值在單獨的列。

+0

謝謝你的代碼中找到另一種方式來做到這一點。我原本只是花了一年又一個月,後來又增加了一天(似乎我昨天太困了,不想記住'DATE'函數),但它仍然給了我一個字符串的日期,而不是一個數字。 除此之外,它的工作原理與它應該完全一樣,並且是一個整潔的方式。謝謝 :) – NorthBridge

0

只是爲了記錄在案,我通過使用CASE...WHEN

SELECT 
    COUNT(phones_statistics.id) AS calls_number, 
    DATE(phones_statistics.calldate), 
    CASE 
    WHEN phones.abbr LIKE '%pattern1%' THEN 'Result1' 
    WHEN phones.abbr LIKE '%pattern2%' THEN 'Result2' 
    ELSE 'default_result' 
    END 
as type 
FROM phones_statistics 
INNER JOIN phones ON phones_statistics.phone_id = phones.id 
GROUP BY type, DATE(phones_statistics.calldate);