11. Matplotlib#

11.1. مروری کلی#

ما تاکنون با استفاده از Matplotlib تعداد قابل توجهی نمودار در این سخنرانی‌ها تولید کرده‌ایم.

Matplotlib یک کتابخانه گرافیکی عالی است که برای محاسبات علمی طراحی شده و دارای ویژگی‌های زیر است:

  • نمودارهای دو بعدی و سه بعدی با کیفیت بالا

  • خروجی در تمام فرمت‌های معمول (PDF، PNG و غیره)

  • یکپارچگی با LaTeX

  • کنترل دقیق بر تمام جنبه‌های نمایش

  • انیمیشن و غیره

11.1.1. شخصیت دوگانه Matplotlib#

Matplotlib در این زمینه غیرمعمول است که دو رابط مختلف برای ترسیم نمودار ارائه می‌دهد.

یکی API ساده به سبک MATLAB (رابط برنامه‌نویسی کاربردی) است که برای کمک به مهاجران MATLAB برای یافتن خانه‌ای آماده نوشته شده است.

دیگری یک API شی‌گرا و “پایتونی‌تر” است.

به دلایلی که در زیر توضیح داده شده است، توصیه می‌کنیم از API دوم استفاده کنید.

اما ابتدا، بیایید در مورد تفاوت آن‌ها بحث کنیم.

11.2. APIها#

11.2.1. API به سبک MATLAB#

در اینجا نوعی مثال ساده است که ممکن است در آموزش‌های مقدماتی بیابید

import matplotlib.pyplot as plt
import numpy as np

x = np.linspace(0, 10, 200)
y = np.sin(x)

plt.plot(x, y, 'b-', linewidth=2)
plt.show()
_images/51116615d318488707de6cfbb80eee314ced979fb431c49af7f8b9d3078c5afb.png

این ساده و راحت است، اما تا حدودی محدود و غیرپایتونی نیز هست.

به عنوان مثال، در فراخوانی‌های تابع، اشیاء زیادی ایجاد و منتقل می‌شوند بدون اینکه خود را به برنامه‌نویس معرفی کنند.

برنامه‌نویسان پایتون تمایل دارند سبک صریح‌تری از برنامه‌نویسی را ترجیح دهند (دستور import this را در یک بلوک کد اجرا کنید و به خط دوم نگاه کنید).

این ما را به جایگزین، یعنی API شی‌گرای Matplotlib هدایت می‌کند.

11.2.2. API شی‌گرا#

در اینجا کد مربوط به نمودار قبلی با استفاده از API شی‌گرا آمده است

fig, ax = plt.subplots()
ax.plot(x, y, 'b-', linewidth=2)
plt.show()
_images/51116615d318488707de6cfbb80eee314ced979fb431c49af7f8b9d3078c5afb.png

در اینجا فراخوانی fig, ax = plt.subplots() یک جفت برمی‌گرداند، که در آن

  • fig یک نمونه از Figure است — مانند یک بوم خالی.

  • ax یک نمونه از AxesSubplot است — آن را به عنوان یک قاب برای ترسیم در نظر بگیرید.

تابع plot() در واقع یک متد از ax است.

در حالی که تایپ کردن کمی بیشتر است، استفاده صریح‌تر از اشیاء کنترل بهتری به ما می‌دهد.

این موضوع با ادامه کار واضح‌تر خواهد شد.

11.2.3. تنظیمات ریز#

در اینجا ما خط را به قرمز تغییر داده و یک راهنما اضافه کرده‌ایم

fig, ax = plt.subplots()
ax.plot(x, y, 'r-', linewidth=2, label='sine function', alpha=0.6)
ax.legend()
plt.show()
_images/01428e14c81ed4742a897d9b2bcf0db580b24633839ec1a1b1db699d5df4d0b8.png

ما همچنین از alpha استفاده کرده‌ایم تا خط را کمی شفاف کنیم — که باعث می‌شود نرم‌تر به نظر برسد.

موقعیت راهنما را می‌توان با جایگزینی ax.legend() با ax.legend(loc='upper center') تغییر داد.

