2010-12-14 2 views
2

У меня есть две таблицы: Статус (status_id, DESC1, DESC2, DESC3, desc4) Status_Level (status_level_id, убывание, levelD, УРОВНЕЙ)Большой некрасиво SQL запрос проблема

Соединение по desc1..4 filed in Status и desc в Status_Level. Мне нужно выбрать status_id, levelD и levelS, где levelD и levelS - самые высокие уровни всех четырех descs.

Я попытался это:

SELECT Status.status_id, MAX(levelS) AS ds_column, MAX(levelD) AS ss_column 
FROM Status, Status_level WHERE 
Status_level.desc=Status.desc1 OR 
Status_level.desc=Status.desc2 OR 
Status_level.desc=Status.desc3 OR 
Status_level.desc=Status.desc4 
GROUP BY Status.status_id 

My SQL очень ржавый, так что любая помощь будет принята с благодарностью. Спасибо.

редактировать: пример:

Status: 
----------------------------------------------------------- 
| 1 | ABC_LEVEL_1 | DEF_LEVEL_5| CBA_LEVEL_2 | ABC_LEVEL_4| 
----------------------------------------------------------- 
| 2 | ABC_LEVEL_1 | DEF_LEVEL_1| CBA_LEVEL_2 | ABC_LEVEL_1| 
----------------------------------------------------------- 
| 3 | ABC_LEVEL_4 | DEF_LEVEL_1| CBA_LEVEL_2 | ABC_LEVEL_4| 
----------------------------------------------------------- 

Status_Level: 
--------------------------- 
| 1 | ABC_LEVEL_1 | 1 | 7 | 
--------------------------- 
| 1 | DEF_LEVEL_5 | 5 | 6 | 
--------------------------- 
| 1 | CBA_LEVEL_2 | 2 | 3 | 
--------------------------- 
| 1 | ABC_LEVEL_4 | 4 | 5 | 
--------------------------- 
| 1 | DEF_LEVEL_1 | 1 | 2 | 

Desired output: 

------------- 
| 1 | 5 | 7 | <- 5 from DEF_LEVEL_5 and 7 from ABC_LEVEL_1 
------------- 
| 2 | 2 | 7 | <- 2 from CBA_LEVEL_2 and 7 from ABC_LEVEL_1 
------------- 
| 3 | 4 | 5 | <- 4 from ABC_LEVEL_4 and 5 from ABC_LEVEL_4 
------------- 
+1

некоторых примеры входные данные и ожидаемые выходные данные помогут объяснить проблему. –

+0

Слушайте услышать. Не могли бы вы разместить только пару подходящих строк из каждого стола? – 5arx

+0

Хорошо, я отредактировал мое сообщение. Надеюсь, это понятно. – Klark

ответ

2
SELECT Status.status_id, MAX(levelS) AS ds_column, MAX(levelD) AS ss_column 
FROM Status, Status_level WHERE 
Status_level.desc in (Status.desc1, Status.desc2, Status.desc3, Status.desc4) 
GROUP BY Status.status_id 
+0

Нравится. +1. Преподавал мне рассмотрение использования 'in', а не' = 'в заявлении о соединении. Модифицированный пример подключения к ANSI ниже для объяснения этого. –

+0

Вот и все. Большое спасибо :) – Klark

1

Я не уверен, если это будет работать в Access, а также, но я уверен, что это должно дать правильные результаты:

SELECT status_id, max(levelS) as ds_column, max(levelD) as ss_column 
FROM (
    SELECT s.status_id, sl.levelS, sl.levelD 
    FROM Status s 
    INNER JOIN Status_level sl ON s.desc1 = sl.desc 
UNION ALL 
    SELECT s.status_id, sl.levelS, sl.levelD 
    FROM Status s 
    INNER JOIN Status_level sl ON s.desc2 = sl.desc 
UNION ALL 
    SELECT s.status_id, sl.levelS, sl.levelD 
    FROM Status s 
    INNER JOIN Status_level sl ON s.desc3 = sl.desc 
UNION ALL 
    SELECT s.status_id, sl.levelS, sl.levelD 
    FROM Status s 
    INNER JOIN Status_level sl ON s.desc4 = sl.desc 
) ssl 
GROUP BY status_id 
2

Как насчет:

SELECT t.status_id, Max(Status_Level.levelD) AS MaxOflevelD, 
     Max(Status_Level.levelS) AS MaxOflevelS 
