Metrika

28 ноября 2011 г.

Сегментирование данных в SSAS

Статья о сегментировании (кластеризации) данных с помощью SQL Server Analytsys Services на примере сегментирования  пользователей он-лайн шутера PointBlank.

Что такое сегментирование (кластеризация). 
Сегментирование - это группировка данных по некоторым признакам. Например есть пользователи, они играют часто или редко, платят мало или много. Т.е. есть два измерения, по которым бьются пользователи, в каждом измерении два значения, т.е. возможно сделать 4 сегмента. В принципе при маленьком количестве измерений специальных средств для построения сегментов можно и не использовать, определить сегменты можно с помощью OLAP-кубов или с помощью SQL-запросов к базе. Но, если измерений много, то разбить данные на сегменты становиться довольно сложно и необходимо применять специальные алгоритмы сегментирования.

Для чего нужно сегментирование.
Сегментирование нужно для более качественного и глубокого исследования данных, например разбиение пользователей на сегменты в игре, может показать какие люди играют в игру, чего они хотят от игры, что им нравиться, а что нет. Далее можно определять сегменты пользователей раз в какой-то промежуток времени и изучать переходы пользователей из одних сегментов в другие. Например, если были определены сегменты пользователей "Новички", "Платящие", "Неактивные", можно определять, кто переходит из сегмента "Новички" в "Платящие", такую информацию можно использовать например в маркетинговых кампаниях для определения наиболее эффективных каналов привлечения пользователей. Изучая переходы из сегмента "Платящие" в "Неактивные", можно определять недостатки в сервисе, можно привести какие-либо акции по возвращению "Неактивных" в "Платящие" и т.д.

Этапы большого пути.
Для начала надо создать таблицу с данными, на основе которых будут строиться сегменты. В принципе, если данных не много, можно использовать вьюху. В таблице должен быть primary key, по которому можно идентифицировать пользователя и поля, которые содержат необходимые параметры пользователей.
Для примера я создам сегменты на основе таблицы с небольшим количеством параметров. На самом деле выбор правильных параметров для анализа само по себе является не простой задачей, и нужно быть готовым, что таблица с исходными данными в процессе построения сегментов может часто менять свою структуру и часто пересчитываться. Например с одной стороны можно решить, что параметр "количество убийств" хорошо характеризует успешность игрока, но на самом деле один игрок может набить 100 убийств за 3 матча, а другой за 10, более подходящий аргумент - количество убийств за матч и т.д.
Создаю таблицу:
create table _dm_test(
    user_id int not null primary key,
    perc_win_per_match int null,            -- Процент побед к матчам
    perc_kill_per_death int null,            -- Процент фрагов к смертям
    kill_per_match int null,                -- Фраги за матч
    perc_headshot_per_kill int null,        -- Процент хедшотов к фрагам
    connecttime_min int null,                -- Продолжительность сессий
    match_per_play_day int null,            -- Количество матчей за игровой день
    days_of_play int not null,                -- Количество игровых дней за месяц
    days_created int null,                    -- Возраст персонажа в днях
    rank_current int not null,                -- Текущее звание игрока
    rank_range varchar(100) null            -- Диапазоны званий
)
Агрегирую в нее данные за последние 7 игровых дней за 30 календарных дней.

Затем в BI Studio создаю проект Analysis Services Project. В проекте создаю DataSource и DataView, который содержит таблицу _dm_test.
После этого в проекте тыкаю правой кнопкой на Mining Structures и выбираю New Mining Structure:
  




Таблица _dm_test выбирается как Case для модели. Nested - используется в более сложных случаях анализа, например для учета покупок пользователей, более подробно можно почитать в книге
Далее проставляем для колонок, как они будут использоваться в модели:

Далее для колонок проставляем Content Type - это то как данные из колонки будут распределяться в модели по кластерам, например Continuous будут показаны в виде распределения вокруг среднего значения (имеет смысл, когда данные в колонке изменяются в широком диапазоне величин и довольно равномерно), Discrete - дискретизация будет взята из таблицы (имеет смысл, когда необходимо разбить данные самому, без участия алгоритма разбиения на сегменты), Discretized - данные будут разбиты на диапазоны алгоритмом построения сегментов. В данном примере Rank Range я предопределил в таблице, поэтому ставлю ему Discrete, остальным данным, кроме User Id, ставлю Discretized:

 Выбираем процент данных, которые будут использоваться для проверки построенной модели:

 Последняя страница создания модели - ввод имен структуры и модели:

 Окно редактирования Mining Structure будет иметь такой вид:

Окно редактирования модели:
 Здесь можно более подробно выставить параметры для обработки модели. Например на изображении сверху я для аргумента Connecttime Min выставляю количество диапазонов (DiscretizationBucketCount =10), на которые его будет разбивать модель (по умолчанию 5). Так же можно поменять Content Type.
Так же для полей можно выбрать то, как они будут участвовать в построении сегментов. Все поля со значением Input будут участвовать в алгоритме, Ignore - не будут участвовать вообще, Predict - используется в алгоритмах предсказания для того, что бы использовать аргумент и на входе алгоритма и на выходе, в построении кластеров его роль не ясна, PredictOnly - для алгоритма кластеризации данные будут просто распределены по кластерам, но в самом разбиении участвовать не будут. В моем случае, я не хочу чтобы поле Rank Current участвовало в разбиении, а поле Rank Range должно быть просто распределено по кластерам:

В этом же окне можно уточнить параметры алгоритма, для этого надо выделить заголовок модели и в свойствах перейти в AlgorithmParameters:
 У меня параметров модели не много, поэтому ограничу количество кластеров (сегментов) пятью - значение CLUSTER_COUNT = 5 (по умолчанию 10):

Далее процессим модель, тойже кнопкой, что и процессим кубы:

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

Так же тут видны связи между сегментами (черные линии). Слева бегунком можно отфильтровать более сильные или слабые связи. На подсветку кластеров влияют выпадающие списки Shading Variable и State. На изображении сверху видно, что 32% пользователей попали в Кластер 1 (проценты отображаются в контроле Density), а на изображении снизу, видно, что большинство тех, у кого процент побед за матч больше 70 попали в Кластер 3:

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

После нескольких итераций я подобрал наиболее удовлетворяющие меня параметры, теперь для более удобной работы можно переименовать кластеры, для этого нужно тыкнуть на заголовке кластера правой кнопкой мыши и выбрать Rename Cluster:



После всех настроек кластеры стали выглядеть вот так:

Что дальше?
Просто разбить данные на кластеры не достаточно, их надо как то использовать. Как минимум надо понять, кто в какой кластер попал. Для этого нужно создать SSIS пакет, который пропустит данные из исходной таблицы через модель и выдаст их в результирующую таблицу.
Создаю в BI Studio проект Integration Services Project, перетаскиваю в Control Flow элемент Data Mining Query Task:

Двойным кликом перехожу в его Editor:
 На вкладке Mining model нажимаю кнопку New, что бы создать новое подключение к SSAS. В списке провайдеров надо выбирать Microsoft OLE DB Provider for Analysis Services, провайдер ... for Data Mining Services у меня не заработал:

В выпадающем списке Initial catalog выбираю модель:
В итоге модель появляется в списке Mining models:
Далее переходим во вкладку Query, где пишеться DMX-запрос к модели или строиться через мастер (кнопка Build New Query):
Тут нужно определить Mining Model, через которую пропускаются данные; Input Table, которая содержит данные, в моем случае я использую ту же таблицу; и внизу формы нужно выбрать поля и/или Prediction Functions, которые будут выведены в результирующую таблицу, мне нужно выбрать кластер и ID пользователя.
После этого во вкладке Query появиться DMX-запрос:
Далее переходим во вкладку Output и выбираем там результирующую таблицу:

Все. После этого запускаем пакет и в таблице _dm_test_out у нас будет связаны ID пользователя и названия кластеров.

Полезные ссылки
2. Так же советую книгу "Программируем коллективный разум" Тоби Сегаран - просто великолепная книга про глубокий анализ данных;
3. Статья о датамайнинге в он-лайн игре Айон:  http://habrahabr.ru/blogs/data_mining/134163/