Создание графиков с разрывной осью в Python

Beginner

This tutorial is from open-source community. Access the source code

Введение

Визуализация данных часто представляет сложности при обработке выбросов. Эти экстремальные значения могут сжимать большинство ваших точек данных, затрудняя наблюдение важных закономерностей или деталей. График с разрывной осью представляет собой элегантное решение, "разрывая" ось для отображения разных диапазонов значений, что позволяет вам одновременно сосредоточиться как на основной распределении данных, так и на выбросах.

В этом руководстве мы научимся создавать график с разрывной осью с использованием библиотеки Matplotlib в Python. Этот метод особенно полезен при визуализации наборов данных с существенными различиями в значениях, что позволяет более ясно представить как обычные данные, так и экстремальные значения.

Советы по виртуальной машине

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

click-notebook

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

Если вы столкнетесь с какими-либо проблемами во время этого практического занятия, не стесняйтесь обращаться за помощью к Labby. Пожалуйста, оставьте отзыв после занятия, чтобы мы могли оперативно решить любые проблемы, с которыми вы столкнулись.

Подготовка среды и создание данных

На этом первом этапе мы настроим рабочую среду, импортировав необходимые библиотеки и создав примерные данные для визуализации. Мы сосредоточимся на создании данных, которые включают некоторые выбросы, что продемонстрирует полезность использования графика с разрывной осью.

Импорт необходимых библиотек

Начнем с импорта библиотек, необходимых для этого руководства. Мы будем использовать Matplotlib для создания визуализаций и NumPy для генерации и манипуляции числовыми данными.

Создайте новую ячейку в Jupyter Notebook и введите следующий код:

import matplotlib.pyplot as plt
import numpy as np

print(f"NumPy version: {np.__version__}")

При запуске этой ячейки вы должны увидеть вывод, похожий на следующий:

NumPy version: 2.0.0
numpy-version

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

Генерация примерных данных с выбросами

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

Создайте новую ячейку и добавьте следующий код:

## Установка случайного семени для воспроизводимости
np.random.seed(19680801)

## Генерация 30 случайных точек со значениями от 0 до 0.2
pts = np.random.rand(30) * 0.2

## Добавление 0.8 к двум определенным точкам для создания выбросов
pts[[3, 14]] += 0.8

## Отображение первых нескольких точек данных для понимания набора данных
print("First 10 data points:")
print(pts[:10])
print("\nData points containing outliers:")
print(pts[[3, 14]])

При запуске этой ячейки вы должны увидеть вывод, похожий на:

First 10 data points:
[0.01182225 0.11765474 0.07404329 0.91088185 0.10502995 0.11190702
 0.14047499 0.01060192 0.15226977 0.06145634]

Data points containing outliers:
[0.91088185 0.97360754]

В этом выводе вы можете четко видеть, что значения по индексам 3 и 14 намного больше, чем другие значения. Это наши выбросы. Большинство наших точек данных находятся ниже 0.2, но эти два выброса находятся выше 0.9, создавая значительную разницу в нашем наборе данных.

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

Создание и настройка графика с разрывной осью

На этом этапе мы создадим саму структуру графика с разрывной осью. График с разрывной осью состоит из нескольких подграфиков, которые показывают разные диапазоны одних и тех же данных. Мы настроим эти подграфики для эффективного отображения как основного набора данных, так и выбросов.

Создание подграфиков

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

Создайте новую ячейку в своем блокноте и добавьте следующий код:

## Создание двух подграфиков, расположенных вертикально с общей осью x
fig, (ax1, ax2) = plt.subplots(2, 1, sharex=True, figsize=(8, 6))

## Добавление общего заголовка к фигуре
fig.suptitle('Broken Axis Plot Example', fontsize=16)

## Построение одних и тех же данных на обеих осях
ax1.plot(pts, 'o-', color='blue')
ax2.plot(pts, 'o-', color='blue')

## Отображение фигуры с обоими подграфиками
plt.tight_layout()
plt.show()
broken-axis-plot

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

Настройка пределов оси Y

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

Создайте новую ячейку и добавьте следующий код:

## Создание двух подграфиков, расположенных вертикально с общей осью x
fig, (ax1, ax2) = plt.subplots(2, 1, sharex=True, figsize=(8, 6))