FROM Status_Level INNER JOIN (SELECT s.status_id, s.desc1 As [Desc] 
FROM status s 
UNION ALL 
SELECT s.status_id, s.desc2 As [Desc] 
FROM status s 
UNION ALL 
SELECT s.status_id, s.desc3 As [Desc] 
FROM status s 
UNION ALL 
SELECT s.status_id, s.desc4 As [Desc] 
FROM status s) AS t ON Status_Level.desc = t.Desc 
GROUP BY t.status_id; 
1

Это будет работать (с моей издевались до примере ниже):

select S.status_id, max(levelD), max(levelS) 
from @status s 
inner join @Status_Level sl1 on sl1.[desc] in (s.desc1,s.desc2,s.desc3,s.desc4) 
group by status_id 

Вот полный макете, который вы можете вставить в окно редактора запросов:

declare @status table (status_id int, desc1 varchar(20), desc2 varchar(20), desc3 varchar(20), desc4 varchar(20)) 
declare @Status_Level table (status_level_id int, [desc]varchar(20), levelD int, levelS int) 

insert into @status values(1, 'ABC_LEVEL_1','DEF_LEVEL_5','CBA_LEVEL_2','ABC_LEVEL_4') 
insert into @status values(2, 'ABC_LEVEL_1','DEF_LEVEL_1','CBA_LEVEL_2','ABC_LEVEL_1') 
insert into @status values(3, 'ABC_LEVEL_4','DEF_LEVEL_1','CBA_LEVEL_2','ABC_LEVEL_4') 

insert into @Status_Level values(1, 'ABC_LEVEL_1',1,7) 
insert into @Status_Level values(1, 'DEF_LEVEL_5',5,6) 
insert into @Status_Level values(1, 'CBA_LEVEL_2',2,3) 
insert into @Status_Level values(1, 'ABC_LEVEL_4',4,5) 
insert into @Status_Level values(1, 'DEF_LEVEL_1',1,2) 

--The select statement 
select S.status_id, max(levelD), max(levelS) 
from @status s 
inner join @Status_Level sl1 on sl1.[desc] in (s.desc1,s.desc2,s.desc3,s.desc4) 
group by status_id 
+0

Это не доступ MS. – Fionnuala

3

Если вы можете создать these функции, то вы можете сделать:

SELECT Status.status_id, 
     MaxOfList(l1.levelD,l2.levelD,l3.levelD,l4.levelD) AS ds_column, 
     MaxOfList(l1.levelS,l2.levelS,l3.levelS,l4.levelS) AS ss_column 
FROM Status s, Status_level l1, Status_level l2, Status_level l3, Status_level l4 
WHERE l1.desc=s.desc1 AND l2.desc=s.desc2 
     AND l3.desc=s.desc3 AND l4.desc=s.desc4; 

Обратите внимание, что я предполагаю, что null не допускается в desc1-4

+0

Очень редко рекомендуется использовать UDF, когда существует правильный прямой SQL. – Fionnuala

+0

@Remou согласился. Большинство СУБД имеют «наибольший» и «наименьший», но не доступ. Я оставляю этот ответ как любопытство. – 2010-12-15 06:59:18

2

Сначала вы нормализуете эту таблицу состояния с помощью UNION, а затем вы делаете группу с максимальными значениями.

select status_id, max(levelid), max(levels) from ( 
select * from status_level, status where desc = desc1 
union 
select * from status_level, status where desc = desc2 
union 
select * from status_level, status where desc = desc3 
union 
select * from status_level, status where desc = desc4) 
group by status_id; 

Здесь весь тестовый скрипт и выход

