(python matplotlib) Как изменить цвет каждого леденца на палочке (ax.stem) - PullRequest
0 голосов
/ 08 октября 2018

Я использую ax.stem, чтобы нарисовать леденец в Python.Однако мне было трудно назначить разные цвета для каждого леденца , как показано здесь

Как вы можете видеть, у меня есть 2 категории "GWP" и "FDP".В моем проекте каждую категорию следует разделить на 4 подкатегории «ингредиент», «отходы», «энергия» и «инфраструктура».Поэтому я хочу назначить им разные цвета для обозначения подкатегории.

Здесь предлагается решение: https://python -graph-gallery.com / 181-custom-lollipop-plot /

Но это только научит вас, какизменить цвет для всех леденцов.

И есть другое решение: https://python -graph-gallery.com / 183-highlight-a-group-lollipop /

Но это недействительно не используйте ax.stem.

Пожалуйста, дайте мне знать, как назначать разные цвета для каждого леденца.

(Кроме того, я не знаю, почему мой график отображается вверх ногами.Кроме того, ось y не выровнена по порядку, и есть одна точка, не соединенная линией. Хотя она правильно отображается на моем исходном графике.)

Вот мой код:

#%%
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt

plt.style.use('ggplot')


# my dataset
columns = np.array(['types', 'GWP100 (year)', 'FDP (year)'])


types = np.array(['Total (ingredient) per kg', 'Total (waste) per kg',
       'energy (whole process) per kg', 'Infrastructure', 'Total (Total)']).reshape(5,1)
gwp = np.array([  2.86982617e+02,   2.16824983e+02,   4.38920760e+01,
         6.02400000e-02,   5.47759916e+02]).reshape(5,1)
fdp = np.array([  1.35455867e+02,   7.02868322e+00,   1.26622560e+01,
         1.64568000e-02,   1.55163263e+02]).reshape(5,1)

original_data = np.concatenate((types, gwp, fdp), axis = 1)




# produce dataframe
data = pd.DataFrame(original_data, columns = columns)

#                           types GWP100 (year)  FDP (year)
#0      Total (ingredient) per kg    286.982617  135.455867
#1           Total (waste) per kg    216.824983  7.02868322
#2  energy (whole process) per kg     43.892076   12.662256
#3                 Infrastructure       0.06024   0.0164568
#4                  Total (Total)    547.759916  155.163263


#%%  graph
fig = plt.figure(1, figsize =(8,6))

# 1st subplot
ax1 = fig.add_subplot(1,2,1)
gwp = data[data.columns[1]]

ax1.stem(gwp)
ax1.set_ylabel(r'kg CO$_2$-Eq', fontsize=10)
ax1.set_xlabel('GWP', fontsize=10)


# 2nd subplot
ax2 = fig.add_subplot(1,2,2)
fdp = data[data.columns[2]]

ax2.stem(fdp)
ax2.set_ylabel(r'kg oil-Eq', fontsize = 10)
ax2.set_xlabel('FDP', fontsize=10)

Ответы [ 2 ]

0 голосов
/ 08 октября 2018

stem в настоящее время состоит из пары линий и «линии», состоящей из точек сверху.Он не имеет возможности раскрасить линии отдельно в своем интерфейсе.

Вы можете повторить график ствола, чтобы нарисовать линии вручную нужным цветом.

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt

columns = np.array(['types', 'GWP100 (year)', 'FDP (year)'])
types = np.array(['Total (ingredient) per kg', 'Total (waste) per kg',
       'energy (whole process) per kg', 'Infrastructure', 'Total (Total)'])
gwp = np.array([  2.86982617e+02,   2.16824983e+02,   4.38920760e+01,
         6.02400000e-02,   5.47759916e+02])
fdp = np.array([  1.35455867e+02,   7.02868322e+00,   1.26622560e+01,
         1.64568000e-02,   1.55163263e+02])

# produce dataframe
data = pd.DataFrame([types,gwp,fdp], index = columns).transpose()

colors = list("bgryk")

fig, (ax, ax2) = plt.subplots(ncols=2)

for t, y, c in zip(data["types"], data["GWP100 (year)"],colors):
    ax.plot([t,t], [0,y], color=c, marker="o", markevery=(1,2))
ax.set_ylim(0,None)
plt.setp(ax.get_xticklabels(), rotation=90)
fig.tight_layout()    
plt.show()

enter image description here

Более эффективныйРешение, конечно, заключается в использовании LineCollection в сочетании с точечной диаграммой для точек.

fig, (ax, ax2) = plt.subplots(ncols=2)

segs = np.zeros((len(data), 2, 2))
segs[:,:,0] = np.repeat(np.arange(len(data)),2).reshape(len(data),2) 
segs[:,1,1] = data["GWP100 (year)"].values

lc = LineCollection(segs, colors=colors)
ax.add_collection(lc)
ax.scatter(np.arange(len(data)), data["GWP100 (year)"].values, c=colors)
ax.set_xticks(np.arange(len(data)))
ax.set_xticklabels(data["types"], rotation=90)
ax.autoscale()
ax.set_ylim(0,None)
fig.tight_layout()
plt.show()
0 голосов
/ 08 октября 2018

Я отвечу на один из ваших основных вопросов, касающихся одинаковой окраски линий и маркеров в отношении категории.Кажется, нет прямой опции при вызове ax1.stem() для указания списка цветов согласно официальным документам.На самом деле они говорят, что получающийся в результате сюжет может быть не разумным, если так поступить.Тем не менее, ниже приведен один трюк, чтобы все было сделано по-своему.

Идея заключается в следующем:

  • Получить объекты (stemline), отображаемые в подзаговоре
  • Получить данные xy маркеров
  • Зациклить данные и изменить цвет каждого стволовой линии .Нанесите маркер по отдельности тем же цветом, что и ствол .colors - это массив, определяющий цвета по вашему выбору.

Ниже приведена соответствующая часть кода:

# 1st subplot
ax1 = fig.add_subplot(1,2,1)
gwp = data[data.columns[1]]

colors = ['r', 'g', 'b', 'y', 'k']
_, stemlines, _ = ax1.stem(gwp)

line = ax1.get_lines()
xd = line[0].get_xdata()
yd = line[0].get_ydata()

# mec and mfc stands for markeredgecolor and markerfacecolor
for i in range(len(stemlines)):
    plt.plot([xd[i]], [yd[i]], 'o', ms=7, mfc=colors[i], mec=colors[i])
    plt.setp(stemlines[i], 'color', colors[i])

ax1.set_ylabel(r'kg CO$_2$-Eq', fontsize=10)
ax1.set_xlabel('GWP', fontsize=10)


# 2nd subplot
ax2 = fig.add_subplot(1,2,2)
fdp = data[data.columns[2]]

_, stemlines, _ = ax2.stem(fdp)

line = ax2.get_lines()
xd = line[0].get_xdata()
yd = line[0].get_ydata()

for i in range(len(stemlines)):
    plt.plot([xd[i]], [yd[i]], 'o', ms=7, mfc=colors[i], mec=colors[i])
    plt.setp(stemlines[i], 'color', colors[i])

enter image description here

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...