## Построение одних и тех же данных на обеих осях
ax1.plot(pts, 'o-', color='blue')
ax2.plot(pts, 'o-', color='blue')

## Установка пределов оси Y для каждого подграфика
ax1.set_ylim(0.78, 1.0)    ## Верхний подграфик показывает только выбросы
ax2.set_ylim(0, 0.22)      ## Нижний подграфик показывает только основные данные

## Добавление заголовка к каждому подграфику
ax1.set_title('Outlier Region')
ax2.set_title('Main Data Region')

## Отображение фигуры с настроенными пределами оси Y
plt.tight_layout()
plt.show()

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

Скрытие осей и настройка делений

Чтобы создать иллюзию "разрывной" оси, нам нужно скрыть соединяющие оси между двумя подграфиками и настроить положение делений.

Создайте новую ячейку и добавьте следующий код:

## Создание двух подграфиков, расположенных вертикально с общей осью x
fig, (ax1, ax2) = plt.subplots(2, 1, sharex=True, figsize=(8, 6))

## Построение одних и тех же данных на обеих осях
ax1.plot(pts, 'o-', color='blue')
ax2.plot(pts, 'o-', color='blue')

## Установка пределов оси Y для каждого подграфика
ax1.set_ylim(0.78, 1.0)    ## Верхний подграфик показывает только выбросы
ax2.set_ylim(0, 0.22)      ## Нижний подграфик показывает только основные данные

## Скрытие осей между ax1 и ax2
ax1.spines.bottom.set_visible(False)
ax2.spines.top.set_visible(False)

## Настройка положения делений
ax1.xaxis.tick_top()          ## Перемещение делений оси x вверх
ax1.tick_params(labeltop=False)  ## Скрытие подписей делений оси x сверху
ax2.xaxis.tick_bottom()       ## Оставление делений оси x снизу

## Добавление подписей к графику
ax2.set_xlabel('Data Point Index')
ax2.set_ylabel('Value')
ax1.set_ylabel('Value')

plt.tight_layout()
plt.show()

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

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

Добавление финальных штрихов к графику с разрывной осью

На этом последнем этапе мы добавим финальные штрихи к нашему графику с разрывной осью, чтобы было ясно, что ось Y разорвана. Мы добавим диагональные линии между подграфиками, чтобы показать разрыв, и улучшим общий вид графика с помощью правильных подписей и сетки.

Добавление диагональных линий разрыва

Для визуального обозначения разрыва оси мы добавим диагональные линии между двумя подграфиками. Это распространенная практика, которая помогает зрителям понять, что часть оси была опущена.

Создайте новую ячейку и добавьте следующий код:

## Создание двух подграфиков, расположенных вертикально с общей осью x
fig, (ax1, ax2) = plt.subplots(2, 1, sharex=True, figsize=(8, 6))

## Построение одних и тех же данных на обеих осях
ax1.plot(pts, 'o-', color='blue')
ax2.plot(pts, 'o-', color='blue')

## Установка пределов оси Y для каждого подграфика
ax1.set_ylim(0.78, 1.0)    ## Верхний подграфик показывает только выбросы
ax2.set_ylim(0, 0.22)      ## Нижний подграфик показывает только основные данные

## Скрытие осей между ax1 и ax2
ax1.spines.bottom.set_visible(False)
ax2.spines.top.set_visible(False)

## Настройка положения делений
ax1.xaxis.tick_top()          ## Перемещение делений оси x вверх
ax1.tick_params(labeltop=False)  ## Скрытие подписей делений оси x сверху
ax2.xaxis.tick_bottom()       ## Оставление делений оси x снизу

## Добавление диагональных линий разрыва
d = 0.5  ## пропорция вертикального и горизонтального размера наклонной линии
kwargs = dict(marker=[(-1, -d), (1, d)], markersize=12,
              linestyle='none', color='k', mec='k', mew=1, clip_on=False)
ax1.plot([0, 1], [0, 0], transform=ax1.transAxes, **kwargs)
ax2.plot([0, 1], [1, 1], transform=ax2.transAxes, **kwargs)

## Добавление подписей и заголовка
ax2.set_xlabel('Data Point Index')
ax2.set_ylabel('Value')
ax1.set_ylabel('Value')
fig.suptitle('Dataset with Outliers', fontsize=16)