fig, ax = plt.subplots()
ax.plot(x, y, 'r-', linewidth=2, label='sine function', alpha=0.6)
ax.legend(loc='upper center')
plt.show()
_images/8f59d4eedd983c92dbf82d1fdc0dd721f558fc97ad999e307900a6dd4c1a6d25.png

اگر همه چیز به درستی پیکربندی شده باشد، اضافه کردن LaTeX بسیار ساده است

fig, ax = plt.subplots()
ax.plot(x, y, 'r-', linewidth=2, label=r'$y=\sin(x)$', alpha=0.6)
ax.legend(loc='upper center')
plt.show()
_images/85440f9c8b3cff5920e0fd3135bc1a6bdff52efad6e7e8952e54d6db55370173.png

کنترل علامت‌ها، افزودن عناوین و غیره نیز ساده است

fig, ax = plt.subplots()
ax.plot(x, y, 'r-', linewidth=2, label=r'$y=\sin(x)$', alpha=0.6)
ax.legend(loc='upper center')
ax.set_yticks([-1, 0, 1])
ax.set_title('Test plot')
plt.show()
_images/12787072805e1323e7406f39a8f1e0524355fc6ee4f58b7d99541ee016b69954.png

11.3. ویژگی‌های بیشتر#

Matplotlib مجموعه عظیمی از توابع و ویژگی‌ها دارد که می‌توانید در طول زمان و با نیاز به آن‌ها، آن‌ها را کشف کنید.

ما فقط چند مورد را ذکر می‌کنیم.

11.3.1. نمودارهای چندگانه روی یک محور#

تولید نمودارهای چندگانه روی یک محور بسیار ساده است.

در اینجا مثالی است که به طور تصادفی سه چگالی نرمال تولید می‌کند و برچسبی با میانگین آن‌ها اضافه می‌کند

from scipy.stats import norm
from random import uniform

fig, ax = plt.subplots()
x = np.linspace(-4, 4, 150)
for i in range(3):
    m, s = uniform(-1, 1), uniform(1, 2)
    y = norm.pdf(x, loc=m, scale=s)
    current_label = rf'$\mu = {m:.2}$'
    ax.plot(x, y, linewidth=2, alpha=0.6, label=current_label)
ax.legend()
plt.show()
_images/0e06e62522238714180e4c7b5497718c45f841c53ddaf6d0261a19590d6be65f.png

11.3.2. زیرنمودارهای چندگانه#

گاهی اوقات می‌خواهیم زیرنمودارهای چندگانه در یک شکل داشته باشیم.

در اینجا مثالی است که ۶ هیستوگرام تولید می‌کند

num_rows, num_cols = 3, 2
fig, axes = plt.subplots(num_rows, num_cols, figsize=(10, 12))
for i in range(num_rows):
    for j in range(num_cols):
        m, s = uniform(-1, 1), uniform(1, 2)
        x = norm.rvs(loc=m, scale=s, size=100)
        axes[i, j].hist(x, alpha=0.6, bins=20)
        t = rf'$\mu = {m:.2}, \quad \sigma = {s:.2}$'
        axes[i, j].set(title=t, xticks=[-4, 0, 4], yticks=[])
plt.show()
_images/770a0e0ad17b7dad8d71bd18e04da1da54dda93cb8899b1835bd75b67d178bcd.png

11.3.3. نمودارهای سه بعدی#

Matplotlib کار خوبی در ترسیم نمودارهای سه بعدی انجام می‌دهد — در اینجا یک مثال آورده شده است

from mpl_toolkits.mplot3d.axes3d import Axes3D
from matplotlib import cm


def f(x, y):
    return np.cos(x**2 + y**2) / (1 + x**2 + y**2)

xgrid = np.linspace(-3, 3, 50)
ygrid = xgrid
x, y = np.meshgrid(xgrid, ygrid)

fig = plt.figure(figsize=(10, 6))
ax = fig.add_subplot(111, projection='3d')
ax.plot_surface(x,
                y,
                f(x, y),
                rstride=2, cstride=2,
                cmap=cm.jet,
                alpha=0.7,
                linewidth=0.25)
ax.set_zlim(-0.5, 1.0)
plt.show()
_images/34927142af97238a1b5ed5c0e642a0216a7a80ad838c72330ed5332bb9b3e13f.png

