Всем привет! Сегодняшний пост напрямую связан с языком представления слабоструктурированных данных XML (extensible Markup Language). Думаю, многие из вас так или иначе сталкивались с ним в своей практике. Однако, далеко не все знакомы с XSLT - языком преобразования XML-документов. Он позволяет создавать новые файлы на основе предложенного XML-документа. Причем результирующие документы могут иметь самые разные форматы. С помощью XSLT можно решать достаточно большой класс задач. Одни из наиболее распространенных - это создание отчетов, например в формате HTML, или преобразование документа из одной XML схемы в другую. Сегодня мы займемся менее типичной для XSLT задачей. Наша цель: на основе результатов поисковых запросов к Yandex API, представленных в XML-формате, создать веб-страницу, на которой представлен небольшой статистический анализ произведенных запросов. Этот пример должен продемонстрировать основные возможности языка XSLT.
В июле этого года консорциум всемирной паутины объявил о появлении на свет версии 3.0 языка XSLT. Однако, для решения наших задач я использовал долгие годы применяемую всеми версию 2.0. Принцип работы с XSLT заключается в написании таблице стилей, в которой нужно описать правила преобразования документа XML. Всю остальную работу выполняет процессор XSLT. Я использовал наиболее полный процессор таблиц стилей под названием Saxon.
Перечислим несколько основных идей, заложенных в XSLT:
При обработке документа процессор XSLT использует следующую логику:
В одном из своих учебных проектов мне были необходимы результаты поисковых запросов для названий книг. В датасете были десятки тысяч экземпляров, что достаточно усложнило задачу, так как многие хорошие поисковые системы предоставляют очень ограничивающие лимиты на количество запросов в своем API. Например, Google позволяет сделать только 100 бесплатных запросов в сутки.
Тем не менее среди достаточно жестких в этом плане заморских движков, нашелся наш любимый Яндекс, который предоставляет возможность делать поисковый запросы с ограничением в 10 тыс в день. Такой вариант меня вполне устроил. Что важно для нас, результаты запроса Яндекс API возвращает в формате XML. Ниже пример ответа на запрос yandex (некоторые элементы удалены).
Небольшую часть собранных данных я использую для демонстрации возможностей XSLT.
Прежде чем переходить к анализу необходимо подготовить XML-документ, с которым мы будем работать. При загрузке данных из Яндекса, я сохранял результаты в отдельные XML файлы. Для того, чтобы нам было удобно анализировать все результаты в общем, нужно объединить их в один документ. Для этого напишем нашу первую таблицу стилей XSLT.
Любая таблица стилей должна начинаться с тега <xsl:stylesheet>, в ней мы определяем версию XSLT и пространство имен. В теге <xsl:output> указываем формат выходного файла, и то, что теги будут автоматически форматироваться с учетом иерархии (indent). Далее следует единственный в этой таблице шаблон, который применяется к корню документа. В выходном документе корнем будет тег <queries>. Его дочерними элементами будет содержимое XML-документов из папки queries, которые обходятся в цикле for-each.
Я проведу простейший анализ, которого хватит чтобы понять, что из себя представляют полученные данные. В качестве изучения рассмотрим количество результатов, которые обнаружила поисковая система в ответ на запрос.
Для подсчета среднего выборочного сначала рассчитаем сумму полученных результатов во всех запросах:
Для того, чтобы обращаться к конкретным элементам XML-документа в XSLT используется язык запросов XPath. Символ / обозначает переход к дочернему элементу, квадратные скобки - альтернатива ключевому слову where, а с помощью символа @ происходит доступ к атрибутам элемента. Далее посчитаем количество запросов:
И наконец выведем в HTML документе результат:
Результат получился достаточно большим. Однако, зачастую среднее выборочное - не самая репрезентативная статистика. Давайте посмотрим насколько велик разброс в наших данных.
Посчитаем минимум и максимум нашей выборки. Для этого в XSLT также есть встроенные функции:
Вместе с полученными значениями выведем в результирующий документ текст самих запросов. Для этого создадим еще один шаблон (все предыдущие преобразования располагались в корневом шаблоне). Кроме того в шаблоне можно указывать параметры.
Для вывода больших чисел в удобочитаемом виде, применим функцию format-number:
Как видите, разброс в имеющихся данных колоссальный. Теперь представим наши данные в чуть большем объеме и в графическом виде.
Просто отобразим на графике пять самых популярных и непопулярных на ответы запросов. Для этого я использовал JavaScript библиотеку amcharts. Все что необходимо, это заполнить свойство dataProvider парами ключ-значение.
Элемент <xsl:choose> позволяет создавать логику условий с множественным выбором. Функция translate поможет не испортить JavaScript код в случае, если в тексте запроса содержатся двойные кавычки. Посмотрим на результат:
Различия в количестве результатов настолько велики, что понять, сколько на самом деле ответов у малопопулярных запросов, можно только наведя курсор на запрос. Теперь представим наши разнородные данные в полном объеме.
Выбросами называются данные, которые выбиваются из общей выборки. Судя по предыдущему графику, можно предположить, что в нашем датасете таких выбросов может быть довольно много. Для представления всех данных на одном графике и выделения при этом выбросов воспользуемся Box-Plot графиком. На нем отображаются медиана, верхний и нижний квартили, минимальное и максимальное значение выборки (без учета выбросов). Кроме того, красными точками на графике указаны умеренные выбросы, а синими - экстремальные. Для демонстрации Box-Plot графика я также исопльзовал готовую библиотеку - Plotly JS. Все, что нужно: заполнить массив данными и передать его в конструктор:
На первый взгляд даже трудно понять, что это действительно Box-Plot график. Однако, если смаштабировать график до нужного размера, то мы увидим следующую картину: Box-Plot график только подтвердил, что датасет содержит очень разнородные результаты.
В этом посте мы познакомились с такой технологией как XSLT. Мы решали достаточно нетипичную задачу с ее помощью, и, конечно, есть более удобные инструменты для анализа данных. Тем не менее XSLT - очень мощный движок, который позволяет решать многие проблемы, связанные с преобразованием XML-документов.
Written on October 15th, 2017 by Alexey Kalina