Как сделать точечный график с пустыми кругами в Python?

166

В Python с Matplotlib, как можно построить график рассеяния с пустыми кругами? Цель состоит в том, чтобы нарисовать пустые круги вокруг некоторых цветных дисков, которые уже нанесены scatter(), чтобы выделить их, в идеале, без необходимости перерисовывать цветные круги.

Я пытался facecolors=None, но безрезультатно.

Эрик О Лебиго
источник
1
Люди, которые хотят нарисовать пустые / полые диаграммы рассеяния разных цветов, могут посмотреть на этот вопрос .
Важное значение

Ответы:

242

Из документации по скаттеру:

Optional kwargs control the Collection properties; in particular:

    edgecolors:
        The string none to plot faces with no outlines
    facecolors:
        The string none to plot unfilled outlines

Попробуйте следующее:

import matplotlib.pyplot as plt 
import numpy as np 

x = np.random.randn(60) 
y = np.random.randn(60)

plt.scatter(x, y, s=80, facecolors='none', edgecolors='r')
plt.show()

пример изображения

Примечание: для других типов графиков см. Этот пост по использованию markeredgecolorи markerfacecolor.

Гари Керр
источник
4
Спасибо! Гвоздь в том, что более обычный (в Python) facecolors=Noneне работает, что меня смутило.
Эрик О Лебиго
24
Очень полезно. Это так markerfacecolor='none', как сейчас.
hesham_EE
2
У меня был мой стиль matplotlib, который устанавливал ширину ребер на ноль. Если вы не видите маркеров, markerfacecolor='none'попробуйте добавитьmarkeredgewidth=1.0
oLas
Этот подход также можно использовать в Seaborn после выполнения стандартного импорта Matplotlib %matplotlib inlineи import matplotlib.pyplot as plt, а затем установки import seaborn as sns; sns.set()
Jakob
68

Будет ли это работать?

plt.scatter(np.random.randn(100), np.random.randn(100), facecolors='none')

пример изображения

или используя plot ()

plt.plot(np.random.randn(100), np.random.randn(100), 'o', mfc='none')

пример изображения

Гекхан Север
источник
3
это полезно, когда вы используете plotвместоscatter
Тревор Бойд Смит
2
Для scatter, вам нужно указать, edgecolorsкак edgecolors='r'. В противном случае круги исчезают. Смотрите здесь
T_T
14

Вот еще один способ: это добавляет круг к текущим осям, графику или изображению или что-то еще

from matplotlib.patches import Circle  # $matplotlib/patches.py

def circle( xy, radius, color="lightsteelblue", facecolor="none", alpha=1, ax=None ):
    """ add a circle to ax= or current axes
    """
        # from .../pylab_examples/ellipse_demo.py
    e = Circle( xy=xy, radius=radius )
    if ax is None:
        ax = pl.gca()  # ax = subplot( 1,1,1 )
    ax.add_artist(e)
    e.set_clip_box(ax.bbox)
    e.set_edgecolor( color )
    e.set_facecolor( facecolor )  # "none" not None
    e.set_alpha( alpha )

альтернативный текст

(Круги на картинке сжимаются до эллипсов, потому что imshow aspect="auto").

Денис
источник
5

В matplotlib 2.0 есть параметр, fillstyle который позволяет лучше контролировать заполнение маркеров. В моем случае я использовал его с errorbars , но это работает для маркеров вообще http://matplotlib.org/api/_as_gen/matplotlib.axes.Axes.errorbar.html

fillstyleпринимает следующие значения: ['full' | «левый» | «правильно» | «дно» | «верх» | 'никто']

Есть две важные вещи , которые нужно иметь в виду при использовании fillstyle,

1) Если для mfc установлено любое значение, оно будет иметь приоритет, следовательно, если вы установили для fillstyle значение «none», оно не будет действовать. Поэтому избегайте использования mfc в сочетании с fillstyle

2) Возможно, вы захотите контролировать ширину края маркера (используя markeredgewidthили mew), потому что, если маркер относительно мал, а ширина края толстая, маркеры будут выглядеть как заполненные, даже если это не так.

Ниже приведен пример использования панелей ошибок:

myplot.errorbar(x=myXval, y=myYval, yerr=myYerrVal, fmt='o', fillstyle='none', ecolor='blue',  mec='blue')
Сальваторе Косентино
источник
2

Основываясь на примере Гэри Керра и, как предлагается здесь, можно создать пустые кружки, связанные с указанными значениями, с помощью следующего кода:

import matplotlib.pyplot as plt 
import numpy as np 
from matplotlib.markers import MarkerStyle

x = np.random.randn(60) 
y = np.random.randn(60)
z = np.random.randn(60)

g=plt.scatter(x, y, s=80, c=z)
g.set_facecolor('none')
plt.colorbar()
plt.show()
Aroc
источник
Это по сути сложная версия принятого ответа ...
Эрик О Лебиго
С моей точки зрения это не так. Использование точечной диаграммы с цветами не означает, что внутри команды facecolor = "none". Для этого необходимо последующее удаление цвета лица, как описано в данной ссылке. К сожалению, это комплексное решение необходимо для удаления цвета лица на точечных диаграммах с помощью цветовой кодировки.
Aroc
Подход в этом ответе действительно полезен, если кто-то хочет обновить график, который изначально не содержит пустых кружков. Тем не менее, вопрос о создании этих кругов напрямую, поэтому принятым решением является путь, так как он делает то же самое, что и этот ответ, но напрямую, без постороннего обновления первого графика.
Эрик О Лебиго
Эта «сложная версия» сработала для меня, когда встраивание аргумента в .scatter()не сработало. Для контекста я также применял карту цветов ( c=z, cmap='jet').
Андрей Сильвер
1

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

Другой вариант - не использовать scatter и рисовать патчи по отдельности с помощью команды circle / ellipse. Они находятся в matplotlib.patches, вот пример кода о том, как рисовать круги прямоугольниками и т. Д.

whatnick
источник