11.3.4. یک تابع سفارشی‌سازی#

شاید مجموعه‌ای از سفارشی‌سازی‌ها را پیدا کنید که به طور منظم از آن‌ها استفاده می‌کنید.

فرض کنید معمولاً ترجیح می‌دهیم محورهای ما از مبدأ عبور کنند و یک شبکه داشته باشند.

در اینجا یک مثال خوب از Matthew Doty وجود دارد که نشان می‌دهد چگونه API شی‌گرا می‌تواند برای ساخت یک تابع سفارشی subplots که این تغییرات را پیاده‌سازی می‌کند، استفاده شود.

با دقت کد را بخوانید و ببینید آیا می‌توانید دنبال کنید که چه اتفاقی می‌افتد

def subplots():
    "Custom subplots with axes through the origin"
    fig, ax = plt.subplots()

    # Set the axes through the origin
    for spine in ['left', 'bottom']:
        ax.spines[spine].set_position('zero')
    for spine in ['right', 'top']:
        ax.spines[spine].set_color('none')

    ax.grid()
    return fig, ax


fig, ax = subplots()  # Call the local version, not plt.subplots()
x = np.linspace(-2, 10, 200)
y = np.sin(x)
ax.plot(x, y, 'r-', linewidth=2, label='sine function', alpha=0.6)
ax.legend(loc='lower right')
plt.show()
_images/4b12a9aa77ff582ea4503e8a516c53a6b414c0c992f659bafbb4f6c84a4bbd5e.png

تابع سفارشی subplots

  1. تابع استاندارد plt.subplots را به صورت داخلی فراخوانی می‌کند تا جفت fig, ax را تولید کند،

  2. سفارشی‌سازی‌های مورد نظر را روی ax انجام می‌دهد، و

  3. جفت fig, ax را به کد فراخوان‌کننده برمی‌گرداند.

11.3.5. برگه‌های سبک#

یکی دیگر از ویژگی‌های مفید در Matplotlib، برگه‌های سبک است.

ما می‌توانیم از برگه‌های سبک برای ایجاد نمودارهایی با سبک‌های یکنواخت استفاده کنیم.

می‌توانیم لیستی از سبک‌های موجود را با چاپ ویژگی plt.style.available پیدا کنیم

print(plt.style.available)
['Solarize_Light2', 'bmh', 'classic', 'dark_background', 'fast', 'fivethirtyeight', 'ggplot', 'grayscale', 'petroff10', 'petroff6', 'petroff8', 'seaborn-v0_8', 'seaborn-v0_8-bright', 'seaborn-v0_8-colorblind', 'seaborn-v0_8-dark', 'seaborn-v0_8-dark-palette', 'seaborn-v0_8-darkgrid', 'seaborn-v0_8-deep', 'seaborn-v0_8-muted', 'seaborn-v0_8-notebook', 'seaborn-v0_8-paper', 'seaborn-v0_8-pastel', 'seaborn-v0_8-poster', 'seaborn-v0_8-talk', 'seaborn-v0_8-ticks', 'seaborn-v0_8-white', 'seaborn-v0_8-whitegrid', 'tableau-colorblind10']

اکنون می‌توانیم از متد plt.style.use() برای تنظیم برگه سبک استفاده کنیم.

بیایید تابعی بنویسیم که نام یک برگه سبک را می‌گیرد و نمودارهای مختلف را با آن سبک ترسیم می‌کند

def draw_graphs(style='default'):

    # Setting a style sheet
    plt.style.use(style)

    fig, axes = plt.subplots(nrows=1, ncols=4, figsize=(10, 3))
    x = np.linspace(-13, 13, 150)

    # Set seed values to replicate results of random draws
    np.random.seed(9)

    for i in range(3):

        # Draw mean and standard deviation from uniform distributions
        m, s = np.random.uniform(-8, 8), np.random.uniform(2, 2.5)

        # Generate a normal density plot
        y = norm.pdf(x, loc=m, scale=s)
        axes[0].plot(x, y, linewidth=3, alpha=0.7)

        # Create a scatter plot with random X and Y values 
        # from normal distributions
        rnormX = norm.rvs(loc=m, scale=s, size=150)
        rnormY = norm.rvs(loc=m, scale=s, size=150)
        axes[1].plot(rnormX, rnormY, ls='none', marker='o', alpha=0.7)

        # Create a histogram with random X values
        axes[2].hist(rnormX, alpha=0.7)

        # and a line graph with random Y values
        axes[3].plot(x, rnormY, linewidth=2, alpha=0.7)

    style_name = style.split('-')[0]
    plt.suptitle(f'Style: {style_name}', fontsize=13)
    plt.show()

