Получить значения между диапазонами - PullRequest
3 голосов
/ 20 декабря 2011

Чем больше я думаю об этом, тем больше я запутался, может быть потому, что довольно давно я писал какой-то сложный sql.

У меня есть таблица с диапазоном значений. Давайте назовем это диапазоном:

RANGE
RANGE_ID   RANGE_SEQ   MIN   MAX  FACTOR
       1           1     0    10       1
       1           2    11   100     1.5
       1           3   101           2.5
       2           1     0    18       1
       2           2    19             2

И у меня есть другая таблица, которая использует эти диапазоны. Давайте назовем это приложение

APPLICATION
APP_ID   RAW_VALUE  RANGE_ID   FINAL_VALUE
     1         20.0       1          30.0     /*In Range 1, 20 falls between 11 and 100, so 1.5 is applied)*/
     2         25.0       2          50.0
     3         18.5       2          18.5  

Я хочу получить те RAW_VALUES, которые попадают между диапазонами. Таким образом, для диапазона 2 я хочу, чтобы те APP_ID s имели RAW_VALUE между 18 и 19. Точно так же для диапазона 1 я хочу, чтобы те APP_ID s имели RAW_VALUE между 10 и 11 и 100 и 101.

Я хочу знать, возможно ли это с помощью SQL, и несколько советов о том, что я могу попробовать. Мне не нужен сам sql, только несколько указателей на подход.

Ответы [ 3 ]

1 голос
/ 20 декабря 2011
create table tq84_range (
  range_id   number not null,
  range_seq  number not null,
  min_       number not null,
  max_       number,
  factor     number not null,
--
  primary key (range_id, range_seq)
);

insert into tq84_range values (1, 1,  0,  10, 1.0);
insert into tq84_range values (1, 2, 10, 100, 1.5);
insert into tq84_range values (1, 3,101,null, 2.5);

insert into tq84_range values (2, 1,  0,  18, 1.0);
insert into tq84_range values (2, 2, 19,null, 2.0);

create table tq84_application (
  app_id     number not null,
  raw_value  number not null,
  range_id   number not null,
  primary key (app_id)
);

insert into tq84_application values (1, 20.0, 1);
insert into tq84_application values (2, 25.0, 2);
insert into tq84_application values (3, 18.5, 2);

Вы хотите использовать left join.

При таком левом соединении вы гарантируете, что каждая запись левого таблица (таблица, появляющаяся до left join в выберите текст выписки) будет возвращен как минимум один раз, хотя условие where не находит запись в правой таблице.

Если tq84_range.range is null, то вы знаете, что соединение условие не нашел запись в tq84_range, следовательно, там похоже на пробел. Итак, вы печатаете Missing:.

Так как tq84_application.max_ может быть null и NULL отображается в укажите бесконечность или верхняя граница вы проверяете верхний предел с nvl(tq84_range.max_, tq84_application.raw_value

Таким образом, оператор select станет примерно таким:

select 
       case when tq84_range.range_id is null then 'Missing: ' 
            else                                  '         '
            end,
       tq84_application.raw_value
  from 
       tq84_application       left join
       tq84_range 
    on
       tq84_application.range_id = tq84_range.range_id 
   and
       tq84_application.raw_value between
       tq84_range.min_ and nvl(tq84_range.max_, tq84_application.raw_value);
1 голос
/ 20 декабря 2011

Попробуйте, чтобы приблизить вас

select app_id,raw_value,aa.range_id,raw_value * xx.factor as FinaL_Value
from Application_table  aa
join range_table xx on (aa.raw_value between xx.min and xx.max)
                  and (aa.range_id=xx.range_id)

Чтобы получить несоответствия (т. Е. Raw_values, которых нет в таблице), попробуйте это

select app_id,raw_value,aa.range_id
from Application_table  aa
left join range_table xx on (aa.raw_value between xx.min and xx.max)
                  and (aa.range_id=xx.range_id)
where xx.range_id is null
0 голосов
/ 20 декабря 2011

Насколько я понимаю, вы говорите, что хотите получить результаты только из таблицы приложения, которые не укладываются ни в один диапазон?Это, например, вернуло бы только строку для app_id = 3 (мои собственные имена столбцов и предположить реальные минимальные и максимальные суммы):

select *
from   APP1 A
where  not exists
         (select null
          from   RANGE1 R
          where  R.RANGE_ID = A.RANGE_ID and A.RAW_VALUE between nvl(R.MINNUM, 0) and nvl(R.MAXNUM, 999999));

Но, конечно, это не будет возвращать факторколичество, поскольку оно не соответствует ни одной строке в таблице диапазонов, так почему же результат для app_id = 3 в приведенном выше примере совпадает с фактором = 1?Если ваш столбец raw_value будет десятичным, то я ожидаю, что диапазоны тоже будут десятичными.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...