How to set same color for markers and lines in a m

2020-06-01 07:49发布

I have to plot multiple lines and markers with matplotlib by creating a loop and I have already set the axes color cycle in the matplolibrc param file. In each cycle of the loop a set of markers and lines are created (lines are created by a separate command). But the marker and line colors are different as per the axes color cycle. I want each time the loop is run the marker and lines to be of the same color of that cycle.

I have included the reproducible code:

import numpy as np
import itertools
import matplotlib.pyplot as plt
m = 5
n = 5
x = np.zeros(shape=(m, n))
plt.figure(figsize=(5.15, 5.15))
plt.clf()
plt.subplot(111)
marker = itertools.cycle(('o', 'v', '^', '<', '>', 's', '8', 'p'))
for i in range(1, n):
    x = np.dot(i, [1, 1.1, 1.2, 1.3])
    y = x ** 2
    plt.plot(x, y, linestyle='', markeredgecolor='none', marker=marker.next())
    plt.plot(x, y, linestyle='-')
plt.ylabel(r'\textit{y}', labelpad=6)
plt.xlabel(r'\textit{x}', labelpad=6)
plt.show()

Using this code the output I get is:

enter image description here

I need the markers and lines plotted in their range to be of the same color. How can it be done in matplotlib?

3条回答
老娘就宠你
2楼-- · 2020-06-01 08:10

Note that iter.next() was removed in Python 3.x as described in this question. If you run the examples in the accepted answer you will therefore receive AttributeError:

'itertools.cycle' object has no attribute 'next'

For both examples this can be solved by replacing:

marker=marker.next()

in plt.plot() with

marker=next(marker)
查看更多
够拽才男人
3楼-- · 2020-06-01 08:13

I present two ways. The first is probably cleaner: it loops through once, and within each loop, gets the next color, and then does two plotting commands with that color. In the second, it loops through and does all the markers and then it resets the colors and loops through again and does the lines.

first method

Directly access the color cycle. If matplotlib 1.5 or later use color=next(ax._get_lines.prop_cycler)['color']. Otherwise color=next(ax._get_lines.color_cycle):

import numpy as np
import itertools
import matplotlib.pyplot as plt
m = 5
n = 5
x = np.zeros(shape=(m, n))
plt.figure(figsize=(5.15, 5.15))
plt.clf()
plt.subplot(111)
marker = itertools.cycle(('o', 'v', '^', '<', '>', 's', '8', 'p'))

ax = plt.gca()
for i in range(1, n):
    x = np.dot(i, [1, 1.1, 1.2, 1.3])
    y = x ** 2
    #
    #for matplotlib before 1.5, use
    #color = next(ax._get_lines.color_cycle)
    #instead of next line (thanks to Jon Loveday for the update)
    #
    color = next(ax._get_lines.prop_cycler)['color']
    plt.plot(x, y, linestyle='', markeredgecolor='none', marker=marker.next(), color=color)
    plt.plot(x, y, linestyle='-', color = color)
plt.ylabel(r'$y$', labelpad=6)
plt.xlabel(r'$x$', labelpad=6)
plt.savefig('test2.png')

Also, notice I changed your \textit{y} to $y$. Usually you actually want math fonts rather than italics.

enter image description here

second method

If you don't want to send a color in as an argument, you can reset the color cycle and go through the loop twice. Here I reset it before the first loop and then again before the second loop just to make sure it's starting from the same place.

import numpy as np
import itertools
import matplotlib.pyplot as plt
m = 5
n = 5
x = np.zeros(shape=(m, n))
plt.figure(figsize=(5.15, 5.15))
plt.clf()
plt.subplot(111)
marker = itertools.cycle(('o', 'v', '^', '<', '>', 's', '8', 'p'))

plt.gca().set_prop_cycle(None) #if matplotlib <1.5 use set_color_cycle
for i in range(1, n):
    x = np.dot(i, [1, 1.1, 1.2, 1.3])
    y = x ** 2
    plt.plot(x, y, linestyle='', markeredgecolor='none', marker=marker.next())
plt.gca().set_prop_cycle(None)
for i in range(1, n):
    x = np.dot(i, [1, 1.1, 1.2, 1.3])
    y = x ** 2
    plt.plot(x, y, linestyle='-')
plt.ylabel(r'$y$', labelpad=6)
plt.xlabel(r'$x$', labelpad=6)
plt.savefig('test.png')

enter image description here

查看更多
做个烂人
4楼-- · 2020-06-01 08:29

Note that in matplotlib 1.5 onwards, color_cycle has been replaced by prop_cycler. The first option then needs:

color = next(ax._get_lines.prop_cycler)['color']
查看更多
登录 后发表回答