بیایید ببینیم برخی از سبک‌ها چگونه به نظر می‌رسند.

ابتدا، نمودارها را با برگه سبک seaborn ترسیم می‌کنیم

draw_graphs(style='seaborn-v0_8')
_images/2c6f709a27805d5e0eade0242aeea8a9cab52c5ca219c718acff8e7792cd8c8c.png

می‌توانیم از grayscale برای حذف رنگ‌ها در نمودارها استفاده کنیم

draw_graphs(style='grayscale')
_images/cf276987c2fec1799d8e3b25e9dc115a438ece0444f639bec1a3fe89b3804728.png

در اینجا نشان داده می‌شود که ggplot چگونه به نظر می‌رسد

draw_graphs(style='ggplot')
_images/65af35dcf48efeb7a3fe48fee86a1a016f4a2e2ed0a11c256730639000075a9e.png

همچنین می‌توانیم از سبک dark_background استفاده کنیم

draw_graphs(style='dark_background')
_images/50fc656d6383f7a403b1c944c099c7f84bf920e3670ad461d451c07b78baa303.png

می‌توانید از این تابع برای آزمایش سبک‌های دیگر در لیست استفاده کنید.

اگر علاقه‌مند هستید، حتی می‌توانید برگه‌های سبک خود را ایجاد کنید.

پارامترهای برگه‌های سبک شما در یک متغیر شبه دیکشنری به نام plt.rcParams ذخیره می‌شوند

print(plt.rcParams.keys())

Hide code cell output

