在Matplotlib中重置颜色循环

8on*_*ne6 50 python matplotlib pandas

假设我有3种交易策略的数据,每种策略都有交易成本.我想在相同的轴上绘制6个变体中每个变量的时间序列(3个策略*2个交易成本).我想"与交易成本"线与绘制alpha=1,并linewidth=1同时我想"无交易成本"与绘制alpha=0.25linewidth=5.但我希望每个策略的两个版本的颜色都相同.

我想要的是:

fig, ax = plt.subplots(1, 1, figsize=(10, 10))

for c in with_transaction_frame.columns:
    ax.plot(with_transaction_frame[c], label=c, alpha=1, linewidth=1)

****SOME MAGIC GOES HERE TO RESET THE COLOR CYCLE

for c in no_transaction_frame.columns:
    ax.plot(no_transaction_frame[c], label=c, alpha=0.25, linewidth=5)

ax.legend()
Run Code Online (Sandbox Code Playgroud)

什么是适当的代码放在指示的行上来重置颜色循环,以便在调用第二个循环时"回到开始"?

pel*_*son 68

您可以使用Axes.set_color_cycle将颜色周期重置为原始颜色.查看代码,有一个功能来完成实际工作:

def set_color_cycle(self, clist=None):
    if clist is None:
        clist = rcParams['axes.color_cycle']
    self.color_cycle = itertools.cycle(clist
Run Code Online (Sandbox Code Playgroud)

Axes上使用它的方法:

def set_color_cycle(self, clist):
    """
    Set the color cycle for any future plot commands on this Axes.

    *clist* is a list of mpl color specifiers.
    """
    self._get_lines.set_color_cycle(clist)
    self._get_patches_for_fill.set_color_cycle(clist)
Run Code Online (Sandbox Code Playgroud)

这基本上意味着您可以使用None作为唯一参数调用set_color_cycle,它将替换为rcParams ['axes.color_cycle']中的默认循环.

我用以下代码尝试了这个并获得了预期的结果:

import matplotlib.pyplot as plt
import numpy as np

for i in range(3):
    plt.plot(np.arange(10) + i)

# for Matplotlib version < 1.5
plt.gca().set_color_cycle(None)
# for Matplotlib version >= 1.5
plt.gca().set_prop_cycle(None)

for i in range(3):
    plt.plot(np.arange(10, 1, -1) + i)

plt.show()
Run Code Online (Sandbox Code Playgroud)

代码输出,显示颜色循环重置功能

  • 从Matplotlib 1.5.0开始,`set_color_cycle`已被弃用,不再接受'None`了!幸运的是,新的(更广泛的)替代`set_prop_cycle`*确实*接受`无'仍然...... (18认同)
  • 将 set_prop_cycle 设置为 None 也可以摆脱标签。有没有办法只重置颜色?plt.gca().set_prop_cycle(color=None) 似乎不起作用。 (2认同)

Ram*_*uet 23

正如@pelson给出的答案所使用的set_color_cycle并且在Matplotlib 1.5中不推荐使用,我认为使用set_prop_cycle以下方法获得其解决方案的更新版本会很有用:

import matplotlib.pyplot as plt
import numpy as np

for i in range(3):
    plt.plot(np.arange(10) + i)

plt.gca().set_prop_cycle(None)

for i in range(3):
    plt.plot(np.arange(10, 0, -1) + i)

plt.show()
Run Code Online (Sandbox Code Playgroud)

还请注意我必须np.arange(10,1,-1)改为np.arange(10,0,-1).前者只提供了9个元素.这可能源于使用不同的Numpy版本.我的是1.10.2.

编辑:删除了使用的需要rcParams.感谢@divenex在评论中指出这一点.

  • 与此答案中所述的相反,`plt.gca().set_prop_cycle(None)` 适用于 Matplotlib 1.5(如@burnpanck 所指出的),我刚刚验证它也适用于 Matplotlib 2.0。 (2认同)

mwa*_*kom 5

既然你提到你正在使用seaborn,我建议你做的是:

with sns.color_palette(n_colors=3):

    ax.plot(...)
    ax.plot(...)
Run Code Online (Sandbox Code Playgroud)

这将设置调色板以使用当前活动的颜色循环,但仅使用前三种颜色.它也是您想要设置临时颜色循环的通用解决方案.

需要注意的是,实际上需要是下唯一with块是无论你正在做的创建Axes对象(也就是plt.subplots,fig.add_subplot()等).这只是因为matplotlib颜色循环本身的工作原理.

做你特别想要的,"重置"颜色循环是可能的,但它是一个黑客,我不会在任何类型的生产代码中.但是,在这里,它是如何发生的:

f, ax = plt.subplots()
ax.plot(np.random.randn(10, 3))
ax._get_lines.color_cycle = itertools.cycle(sns.color_palette())
ax.plot(np.random.randn(10, 3), lw=5, alpha=.25)
Run Code Online (Sandbox Code Playgroud)

在此输入图像描述