Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Most pythonic way to plot multiple signals

I would like to plot one ore more signals into one plot.

For each signal, a individual color, linewidth and linestyle may be specified. If multiple signals have to be plotted, a legend should be provided as well.

So far, I use the following code which allows me to plot up to three signals.

import matplotlib
fig = matplotlib.figure.Figure(figsize=(8,6))
subplot = fig.add_axes([0.1, 0.2, 0.8, 0.75])
Signal2, Signal3, legend, t = None, None, None, None
Signal1, = subplot.plot(xDataSignal1, yDataSignal1, color=LineColor[0], linewidth=LineWidth[0],linestyle=LineStyle[0])
if (yDataSignal2 != [] and yDataSignal3 != []):
    Signal2, = subplot.plot(xDataSignal2, yDataSignal2, color=LineColor[1], linewidth=LineWidth[1],linestyle=LineStyle[1])
    Signal3, = subplot.plot(xDataSignal3, yDataSignal3, color=LineColor[2], linewidth=LineWidth[2],linestyle=LineStyle[2])
    legend = subplot.legend([Signal1, Signal2, Signal3], [yLabel[0], yLabel[1], yLabel[2]],LegendPosition,labelspacing=0.1, borderpad=0.1)
    legend.get_frame().set_linewidth(0.5)
    for t in legend.get_texts():
        t.set_fontsize(10)
elif (yDataSignal2 != []):
    Signal2, = subplot.plot(xDataSignal2, yDataSignal2, color=LineColor[1], linewidth=LineWidth[1],linestyle=LineStyle[1])
    legend = subplot.legend([Signal1, Signal2], [yLabel[0], yLabel[1]], LegendPosition,labelspacing=0.1, borderpad=0.1)
    legend.get_frame().set_linewidth(0.5)
    for t in legend.get_texts():
        t.set_fontsize(10)

Is it possible to generalize that code such that it is more Pythonic and supports up to n signals by still making use of matplotlib and subplot?

Any suggestions are highly appreciated.

like image 819
Rickson Avatar asked Dec 12 '16 14:12

Rickson


1 Answers

A list of dicts might be a good solution for this (you could even use a defaultdict to default the color and linewidth in case you don't want to specify it, read more here)

import matplotlib as mpl
import matplotlib.pyplot as plt
import numpy as np

mysignals = [{'name': 'Signal1', 'x': np.arange(10,20,1),
             'y': np.random.rand(10), 'color':'r', 'linewidth':1},
            {'name': 'Signal2', 'x': np.arange(10,20,1),
             'y': np.random.rand(10), 'color':'b', 'linewidth':3},
            {'name': 'Signal3', 'x': np.arange(10,20,1),
             'y': np.random.rand(10), 'color':'k', 'linewidth':2}]

fig, ax = plt.subplots()
for signal in mysignals:
    ax.plot(signal['x'], signal['y'], 
            color=signal['color'], 
            linewidth=signal['linewidth'],
            label=signal['name'])

# Enable legend
ax.legend()
ax.set_title("My graph")
plt.show()

enter image description here

like image 145
Julien Marrec Avatar answered Oct 17 '22 09:10

Julien Marrec