Create over 20 unique legend colors using matplotlib

I draw 20 different lines in one plot using matplotlib. I use a for loop to build and label each line with my key, and then use the legend function

for key in dict.keys(): plot(x,dict[key], label = key) graph.legend() 

But using this method, the graph repeats many colors in the legend. Is there a way to ensure that each line is assigned a unique color using matplotlib and more than 20 lines?

thank

+23
python matplotlib legend
Dec 05 2018-11-12T00:
source share
2 answers

The answer to your question is related to two other SO questions.

Answer to How to choose a new color for each plotted line in a shape in matplotlib? explains how to define a default color list, choose the next color for the plot. This is done using the Axes.set_color_cycle method.

You want the right list of colors, although this is easiest to do using a color map, as explained in the answer to this question: Create a color generator from the given color map in matplotlib . There, the color map takes a value from 0 to 1 and returns the color.

So, for your 20 lines, you want to cycle from 0 to 1 in increments of 1/20. In particular, you want to cycle the form from 0 to 19/20, because 1 maps back to 0.

This is done in this example:

 import matplotlib.pyplot as plt import numpy as np NUM_COLORS = 20 cm = plt.get_cmap('gist_rainbow') fig = plt.figure() ax = fig.add_subplot(111) ax.set_color_cycle([cm(1.*i/NUM_COLORS) for i in range(NUM_COLORS)]) for i in range(NUM_COLORS): ax.plot(np.arange(10)*(i+1)) fig.savefig('moreColors.png') plt.show() 

This is the result:

Yosemitebear Mountain Giant Double Rainbow 1-8-10

Alternative, better (debatable) solution:

There is an alternative way to use the ScalarMappable object to convert a range of values โ€‹โ€‹into colors. The advantage of this method is that you can use non-linear Normalization to convert from the row index to the actual color. The following code gives the exact same result:

 import matplotlib.pyplot as plt import matplotlib.cm as mplcm import matplotlib.colors as colors import numpy as np NUM_COLORS = 20 cm = plt.get_cmap('gist_rainbow') cNorm = colors.Normalize(vmin=0, vmax=NUM_COLORS-1) scalarMap = mplcm.ScalarMappable(norm=cNorm, cmap=cm) fig = plt.figure() ax = fig.add_subplot(111) # old way: #ax.set_color_cycle([cm(1.*i/NUM_COLORS) for i in range(NUM_COLORS)]) # new way: ax.set_color_cycle([scalarMap.to_rgba(i) for i in range(NUM_COLORS)]) for i in range(NUM_COLORS): ax.plot(np.arange(10)*(i+1)) fig.savefig('moreColors.png') plt.show() 
+61
Dec 05 '11 at 20:29
source share

I had a plot with 12 lines, and it was difficult for me to distinguish lines with similar colors when I tried the Yann method. My lines were also displayed in pairs, so I used the same color for two lines in each pair and used two different line widths. You can also change the line style to get more combinations.

You can use set_prop_cycle() , but I just changed the line objects after calling plot() .

Here is an example of Yann with three different line widths:

 import matplotlib.pyplot as plt import numpy as np NUM_COLORS = 20 cm = plt.get_cmap('gist_rainbow') fig = plt.figure() ax = fig.add_subplot(111) for i in range(NUM_COLORS): lines = ax.plot(np.arange(10)*(i+1)) lines[0].set_color(cm(i//3*3.0/NUM_COLORS)) lines[0].set_linewidth(i%3 + 1) fig.savefig('moreColors.png') plt.show() 

Graph Example with Line Width

Here is the same example with different line styles. Of course, you could combine these two if you want.

 import matplotlib.pyplot as plt import numpy as np NUM_COLORS = 20 LINE_STYLES = ['solid', 'dashed', 'dashdot', 'dotted'] NUM_STYLES = len(LINE_STYLES) cm = plt.get_cmap('gist_rainbow') fig = plt.figure() ax = fig.add_subplot(111) for i in range(NUM_COLORS): lines = ax.plot(np.arange(10)*(i+1)) lines[0].set_color(cm(i//NUM_STYLES*float(NUM_STYLES)/NUM_COLORS)) lines[0].set_linestyle(LINE_STYLES[i%NUM_STYLES]) fig.savefig('moreColors.png') plt.show() 

Line Style Example

+4
Jul 05 '17 at 22:48
source share



All Articles