KeysView(RcParams({'_internal.classic_mode': False,
          'agg.path.chunksize': 0,
          'animation.bitrate': -1,
          'animation.codec': 'h264',
          'animation.convert_args': ['-layers', 'OptimizePlus'],
          'animation.convert_path': 'convert',
          'animation.embed_limit': 20.0,
          'animation.ffmpeg_args': [],
          'animation.ffmpeg_path': 'ffmpeg',
          'animation.frame_format': 'png',
          'animation.html': 'none',
          'animation.writer': 'ffmpeg',
          'axes.autolimit_mode': 'data',
          'axes.axisbelow': True,
          'axes.edgecolor': 'white',
          'axes.facecolor': 'black',
          'axes.formatter.limits': [-5, 6],
          'axes.formatter.min_exponent': 0,
          'axes.formatter.offset_threshold': 4,
          'axes.formatter.use_locale': False,
          'axes.formatter.use_mathtext': False,
          'axes.formatter.useoffset': True,
          'axes.grid': True,
          'axes.grid.axis': 'both',
          'axes.grid.which': 'major',
          'axes.labelcolor': 'white',
          'axes.labelpad': 4.0,
          'axes.labelsize': 'large',
          'axes.labelweight': 'normal',
          'axes.linewidth': 1.0,
          'axes.prop_cycle': cycler('color', ['#8dd3c7', '#feffb3', '#bfbbd9', '#fa8174', '#81b1d2', '#fdb462', '#b3de69', '#bc82bd', '#ccebc4', '#ffed6f']),
          'axes.spines.bottom': True,
          'axes.spines.left': True,
          'axes.spines.right': True,
          'axes.spines.top': True,
          'axes.titlecolor': 'auto',
          'axes.titlelocation': 'center',
          'axes.titlepad': 6.0,
          'axes.titlesize': 'x-large',
          'axes.titleweight': 'normal',
          'axes.titley': None,
          'axes.unicode_minus': True,
          'axes.xmargin': 0.05,
          'axes.ymargin': 0.05,
          'axes.zmargin': 0.05,
          'axes3d.automargin': False,
          'axes3d.depthshade': True,
          'axes3d.depthshade_minalpha': 0.3,
          'axes3d.grid': True,
          'axes3d.mouserotationstyle': 'arcball',
          'axes3d.snap_rotation': 5.0,
          'axes3d.trackballborder': 0.2,
          'axes3d.trackballsize': 0.667,
          'axes3d.xaxis.panecolor': (0.95, 0.95, 0.95, 0.5),
          'axes3d.yaxis.panecolor': (0.9, 0.9, 0.9, 0.5),
          'axes3d.zaxis.panecolor': (0.925, 0.925, 0.925, 0.5),
          'backend': 'module://matplotlib_inline.backend_inline',
          'backend_fallback': True,
          'boxplot.bootstrap': None,
          'boxplot.boxprops.color': 'white',
          'boxplot.boxprops.linestyle': '-',
          'boxplot.boxprops.linewidth': 1.0,
          'boxplot.capprops.color': 'white',
          'boxplot.capprops.linestyle': '-',
          'boxplot.capprops.linewidth': 1.0,
          'boxplot.flierprops.color': 'white',
          'boxplot.flierprops.linestyle': 'none',
          'boxplot.flierprops.linewidth': 1.0,
          'boxplot.flierprops.marker': 'o',
          'boxplot.flierprops.markeredgecolor': 'white',
          'boxplot.flierprops.markeredgewidth': 1.0,
          'boxplot.flierprops.markerfacecolor': 'none',
          'boxplot.flierprops.markersize': 6.0,
          'boxplot.meanline': False,
          'boxplot.meanprops.color': 'C2',
          'boxplot.meanprops.linestyle': '--',
          'boxplot.meanprops.linewidth': 1.0,
          'boxplot.meanprops.marker': '^',
          'boxplot.meanprops.markeredgecolor': 'C2',
          'boxplot.meanprops.markerfacecolor': 'C2',
          'boxplot.meanprops.markersize': 6.0,
          'boxplot.medianprops.color': 'C1',
          'boxplot.medianprops.linestyle': '-',
          'boxplot.medianprops.linewidth': 1.0,
          'boxplot.notch': False,
          'boxplot.patchartist': False,
          'boxplot.showbox': True,
          'boxplot.showcaps': True,
          'boxplot.showfliers': True,
          'boxplot.showmeans': False,
          'boxplot.vertical': True,
          'boxplot.whiskerprops.color': 'white',
          'boxplot.whiskerprops.linestyle': '-',
          'boxplot.whiskerprops.linewidth': 1.0,
          'boxplot.whiskers': 1.5,
          'contour.algorithm': 'mpl2014',
          'contour.corner_mask': True,
          'contour.linewidth': None,
          'contour.negative_linestyle': 'dashed',
          'date.autoformatter.day': '%Y-%m-%d',
          'date.autoformatter.hour': '%m-%d %H',
          'date.autoformatter.microsecond': '%M:%S.%f',
          'date.autoformatter.minute': '%d %H:%M',
          'date.autoformatter.month': '%Y-%m',
          'date.autoformatter.second': '%H:%M:%S',
          'date.autoformatter.year': '%Y',
          'date.converter': 'auto',
          'date.epoch': '1970-01-01T00:00:00',
          'date.interval_multiples': True,
          'docstring.hardcopy': False,
          'errorbar.capsize': 0.0,
          'errorbar.capthick': None,
          'errorbar.elinewidth': None,
          'figure.autolayout': False,
          'figure.constrained_layout.h_pad': 0.04167,
          'figure.constrained_layout.hspace': 0.02,
          'figure.constrained_layout.use': False,
          'figure.constrained_layout.w_pad': 0.04167,
          'figure.constrained_layout.wspace': 0.02,
          'figure.dpi': 100.0,
          'figure.edgecolor': 'black',
          'figure.facecolor': 'black',
          'figure.figsize': [8.0, 5.5],
          'figure.frameon': True,
          'figure.hooks': [],
          'figure.labelsize': 'large',
          'figure.labelweight': 'normal',
          'figure.max_open_warning': 20,
          'figure.raise_window': True,
          'figure.subplot.bottom': 0.11,
          'figure.subplot.hspace': 0.2,
          'figure.subplot.left': 0.125,
          'figure.subplot.right': 0.9,
          'figure.subplot.top': 0.88,
          'figure.subplot.wspace': 0.2,
          'figure.titlesize': 'large',
          'figure.titleweight': 'normal',
          'font.cursive': ['Apple Chancery',
                           'Textile',
                           'Zapf Chancery',
                           'Sand',
                           'Script MT',
                           'Felipa',
                           'Comic Neue',
                           'Comic Sans MS',
                           'cursive'],
          'font.enable_last_resort': True,
          'font.family': ['sans-serif'],
          'font.fantasy': ['Chicago',
                           'Charcoal',
                           'Impact',
                           'Western',
                           'xkcd script',
                           'fantasy'],
          'font.monospace': ['DejaVu Sans Mono',
                             'Bitstream Vera Sans Mono',
                             'Computer Modern Typewriter',
                             'Andale Mono',
                             'Nimbus Mono L',
                             'Courier New',
                             'Courier',
                             'Fixed',
                             'Terminal',
                             'monospace'],
          'font.sans-serif': ['Arial',
                              'Liberation Sans',
                              'DejaVu Sans',
                              'Bitstream Vera Sans',
                              'sans-serif'],
          'font.serif': ['DejaVu Serif',
                         'Bitstream Vera Serif',
                         'Computer Modern Roman',
                         'New Century Schoolbook',
                         'Century Schoolbook L',
                         'Utopia',
                         'ITC Bookman',
                         'Bookman',
                         'Nimbus Roman No9 L',
                         'Times New Roman',
                         'Times',
                         'Palatino',
                         'Charter',
                         'serif'],
          'font.size': 10.0,
          'font.stretch': 'normal',
          'font.style': 'normal',
          'font.variant': 'normal',
          'font.weight': 'normal',
          'grid.alpha': 1.0,
          'grid.color': 'white',
          'grid.linestyle': '-',
          'grid.linewidth': 1.0,
          'grid.major.alpha': None,
          'grid.major.color': None,
          'grid.major.linestyle': None,
          'grid.major.linewidth': None,
          'grid.minor.alpha': None,
          'grid.minor.color': None,
          'grid.minor.linestyle': None,
          'grid.minor.linewidth': None,
          'hatch.color': 'edge',
          'hatch.linewidth': 1.0,
          'hist.bins': 10,
          'image.aspect': 'equal',
          'image.cmap': 'gray',
          'image.composite_image': True,
          'image.interpolation': 'auto',
          'image.interpolation_stage': 'auto',
          'image.lut': 256,
          'image.origin': 'upper',
          'image.resample': True,
          'interactive': True,
          'keymap.back': ['left', 'c', 'backspace', 'MouseButton.BACK'],
          'keymap.copy': ['ctrl+c', 'cmd+c'],
          'keymap.forward': ['right', 'v', 'MouseButton.FORWARD'],
          'keymap.fullscreen': ['f', 'ctrl+f'],
          'keymap.grid': ['g'],
          'keymap.grid_minor': ['G'],
          'keymap.help': ['f1'],
          'keymap.home': ['h', 'r', 'home'],
          'keymap.pan': ['p'],
          'keymap.quit': ['ctrl+w', 'cmd+w', 'q'],
          'keymap.quit_all': [],
          'keymap.save': ['s', 'ctrl+s'],
          'keymap.xscale': ['k', 'L'],
          'keymap.yscale': ['l'],
          'keymap.zoom': ['o'],
          'legend.borderaxespad': 0.5,
          'legend.borderpad': 0.4,
          'legend.columnspacing': 2.0,
          'legend.edgecolor': '0.8',
          'legend.facecolor': 'inherit',
          'legend.fancybox': True,
          'legend.fontsize': 10.0,
          'legend.framealpha': 0.8,
          'legend.frameon': False,
          'legend.handleheight': 0.7,
          'legend.handlelength': 2.0,
          'legend.handletextpad': 0.8,
          'legend.labelcolor': 'None',
          'legend.labelspacing': 0.5,
          'legend.linewidth': None,
          'legend.loc': 'best',
          'legend.markerscale': 1.0,
          'legend.numpoints': 1,
          'legend.scatterpoints': 1,
          'legend.shadow': False,
          'legend.title_fontsize': None,
          'lines.antialiased': True,
          'lines.color': 'white',
          'lines.dash_capstyle': <CapStyle.butt: 'butt'>,
          'lines.dash_joinstyle': <JoinStyle.round: 'round'>,
          'lines.dashdot_pattern': [6.4, 1.6, 1.0, 1.6],
          'lines.dashed_pattern': [3.7, 1.6],
          'lines.dotted_pattern': [1.0, 1.65],
          'lines.linestyle': '-',
          'lines.linewidth': 1.75,
          'lines.marker': 'None',
          'lines.markeredgecolor': 'auto',
          'lines.markeredgewidth': 0.0,
          'lines.markerfacecolor': 'auto',
          'lines.markersize': 7.0,
          'lines.scale_dashes': True,
          'lines.solid_capstyle': <CapStyle.round: 'round'>,
          'lines.solid_joinstyle': <JoinStyle.round: 'round'>,
          'macosx.window_mode': 'system',
          'markers.fillstyle': 'full',
          'mathtext.bf': 'sans:bold',
          'mathtext.bfit': 'sans:italic:bold',
          'mathtext.cal': 'cursive',
          'mathtext.default': 'normal',
          'mathtext.fallback': 'cm',
          'mathtext.fontset': 'dejavusans',
          'mathtext.it': 'sans:italic',
          'mathtext.rm': 'sans',
          'mathtext.sf': 'sans',
          'mathtext.tt': 'monospace',
          'patch.antialiased': True,
          'patch.edgecolor': 'white',
          'patch.facecolor': '#348ABD',
          'patch.force_edgecolor': False,
          'patch.linewidth': 0.5,
          'path.effects': [],
          'path.simplify': True,
          'path.simplify_threshold': 0.111111111111,
          'path.sketch': None,
          'path.snap': True,
          'pcolor.shading': 'auto',
          'pcolormesh.snap': True,
          'pdf.compression': 6,
          'pdf.fonttype': 3,
          'pdf.inheritcolor': False,
          'pdf.use14corefonts': False,
          'pgf.preamble': '',
          'pgf.rcfonts': True,
          'pgf.texsystem': 'xelatex',
          'polaraxes.grid': True,
          'ps.distiller.res': 6000,
          'ps.fonttype': 3,
          'ps.papersize': 'letter',
          'ps.useafm': False,
          'ps.usedistiller': None,
          'savefig.bbox': None,
          'savefig.directory': '~',
          'savefig.dpi': 'figure',
          'savefig.edgecolor': 'white',
          'savefig.facecolor': 'white',
          'savefig.format': 'png',
          'savefig.orientation': 'portrait',
          'savefig.pad_inches': 0.1,
          'savefig.transparent': False,
          'scatter.edgecolors': 'face',
          'scatter.marker': 'o',
          'svg.fonttype': 'path',
          'svg.hashsalt': None,
          'svg.id': None,
          'svg.image_inline': True,
          'text.antialiased': True,
          'text.color': 'white',
          'text.hinting': 'default',
          'text.hinting_factor': None,
          'text.kerning_factor': None,
          'text.language': None,
          'text.latex.engine': 'latex',
          'text.latex.preamble': '',
          'text.parse_math': True,
          'text.usetex': False,
          'timezone': 'UTC',
          'tk.window_focus': False,
          'toolbar': 'toolbar2',
          'webagg.address': '127.0.0.1',
          'webagg.open_in_browser': True,
          'webagg.port': 8988,
          'webagg.port_retries': 50,
          'xaxis.labellocation': 'center',
          'xtick.alignment': 'center',
          'xtick.bottom': True,
          'xtick.color': 'white',
          'xtick.direction': 'out',
          'xtick.labelbottom': True,
          'xtick.labelcolor': 'inherit',
          'xtick.labelsize': 10.0,
          'xtick.labeltop': False,
          'xtick.major.bottom': True,
          'xtick.major.pad': 7.0,
          'xtick.major.size': 0.0,
          'xtick.major.top': True,
          'xtick.major.width': 1.0,
          'xtick.minor.bottom': True,
          'xtick.minor.ndivs': 'auto',
          'xtick.minor.pad': 3.4,
          'xtick.minor.size': 0.0,
          'xtick.minor.top': True,
          'xtick.minor.visible': False,
          'xtick.minor.width': 0.5,
          'xtick.top': False,
          'yaxis.labellocation': 'center',
          'ytick.alignment': 'center_baseline',
          'ytick.color': 'white',
          'ytick.direction': 'out',
          'ytick.labelcolor': 'inherit',
          'ytick.labelleft': True,
          'ytick.labelright': False,
          'ytick.labelsize': 10.0,
          'ytick.left': True,
          'ytick.major.left': True,
          'ytick.major.pad': 7.0,
          'ytick.major.right': True,
          'ytick.major.size': 0.0,
          'ytick.major.width': 1.0,
          'ytick.minor.left': True,
          'ytick.minor.ndivs': 'auto',
          'ytick.minor.pad': 3.4,
          'ytick.minor.right': True,
          'ytick.minor.size': 0.0,
          'ytick.minor.visible': False,
          'ytick.minor.width': 0.5,
          'ytick.right': False}))

