Точечные графики: scatter()

Точечные графики: scatter() Matplotlib / Seaborn

Привет! Линейные графики хороши для показа трендов, но что, если нужно увидеть, как связаны две переменные? Или найти выбросы? Для этого есть точечные графики (scatter plots) — один из самых мощных инструментов визуализации данных.

В этой статье мы разберём:

  • Что такое точечный график и зачем он нужен
  • Как строить графики с помощью scatter()
  • Настройка цвета, размера и прозрачности точек
  • Использование цветовой шкалы для третьей переменной
  • Сравнение scatter() и plot()

Что нужно знать перед началом

Для этого урока тебе понадобится:

  • Установленный Matplotlib (pip install matplotlib)
  • Базовое понимание графиков из предыдущих статей
  • Желание находить связи в данных

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

Основная часть

Простой точечный график

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

# Данные
x = np.random.rand(50) * 10
y = np.random.rand(50) * 10

# Создаём точечный график
plt.scatter(x, y)
plt.title('Простой точечный график')
plt.xlabel('X')
plt.ylabel('Y')
plt.grid(True, alpha=0.3)
plt.show()

Совет: scatter() отображает каждую пару значений (x, y) как отдельную точку. Это помогает увидеть скопления и пустоты в данных.

Разница между plot() и scatter()

plot()scatter()
Соединяет точки линиямиОтображает отдельные точки
Каждая точка — одна параКаждая точка — одна пара
Не настраивается размер точекМожно настраивать размер точек
Ограниченные возможности по цветуМожно задавать цвет для каждой точки
# Сравнение
x = np.linspace(0, 10, 20)
y = np.sin(x)

fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(10, 4))

# plot() — линии между точками
ax1.plot(x, y, marker='o')
ax1.set_title('plot() с маркерами')
ax1.grid(True, alpha=0.3)

# scatter() — только точки
ax2.scatter(x, y)
ax2.set_title('scatter()')
ax2.grid(True, alpha=0.3)

plt.tight_layout()
plt.show()

Совет: scatter() лучше подходит для визуализации распределения данных. plot() — для трендов и временных рядов.

Настройка внешнего вида точек

Размер точек (s)

x = np.random.rand(30) * 10
y = np.random.rand(30) * 10

# Разные размеры точек
plt.scatter(x, y, s=100)      # Большие
plt.scatter(x + 0.5, y + 0.5, s=20)   # Маленькие
plt.title('Разный размер точек')
plt.show()

Цвет точек (c)

plt.scatter(x, y, c='red')
plt.scatter(x + 0.5, y + 0.5, c='blue')
plt.title('Разный цвет точек')
plt.show()

Прозрачность (alpha)

plt.scatter(x, y, alpha=0.5)
plt.title('Полупрозрачные точки')
plt.show()

Цвет контура (edgecolors)

plt.scatter(x, y, s=100, facecolors='none', edgecolors='blue', linewidths=2)
plt.title('Точки с контуром')
plt.show()

Совет: Прозрачность (alpha) помогает видеть перекрывающиеся точки. Чем больше точек, тем меньше должна быть прозрачность.

Цветовая шкала для третьей переменной

Одна из самых мощных возможностей scatter() — кодировать третью переменную цветом:

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

n = 100
x = np.random.rand(n) * 10
y = np.random.rand(n) * 10
colors = np.random.rand(n) * 100  # Третья переменная

plt.scatter(x, y, c=colors, cmap='viridis', s=50, alpha=0.7)
plt.colorbar(label='Третья переменная')
plt.title('Точечный график с цветовой шкалой')
plt.xlabel('X')
plt.ylabel('Y')
plt.grid(True, alpha=0.3)
plt.show()

Другие популярные цветовые схемы (cmap):

НазваниеОписание
'viridis'От зелёного к синему (по умолчанию)
'plasma'От фиолетового к жёлтому
'inferno'От чёрного к жёлтому
'coolwarm'От синего к красному через белый
'RdBu'От красного к синему

Совет: Цветовая шкала позволяет визуализировать до 4 измерений на одном графике: x, y, размер (s) и цвет (c).

Размер точек для четвёртой переменной

Можно использовать размер точек для ещё одной переменной:

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

n = 50
x = np.random.rand(n) * 10
y = np.random.rand(n) * 10
colors = np.random.rand(n) * 100
sizes = np.random.rand(n) * 500 + 50

