SQL - Создать количество категорий на основе заранее определенного количества разделений - PullRequest
1 голос
/ 04 августа 2020

Я использую BigQuery и пытаюсь присвоить категориальные значения каждой из моих записей в зависимости от количества назначенных ей «разделений».

В таблице есть совокупное количество записей, сгруппированных в Уровень STR - то есть, если есть 4 SKU на 2 STR, SKU будут помечены как 1,2,3,4. Каждому STR присваивается значение SPLIT, поэтому, если STR имеет значение SPLIT, равное 2, я хочу, чтобы он разделил свои SKU на 2 категории. Я хочу создать еще один столбец, который будет назначать SKU с меткой 1-2 как «1», а SKU с меткой 3-4 как «2». (Фактические данные имеют гораздо больший масштаб, но я подумал, что это будет проще.)

+-----+------+---------------+--------+
| STR | SKU  | SKU_ROW_COUNT | SPLITS |
+-----+------+---------------+--------+
|   1 | 1230 |             1 |      3 |
|   1 | 1231 |             2 |      3 |
|   1 | 1232 |             3 |      3 |
|   1 | 1233 |             4 |      3 |
|   1 | 1234 |             5 |      3 |
|   1 | 1235 |             6 |      3 |
|   2 | 1310 |             1 |      2 |
|   2 | 1311 |             2 |      2 |
|   2 | 1312 |             3 |      2 |
|   2 | 1313 |             4 |      2 |
|   3 | 2345 |             1 |      1 |
|   3 | 2346 |             2 |      1 |
|   3 | 2347 |             3 |      1 |
+-----+------+---------------+--------+

Столбец SPLITS - это динамический c, в диапазоне от 1 до 3. Количество SKU в каждой категории должны быть относительно равными, но это не столько приоритет, сколько количество создаваемых групп. В идеале итоговая таблица с новым столбцом (HOST_NUMBER) должна выглядеть примерно так:

+-----+------+---------------+--------+-------------+
| STR | SKU  | SKU_ROW_COUNT | SPLITS | HOST_NUMBER |
+-----+------+---------------+--------+-------------+
|   1 | 1230 |             1 |      3 |           1 |
|   1 | 1231 |             2 |      3 |           1 |
|   1 | 1232 |             3 |      3 |           2 |
|   1 | 1233 |             4 |      3 |           2 |
|   1 | 1234 |             5 |      3 |           3 |
|   1 | 1235 |             6 |      3 |           3 |
|   2 | 1310 |             1 |      2 |           1 |
|   2 | 1311 |             2 |      2 |           1 |
|   2 | 1312 |             3 |      2 |           2 |
|   2 | 1313 |             4 |      2 |           2 |
|   3 | 2345 |             1 |      1 |           1 |
|   3 | 2346 |             2 |      1 |           1 |
|   3 | 2347 |             3 |      1 |           1 |
+-----+------+---------------+--------+-------------+

Ответы [ 3 ]

0 голосов
/ 04 августа 2020

Если порядок значений в группах не имеет значения, просто используйте по модулю арифметики c:

select t.*, (SKU_ROW_COUNT % SPLITS) as split_group
from t
0 голосов
/ 04 августа 2020

Ниже для BigQuery Standard SQL

#standardSQL
SELECT *, 1 + MOD(SKU_ROW_COUNT, SPLITS) AS HOST_NUMBER 
FROM `project.dataset.table`
0 голосов
/ 04 августа 2020

Вы можете использовать оконные функции и арифметику:

select 
    t.*,
    1 + floor((sku_row_count - 1) * splits / count(*) over(partition by str)) host_number
from mytable t
order by sku

На самом деле, ntile(), похоже, делает именно то, что вы хотите - и вам даже не нужен столбец sku_row_count (который в основном имитирует row_number() в любом случае):

select 
    t.*,
    ntile(splits) over(partition by str order by sku) host_number
from mytable t
order by sku
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...