2016-06-22 3 views
-1
select 
    DISTINCT(destination_name), 
    count(dst),TIME_FORMAT(SEC_TO_TIME(sum(duration)), '%H:%i:%s'), 
    TIME_FORMAT(SEC_TO_TIME(sum(billsec)), '%H:%i:%s'), 
    ROUND((sum(billsec)*cost) ,2), 
    tarrif_plan.planname from tarrif_rate_domestic 
LEFT OUTER JOIN 
    tarrif_plan ON (tarrif_plan.planname = tarrif_rate_domestic.planname) 
LEFT OUTER JOIN cdr on (tarrif_plan.planname = tarrif_rate_domestic.planname) 
where cdr.dstchannel REGEXP tarrif_plan.trunkname and 
    cdr.dst REGEXP tarrif_rate_domestic.areacode and 
    disposition = 'ANSWERED' 
group by destination_name,tarrif_plan.planname; 

Выход:Sql Query изменение - 3 таблицы присоединиться

+------------------------+------------+-----------------------------------------------------+----------------------------------------------------+-------------------------------+----------------+ 
| destination_name  | count(dst) | TIME_FORMAT(SEC_TO_TIME(sum(duration)), '%H:%i:%s') | TIME_FORMAT(SEC_TO_TIME(sum(billsec)), '%H:%i:%s') | ROUND((sum(billsec)*cost) ,2) | planname  | 
+------------------------+------------+-----------------------------------------------------+----------------------------------------------------+-------------------------------+----------------+ 
| Mobile 2    |  3018 | 63:08:02           | 49:34:58           |      3402.17 | Standard  | 
| Mobile 2    |   41 | 02:10:08           | 01:51:45           |       0.00 | Other Provider | 
| On-Net     |  455 | 16:30:37           | 15:19:22           |      374.00 | Standard  | 
| On-Net     |  712 | 50:45:15           | 49:51:03           |       0.00 | Other Provider | 
| Special    |  143 | 11:51:49           | 11:43:07           |      286.03 | Standard  | 
| Mobile     |  3177 | 77:20:13           | 62:30:31           |      4289.09 | Standard  | 
| Mobile     |   80 | 03:28:29           | 02:52:08           |       0.00 | Other Provider | 
+------------------------+------------+-----------------------------------------------------+----------------------------------------------------+-------------------------------+----------------+ 

Однако я хотел бы иметь дополнительную строку, чтобы показать значения, которые не соответствуют: а может быть, "Неизвестный"

I верю, что мне нужно использовать CASE, но я не могу найти, где мне нужно добавить в запрос.

Вот некоторые данные для 3-х таблиц:

Tarrif_plan:

+----------+----------------+--------------+ 
| uniqueid | planname  | trunkname | 
+----------+----------------+--------------+ 
|  1 | Standard  | IAX2/tmp  | 
|  2 | Other Provider | IAX2/myprov | 
+----------+----------------+--------------+ 

Tarrif_rate_domestic:

+----------+------------------------+--------------------------------------------------------------------------------------------+---------+----------------+ 
| uniqueid | destination_name  | areacode  | cost | planname  | 
+----------+------------------------+--------------------------------------------------------------------------------------------+---------+----------------+ 
|  1 | Mobile 2    | 2[2]{9}  | 0.01906 | Standard  | 
|  2 | Mobile 2    | 2[2]{9}  | 0  | Other Provider | 
|  3 | Special    | 9[9]{9}  | 0.01906 | Standard  | 
|  4 | Special    | 9[9]{9}  | 0  | Other Provider | 
|  5 | Mobile     | 1[1]{9}  | 0.00678 | Standard  | 
|  6 | Mobile     | 1[1]{9}  | 0  | Other Provider | 

CDR:

+---------------------+------------+------------+-------------------+----------+---------+-------------+ 
| calldate   | src  | dst  | dstchannel  | duration | billsec | disposition | 
+---------------------+------------+------------+-------------------+----------+---------+-------------+ 
| 2016-06-20 03:28:23 | 100  | 2222222222 | IAX2/tmp-16938 |  28 |  21 | ANSWERED | 
| 2016-06-20 04:39:11 | 7777777777 | 1111111111 |     |  11 |  11 | ANSWERED | 
| 2016-06-20 04:46:21 | 100  | 2222222222 | IAX2/tmp-22288 |  43 |  30 | ANSWERED | 
| 2016-06-20 04:48:13 | 7777777777 | 1111111111 |     |  9 |  9 | ANSWERED | 
| 2016-06-20 04:53:15 | 100  | 4444444444 | IAX2/myprov-00d94 |  5 |  0 | NO ANSWER | 
| 2016-06-20 05:01:03 | 100  | 9999999999 | IAX2/tmp-20367 |  914 |  893 | ANSWERED | 
| 2016-06-20 05:12:47 | 100  | 200  | SIP/200-00000d98 |  16 |  13 | ANSWERED | 
| 2016-06-20 05:15:38 | 100  | 9999999999 | IAX2/tmp-30597 |  1 |  0 | NO ANSWER | 
| 2016-06-20 05:15:57 | 100  | 200  | SIP/200-00000d9c |  3 |  0 | NO ANSWER | 
| 2016-06-20 05:16:18 | 100  | 9999999999 | IAX2/tmp-22584 |  32 |  3 | ANSWERED | 
| 2016-06-20 05:16:40 | 100  | 200  | SIP/200-00000da0 |  4 |  0 | NO ANSWER | 
| 2016-06-20 05:17:58 | 100  | 1111111111 | IAX2/tmp-25515 |  23 |  14 | ANSWERED | 
| 2016-06-20 05:19:39 | 100  | 200  | SIP/200-00000da4 |  29 |  24 | ANSWERED | 
| 2016-06-20 05:20:45 | 8888888888 | 9999999999 | IAX2/myprov-00da7 |  81 |  81 | ANSWERED | 
| 2016-06-20 05:21:13 | 100  | 4444444444 | IAX2/tmp-29717 |  339 |  311 | ANSWERED | 
| 2016-06-20 05:21:25 | 100  | 2222222222 | IAX2/tmp-17460 |  40 |  3 | ANSWERED | 
| 2016-06-20 05:21:45 | 100  | 200  | SIP/200-00000daa |  21 |  0 | NO ANSWER | 
| 2016-06-20 05:23:16 | 100  | 200  | SIP/200-00000dae |  54 |  51 | ANSWERED | 
| 2016-06-20 05:24:30 | 100  | 2222222222 | IAX2/tmp-19105 |  19 |  3 | ANSWERED | 
| 2016-06-20 05:26:10 | 100  | 1111111111 | IAX2/tmp-24135 |  54 |  23 | ANSWERED | 
+---------------------+------------+------------+-------------------+----------+---------+-------------+ 