plt.scatter(x, y, c=colors, s=sizes, cmap='plasma', alpha=0.6)
plt.colorbar(label='Цветовая переменная')
plt.title('Цвет и размер кодируют две дополнительные переменные')
plt.xlabel('X')
plt.ylabel('Y')
plt.grid(True, alpha=0.3)
plt.show()

Совет: Использование размера и цвета на одном графике может сделать его перегруженным. Используй эту технику аккуратно.

Практический пример: корреляция между признаками

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

# Данные о продажах и рекламных затратах
ad_spend = np.random.randint(1, 50, 30) * 1000
sales = ad_spend * 2 + np.random.randint(-5000, 5000, 30)

plt.figure(figsize=(8, 6))
plt.scatter(ad_spend, sales, s=80, alpha=0.7, color='#2E86C1', edgecolors='black', linewidths=1)

# Добавляем линию тренда (позже в статье)
z = np.polyfit(ad_spend, sales, 1)
p = np.poly1d(z)
plt.plot(ad_spend, p(ad_spend), color='red', linewidth=2, label='Линия тренда')

plt.title('Зависимость продаж от рекламных затрат', fontsize=14, fontweight='bold')
plt.xlabel('Рекламные затраты (руб.)', fontsize=12)
plt.ylabel('Продажи (руб.)', fontsize=12)
plt.grid(True, alpha=0.3)
plt.legend()
plt.tight_layout()
plt.show()

# Выводим корреляцию
correlation = np.corrcoef(ad_spend, sales)[0, 1]
print(f"Коэффициент корреляции Пирсона: {correlation:.3f}")

Совет: Корреляция близкая к 1 говорит о сильной положительной связи, близкая к -1 — об отрицательной. Близкая к 0 — связи нет.

Визуализация кластеров

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

# Создаём три кластера точек
cluster1 = np.random.randn(30, 2) + [2, 2]
cluster2 = np.random.randn(30, 2) + [8, 3]
cluster3 = np.random.randn(30, 2) + [5, 8]

plt.figure(figsize=(8, 6))
plt.scatter(cluster1[:, 0], cluster1[:, 1], label='Кластер 1', s=60, alpha=0.7)
plt.scatter(cluster2[:, 0], cluster2[:, 1], label='Кластер 2', s=60, alpha=0.7)
plt.scatter(cluster3[:, 0], cluster3[:, 1], label='Кластер 3', s=60, alpha=0.7)

plt.title('Визуализация трёх кластеров', fontsize=14, fontweight='bold')
plt.xlabel('Признак 1', fontsize=12)
plt.ylabel('Признак 2', fontsize=12)
plt.legend()
plt.grid(True, alpha=0.3)
plt.tight_layout()
plt.show()

Точечный график с подписями точек

import matplotlib.pyplot as plt

# Данные с названиями
points = {
    'A': (1, 10),
    'B': (2, 15),
    'C': (3, 8),
    'D': (4, 20),
    'E': (5, 12)
}

x = [points[p][0] for p in points]
y = [points[p][1] for p in points]
labels = list(points.keys())

plt.figure(figsize=(6, 5))
plt.scatter(x, y, s=80, color='blue')

# Добавляем подписи
for i, label in enumerate(labels):
    plt.annotate(label, (x[i], y[i]), xytext=(5, 5), textcoords='offset points')

plt.title('Точечный график с подписями')
plt.grid(True, alpha=0.3)
plt.show()

Совет: Подписи полезны, когда точек немного и важно показать названия объектов.

Полный пример: анализ данных о жилье

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

# Создаём данные о квартирах
n = 100
area = np.random.randint(30, 120, n)
price = area * 5000 + np.random.randint(-50000, 50000, n)
rooms = np.random.randint(1, 5, n)
floor = np.random.randint(1, 20, n)

fig, axes = plt.subplots(2, 2, figsize=(12, 10))

# 1. Цена vs Площадь
axes[0, 0].scatter(area, price, s=60, alpha=0.6, color='blue')
axes[0, 0].set_title('Цена vs Площадь')
axes[0, 0].set_xlabel('Площадь (м²)')
axes[0, 0].set_ylabel('Цена (руб.)')
axes[0, 0].grid(True, alpha=0.3)

# 2. Цена vs Площадь (цвет = этаж)
scatter = axes[0, 1].scatter(area, price, c=floor, s=60, alpha=0.6, cmap='plasma')
axes[0, 1].set_title('Цена vs Площадь (цвет = этаж)')
axes[0, 1].set_xlabel('Площадь (м²)')
axes[0, 1].set_ylabel('Цена (руб.)')
axes[0, 1].grid(True, alpha=0.3)
plt.colorbar(scatter, ax=axes[0, 1], label='Этаж')