## Добавление сетки к обоим подграфикам для лучшей читаемости
ax1.grid(True, linestyle='--', alpha=0.7)
ax2.grid(True, linestyle='--', alpha=0.7)

plt.tight_layout()
plt.subplots_adjust(hspace=0.1)  ## Настройка расстояния между подграфиками
plt.show()

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

Понимание графика с разрывной осью

Давайте немного разберемся в ключевых компонентах нашего графика с разрывной осью:

  1. Два подграфика: Мы создали два отдельных подграфика, каждый из которых сосредоточен на разном диапазоне значений оси Y.
  2. Скрытые оси: Мы скрыли соединяющие оси между подграфиками, чтобы создать визуальное разделение.
  3. Диагональные линии разрыва: Мы добавили диагональные линии, чтобы показать, что ось разорвана.
  4. Предельные значения оси Y: Мы установили разные предельные значения оси Y для каждого подграфика, чтобы сосредоточиться на определенных частях данных.
  5. Сетка: Мы добавили сетку, чтобы улучшить читаемость и облегчить оценку значений.

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

Эксперименты с графиком

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

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

## Создание двух подграфиков, расположенных вертикально с общей осью x
fig, (ax1, ax2) = plt.subplots(2, 1, sharex=True, figsize=(8, 6))

## Построение одних и тех же данных на обеих осях с разными стилями
ax1.plot(pts, 'o-', color='darkblue', label='Data Points', linewidth=2)
ax2.plot(pts, 'o-', color='darkblue', linewidth=2)

## Отметка выбросов другим цветом
outlier_indices = [3, 14]
ax1.plot(outlier_indices, pts[outlier_indices], 'ro', markersize=8, label='Outliers')

## Установка пределов оси Y для каждого подграфика
ax1.set_ylim(0.78, 1.0)    ## Верхний подграфик показывает только выбросы
ax2.set_ylim(0, 0.22)      ## Нижний подграфик показывает только основные данные

## Скрытие осей между ax1 и ax2
ax1.spines.bottom.set_visible(False)
ax2.spines.top.set_visible(False)

## Настройка положения делений
ax1.xaxis.tick_top()          ## Перемещение делений оси x вверх
ax1.tick_params(labeltop=False)  ## Скрытие подписей делений оси x сверху
ax2.xaxis.tick_bottom()       ## Оставление делений оси x снизу

## Добавление диагональных линий разрыва
d = 0.5  ## пропорция вертикального и горизонтального размера наклонной линии
kwargs = dict(marker=[(-1, -d), (1, d)], markersize=12,
              linestyle='none', color='k', mec='k', mew=1, clip_on=False)
ax1.plot([0, 1], [0, 0], transform=ax1.transAxes, **kwargs)
ax2.plot([0, 1], [1, 1], transform=ax2.transAxes, **kwargs)

## Добавление подписей и заголовка
ax2.set_xlabel('Data Point Index')
ax2.set_ylabel('Value')
ax1.set_ylabel('Value')
fig.suptitle('Dataset with Outliers - Enhanced Visualization', fontsize=16)

## Добавление сетки к обоим подграфикам для лучшей читаемости
ax1.grid(True, linestyle='--', alpha=0.7)
ax2.grid(True, linestyle='--', alpha=0.7)

## Добавление легенды к верхнему подграфику
ax1.legend(loc='upper right')

plt.tight_layout()
plt.subplots_adjust(hspace=0.1)  ## Настройка расстояния между подграфиками
plt.show()

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

Поздравляем! Вы успешно создали график с разрывной осью на Python с использованием Matplotlib. Эта техника поможет вам создавать более эффективные визуализации при работе с данными, содержащими выбросы.

Резюме

В этом руководстве вы узнали, как создать график с разрывной осью с использованием библиотеки Matplotlib в Python. Эта техника визуализации очень ценна при работе с данными, содержащими выбросы, так как позволяет ясно отобразить как основное распределение данных, так и выбросы на одной фигуре.

Вот краткий обзор того, что вы достигли:

  1. Настройка среды и создание данных: Вы импортировали необходимые библиотеки и создали пример данных, содержащих выбросы, чтобы продемонстрировать концепцию.

  2. Создание базовой структуры графика: Вы создали два подграфика с разными пределами оси Y, чтобы сосредоточиться на разных диапазонах значений, и настроили внешний вид осей.

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

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

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