create table status (status_id number, desc1 varchar2(50), desc2 varchar2(50), desc3 varchar2(50), desc4 varchar2(50)); 

    create table status_level (status_level_id number, descx varchar2(50), levelid number, levels number); 

    insert into status values (1,'ABC_LEVEL_1','DEF_LEVEL_5','CBA_LEVEL_2','ABC_LEVEL_4'); 
    insert into status values (2,'ABC_LEVEL_1','DEF_LEVEL_1','CBA_LEVEL_2','ABC_LEVEL_1'); 
    insert into status values (3,'ABC_LEVEL_4','DEF_LEVEL_1','CBA_LEVEL_2','ABC_LEVEL_4'); 

    insert into status_level values (1,'ABC_LEVEL_1',1,7); 
    insert into status_level values (1,'DEF_LEVEL_5',5,6); 
    insert into status_level values (1,'CBA_LEVEL_2',2,3); 
    insert into status_level values (1,'ABC_LEVEL_4',4,5); 
    insert into status_level values (1,'DEF_LEVEL_1',1,2); 

    commit; 

    select * from status; 

    select * from status_level; 

    select * from status, status_level where descx = desc1 
    union 
    select * from status, status_level where descx = desc2 
    union 
    select * from status, status_level where descx = desc3 
    union 
    select * from status, status_level where descx = desc4; 


    select status_id, max(levelid), max(levels) from (
    select * from status_level, status where descx = desc1 
    union 
    select * from status_level, status where descx = desc2 
    union 
    select * from status_level, status where descx = desc3 
    union 
    select * from status_level, status where descx = desc4) 
    group by status_id; 

    Table created. 
    Table created. 
    1 row created. 
    1 row created. 
    1 row created. 
    1 row created. 
    1 row created. 
    1 row created. 
    1 row created. 
    1 row created. 
    Commit complete. 

    STATUS_ID DESC1            DESC2            DESC3            DESC4            
    ---------- -------------------------------------------------- -------------------------------------------------- -------------------------------------------------- -------------------------------------------------- 
      1 ABC_LEVEL_1          DEF_LEVEL_5          CBA_LEVEL_2          ABC_LEVEL_4          
      2 ABC_LEVEL_1          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_1          
      3 ABC_LEVEL_4          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_4          


    3 rows selected. 

    STATUS_LEVEL_ID DESCX             LEVELID  LEVELS 
    --------------- -------------------------------------------------- ---------- ---------- 
        1 ABC_LEVEL_1             1   7 
        1 DEF_LEVEL_5             5   6 
        1 CBA_LEVEL_2             2   3 
        1 ABC_LEVEL_4             4   5 
        1 DEF_LEVEL_1             1   2 


    5 rows selected. 

    STATUS_ID DESC1            DESC2            DESC3            DESC4            STATUS_LEVEL_ID DESCX             LEVELID  LEVELS 
    ---------- -------------------------------------------------- -------------------------------------------------- -------------------------------------------------- -------------------------------------------------- --------------- -------------------------------------------------- ---------- ---------- 
      1 ABC_LEVEL_1          DEF_LEVEL_5          CBA_LEVEL_2          ABC_LEVEL_4              1 ABC_LEVEL_1             1   7 
      1 ABC_LEVEL_1          DEF_LEVEL_5          CBA_LEVEL_2          ABC_LEVEL_4              1 ABC_LEVEL_4             4   5 
      1 ABC_LEVEL_1          DEF_LEVEL_5          CBA_LEVEL_2          ABC_LEVEL_4              1 CBA_LEVEL_2             2   3 
      1 ABC_LEVEL_1          DEF_LEVEL_5          CBA_LEVEL_2          ABC_LEVEL_4              1 DEF_LEVEL_5             5   6 
      2 ABC_LEVEL_1          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_1              1 ABC_LEVEL_1             1   7 
      2 ABC_LEVEL_1          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_1              1 CBA_LEVEL_2             2   3 
      2 ABC_LEVEL_1          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_1              1 DEF_LEVEL_1             1   2 
      3 ABC_LEVEL_4          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_4              1 ABC_LEVEL_4             4   5 
      3 ABC_LEVEL_4          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_4              1 CBA_LEVEL_2             2   3 
      3 ABC_LEVEL_4          DEF_LEVEL_1          CBA_LEVEL_2          ABC_LEVEL_4              1 DEF_LEVEL_1             1   2 


    10 rows selected. 

    STATUS_ID MAX(LEVELID) MAX(LEVELS) 
    ---------- ------------ ----------- 
      1   5   7 
      2   2   7 
      3   4   5 


    3 rows selected. 
+0

Это не похоже на MS Access для меня. – Fionnuala

+0

:-) Я этого не замечал. Спасибо за подсказку. Но он также должен работать на MSAccess. Позвольте мне проверить это. Может быть, мне нужно удалить этот ответ. – hol

+0

в порядке. Я создал таблицы в доступе и запустил sql. все еще работает одинаково. – hol

Смежные вопросы