# 3. Цена vs Площадь (размер = комнаты)
scatter = axes[1, 0].scatter(area, price, c='green', s=rooms * 80, alpha=0.6)
axes[1, 0].set_title('Цена vs Площадь (размер = комнаты)')
axes[1, 0].set_xlabel('Площадь (м²)')
axes[1, 0].set_ylabel('Цена (руб.)')
axes[1, 0].grid(True, alpha=0.3)

# 4. Комнаты vs Площадь
axes[1, 1].scatter(rooms, area, s=60, alpha=0.6, color='purple')
axes[1, 1].set_title('Комнаты vs Площадь')
axes[1, 1].set_xlabel('Количество комнат')
axes[1, 1].set_ylabel('Площадь (м²)')
axes[1, 1].grid(True, alpha=0.3)

plt.tight_layout()
plt.show()

scatter() с непрозрачностью для больших данных

import matplotlib.pyplot as plt
import numpy as np

np.random.seed(42)

# Генерируем 1000 точек
n = 1000
x = np.random.randn(n) * 10
y = np.random.randn(n) * 10

plt.figure(figsize=(8, 6))
plt.scatter(x, y, s=10, alpha=0.3)
plt.title('1000 точек с низкой непрозрачностью')
plt.grid(True, alpha=0.3)
plt.show()

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

Задачи для закрепления

Задача 1. Создай точечный график для случайных 30 точек.

Задача 2. Добавь на график синие точки размером 50.

Задача 3. Используй цветовую шкалу для третьей переменной.

Задача 4. Сделай точки полупрозрачными (alpha=0.5).

Задача 5. Построй scatter plot для визуализации корреляции между двумя переменными.

Ответы:

Задача 1.

x = np.random.rand(30) * 10
y = np.random.rand(30) * 10
plt.scatter(x, y)
plt.show()

Задача 2.

plt.scatter(x, y, color='blue', s=50)

Задача 3.

colors = np.random.rand(30) * 100
plt.scatter(x, y, c=colors, cmap='viridis')
plt.colorbar()
plt.show()

Задача 4.

plt.scatter(x, y, alpha=0.5)

Задача 5.

x = np.random.rand(50) * 10
y = x * 2 + np.random.randn(50) * 2
plt.scatter(x, y)
plt.show()

Нюансы и подводные камни

Сравнение scatter() и plot() по производительности

scatter() может быть медленнее для очень большого количества точек (более 10000). В таких случаях используй plot() с маркерами:

# Для 10000+ точек
plt.plot(x, y, 'o', markersize=3, alpha=0.5)

Цветовая шкала и значения

Цветовая шкала автоматически подстраивается под диапазон значений c. Если нужно зафиксировать диапазон, используй vmin и vmax:

plt.scatter(x, y, c=values, vmin=0, vmax=100, cmap='viridis')

Частые ошибки и как их избежать

Ошибка 1: Неправильная размерность массивов

# Ошибка: x и y разной длины
plt.scatter([1, 2, 3], [1, 2])

# Правильно: одинаковые длины
plt.scatter([1, 2, 3], [1, 2, 3])

Ошибка 2: Путаница между plot() и scatter()

# plot() соединяет точки линиями
plt.plot(x, y)

# scatter() показывает точки
plt.scatter(x, y)

Ошибка 3: Забыл plt.colorbar() для цветовой шкалы

# Цветовая шкала не отображается
plt.scatter(x, y, c=colors)

# Добавляем шкалу
plt.scatter(x, y, c=colors)
plt.colorbar()

Шпаргалка

Что нужноКак пишется
Базовый scatterplt.scatter(x, y)
Размер точекs=50
Цвет точекc='red'
Прозрачностьalpha=0.5
Цветовая шкалаcmap='viridis' и plt.colorbar()
Контур точекedgecolors='black', linewidths=1
Пустые точкиfacecolors='none'
Фиксированный диапазон цветовvmin=0, vmax=100

Заключение

Сегодня мы научились:

  • Строить точечные графики с помощью scatter()
  • Настраивать цвет, размер и прозрачность точек
  • Использовать цветовую шкалу для третьей переменной
  • Визуализировать корреляции и кластеры
  • Сравнивать scatter() и plot()

КВИЗ

Что дальше?

Оцените статью
IMI-DS - PYTHON LERNEN
Содержание
Оглавление ×