پارامترهای زیادی وجود دارد که می‌توانید برای برگه‌های سبک خود تنظیم کنید.

پارامترها را برای برگه سبک خود با روش‌های زیر تنظیم کنید:

  1. ایجاد فایل matplotlibrc خود، یا

  2. به‌روزرسانی مقادیر ذخیره شده در متغیر شبه دیکشنری plt.rcParams

بیایید سبک خطوط چگالی روی هم قرار گرفته خود را با استفاده از روش دوم تغییر دهیم

from cycler import cycler

# set to the default style sheet
plt.style.use('default')

# You can update single values using keys:

# Set the font style to italic
plt.rcParams['font.style'] = 'italic'

# Update linewidth
plt.rcParams['lines.linewidth'] = 2


# You can also update many values at once using the update() method:

parameters = {

    # Change default figure size
    'figure.figsize': (5, 4),

    # Add horizontal grid lines
    'axes.grid': True,
    'axes.grid.axis': 'y',

    # Update colors for density lines
    'axes.prop_cycle': cycler('color', 
                            ['dimgray', 'slategrey', 'darkgray'])
}

plt.rcParams.update(parameters)

Note

این تنظیمات سراسری هستند.

هر نمودار تولید شده پس از تغییر پارامترها در .rcParams تحت تأثیر این تنظیم قرار می‌گیرد.