Подведем итоги:

  1. Использование tarrif_plan найти только записи в CDR, где cdr.dstchannel совпадают с tarrif_plan.trunkname (REGEXP)
  2. Использование Tarrif_plan, чтобы получить имя получателя, если матч cdr.dst tarrif_rate_domestic.areacode (REGEXP) NB: Если не найдено дисплей как "Unknown" ехр: 4444444444
+0

я понял, что из-за cdr.dst не соответствует tarrif_rate_domestic.areacode, нет tarrif_rate_domestic.planname и значение NULL Значение было когда-либо у меня «tarrif_plan.planname = tarrif_rate_domestic.planname» не позволяет мне подсчитать эти несоответствующие значения. – user1019214

ответ

0

Вы можете добавить СЛУЧАЙ в выберите, я попытался ниже

select 
    CASE 
    WHEN destination_name IS NULL THEN 'Unknown' 
    ELSE destination_name 
    END as destination_name, 
    count(dst),TIME_FORMAT(SEC_TO_TIME(sum(duration)), '%H:%i:%s'), 
    TIME_FORMAT(SEC_TO_TIME(sum(billsec)), '%H:%i:%s'), 
    ROUND((sum(billsec)*cost) ,2), 
    tarrif_plan.planname from tarrif_rate_domestic 
LEFT OUTER JOIN 
    tarrif_plan ON (tarrif_plan.planname = tarrif_rate_domestic.planname) 
LEFT OUTER JOIN cdr on (tarrif_plan.planname = tarrif_rate_domestic.planname) 
where cdr.dstchannel REGEXP tarrif_plan.trunkname and 
    cdr.dst REGEXP tarrif_rate_domestic.areacode and 
    disposition = 'ANSWERED' 
group by destination_name,tarrif_plan.planname; 

Th не уверен, какой столбец вы предпочитаете, поэтому отрегулируйте регистр в запросе по вашему желанию.

Решение Реф. - Joining two tables when there is a not matching record exist

+0

Я пробовал, что это не работает, потому что «имя_пакета» всегда имеет значение из-за полного запроса. Некоторые, где в WHERE или JOINS запрос даже не смотрит на значения, которые не совпадают. – user1019214

+0

Есть 2 столбца «cdr.dst» и «tarrif_rate_domestic.areacode», которые должны соответствовать, что когда-либо не соответствует, нужно отображать «имя_пакета» как неизвестное. Он отлично подходит для подсчета количества «cdr.dst», которые соответствуют «tarrif_rate_domestic.areacode» – user1019214

+0

Важно отметить. Существует второй матч «cdr.dstchannel» и «tarrif_plan.trunkname» – user1019214

0

Я подозреваю, что я нашел свое решение:

select 
    count(dst),duration,TIME_FORMAT(SEC_TO_TIME(billsec), '%H:%i:%s') as talktime, 
    ROUND((billsec*cost) ,2), 
    CASE WHEN destination_name IS NULL 
    THEN 'Unknown' ELSE destination_name END as Destname, tarrif_plan.planname 
from cdr 
LEFT OUTER JOIN tarrif_rate_domestic ON (cdr.dst REGEXP tarrif_rate_domestic.areacode) 
LEFT JOIN tarrif_plan ON (tarrif_plan.planname = tarrif_rate_domestic.planname) 
where 
    (cdr.dstchannel REGEXP tarrif_plan.trunkname or tarrif_plan.trunkname is null) and 
    disposition = 'ANSWERED' 
group by destname,tarrif_rate_domestic.planname; 

нужно попытаться выяснить, что по-другому.

+0

Я могу подтвердить, что это тоже не работает. Он подсчитывает все значения cdr.dst, которые не соответствуют cdr.dstchannel для tarrif_plan.trunkname. – user1019214

0

Ниже я могу подтвердить, работает точно так, как ожидалось:

SELECT 
    count(pf.dst), 
    TIME_FORMAT(SEC_TO_TIME(sum(pf.duration)), '%H:%i:%s') as totaltime, 
    TIME_FORMAT(SEC_TO_TIME(sum(pf.billsec)), '%H:%i:%s') as talktime, 
    ROUND((sum(pf.billsec*f.cost)), 2), 
    f.planname, 
    f.destination_name 
FROM cdr AS pf 
    LEFT JOIN tarrif_plan AS p ON pf.dstchannel REGEXP p.trunkname 
    LEFT JOIN tarrif_rate_domestic AS f ON pf.dst REGEXP f.areacode 
WHERE 
    trunkname is not null and 
    (p.planname = f.planname or f.planname is null) 
GROUP BY f.destination_name,f.planname; 
Смежные вопросы