2016-10-14 1 views
0

У меня есть таблица РСУБД со столбцом BIGINT Тип и значения не являются последовательными. У меня есть Java-программа, где я хочу каждый поток, чтобы получить данные, как на PARTITION_SIZE т.е. я хочу пару значений столбцов, как после выполнения ORDER BY на результате,Возможно ли получить секционированные данные с использованием SQL?

Column_Value at Row 0 , Column_Value at Row `PARTITION_SIZE` 

Column_Value at Row `PARTITION_SIZE+1` , Column_Value at Row `2*PARTITION_SIZE` 

Column_Value at Row `2*PARTITION_SIZE+1` , Column_Value at Row `3*PARTITION_SIZE` 

В конце концов, я передам выше диапазонов значений в запросе выборки-х BETWEEN, чтобы получить разделенные данные для каждого потока.

В настоящее время я в состоянии сделать это разделение с помощью Java, поставив все значения в List (после получения всех значений из БД), а затем получить значение в этих конкретных показателях - {0,PARTITION_SIZE},{PARTITION_SIZE+1,2*PARTITION_SIZE} ..etc но проблема есть в том, что List мощи имеют миллионы записей и не рекомендуется хранить в памяти.

Так что мне было интересно, можно ли написать такой запрос с использованием самого SQL, который вернет мне те диапазоны, как внизу?

строк 1 -> minId, maxId

строка-2 -> minId, maxId

....

базы данных это DB2.

Например,

Для столбца таблицы значений 1,2,12,3,4,5,20,30,7,9,11, результат SQL запроса для размера в раздела = 2 должно быть {1,2},{3,4} ,{5,7},{9,11},{12,20},{30}.

+0

Могу ли я получить свой вопрос прямо - вы хотите получить данные из DB2 параллельно с использованием нескольких потоков. И вы спрашиваете, как вы можете выбрать строки для получения непересекающихся SELECT? – MichaelTiefenbacher

+0

Спасибо, что посмотрели. Я добавил пример на вопрос и да, я думаю, вы поняли это правильно. –

+0

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

ответ

1

В моих глазах функция mod() решила вашу проблему, и вы могли бы выбрать с ней динамическое количество разделов.

WITH numbered_rows_temp as ( 
SELECT rownumber() over() as rownum, 
     col1, 
     ... 
     coln 
    FROM table 
    ORDER BY col1) 

SELECT * FROM numbered_rows_temp 
    WHERE mod(rownum, <numberofpartitions>) = 0 

Заполните необходимые и измените результат от 0 до 1 в ваших запросах.

+0

, так что в основном с указанным выше запросом, если моя таблица имеет только один столбец '' D'of типа 'BIGINT', я бы получил конечные значения диапазона разделов в таблице' numbered_rows_temp', и я могу использовать '<= ID' для каждого идентификатора 'из таблицы' numbered_rows_temp' в SELECT sql моего потока? Я имею в виду, мне придется вычислять начальный индекс отдельно для каждого диапазона, но это нормально. –

+0

no - забудьте о диапазонах - в этом случае mod (modulo) выполняет расчет, и у вас есть два раздела, каждая нечетная строка будет в разделе 1, и каждая четная строка будет в разделе 2. – MichaelTiefenbacher

+0

Я не получал точных результатов, если Я передаю первый запрос как внутренний запрос вместо таблицы temp, но он работает правильно, если вместо выполнения 'ORDER BY col1' отдельно, я делаю' over (ORDER BY col1) ' –

1

Michael Tiefenbacher's answer, вероятно, более полезным, поскольку это позволяет избежать дополнительного запроса, но если вы хотите, чтобы определить диапазон идентификаторов, это может работать для вас:

WITH parms(partition_size) AS (VALUES 1000) -- or whatever 
SELECT 
    MIN(id), MAX(id), 
    INT(rn/parms.partition_size) partition_num 
FROM (
    SELECT id, ROW_NUMBER() OVER (ORDER BY id) rn 
    FROM yourtable 
) t , parms 
GROUP BY INT(rn/parms.partition_size) 
+0

Спасибо, вы тоже работаете и предлагает значения диапазона в одном и том же ряд. –

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