fig, ax = plt.subplots()
x = np.linspace(-4, 4, 150)
for i in range(3):
    m, s = uniform(-1, 1), uniform(1, 2)
    y = norm.pdf(x, loc=m, scale=s)
    current_label = rf'$\mu = {m:.2}$'
    ax.plot(x, y, linewidth=2, alpha=0.6, label=current_label)
ax.legend()
plt.show()
_images/b1c5bc8e80d31d2077ba7ebd3b146fb1f3eb178504648e7a9f3ce44ddf6c57ed.png

دوباره برگه سبک default را اعمال کنید تا سبک خود را به حالت پیش‌فرض برگردانید

plt.style.use('default')

# Reset default figure size
plt.rcParams['figure.figsize'] = (10, 6)

11.4. مطالعه بیشتر#

  • گالری Matplotlib مثال‌های زیادی ارائه می‌دهد.

  • یک آموزش خوب Matplotlib توسط Nicolas Rougier، Mike Muller و Gael Varoquaux.

  • mpltools امکان تعویض آسان بین سبک‌های نمودار را فراهم می‌کند.

  • Seaborn نمودارهای آماری رایج را در Matplotlib تسهیل می‌کند.

11.5. تمرین‌ها#

Exercise 11.1

تابع زیر را ترسیم کنید

\[ f(x) = \cos(\pi \theta x) \exp(-x) \]

روی بازه \([0, 5]\) برای هر \(\theta\) در np.linspace(0, 2, 10).

تمام منحنی‌ها را در یک شکل قرار دهید.

خروجی باید شبیه این باشد

_images/matplotlib_ex1.png