معرفی کتابخانه Matplotlib (قسمت سوم)


شخصی سازی در نمودار دایره­ای:

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

کلمه shodow که به معنی سایه هست، برای نمودار سایه میسازد. پس شدو را معرفی و مقدار آن را True میگذاریم

plt.pie(slices,
  labels = Genres,
  colors = ['red', 'blue', 'green', 'pink'],
  shadow = True)


برای جدا کردن قسمتی از نمودار و معمولاً برای فوکوس کردن و بررسی بخش ویژه ای از نمودار از دستور explode استفاده میشود. به این ترتیب که explode را معرفی و به صورت آرایه ای، ژانری را که میخواهیم از بقیه جدا شده باشد را با عددی بزرگتر از صفر و بخش هایی که میخواهیم بدون تغییر باشند را با عدد صفر مقداردهی میکنیم. مثلاً میخواهیم بخش درام را جدا کنیم. از آنجا که اولین نمودار در قسمت slices نمودار درام است

پس اولین نمودار که مقدار 0.3 برای آن میگذاریم. کد زیر بیانگر همین مسئله است:

plt.pie(slices,
  labels= Genres,
  colors= ['red', 'blue', 'green', 'pink'],
  explode= [0.3, 0, 0, 0],
  shadow= True)


تنظیم استایل با استفاده از Cycler:

در این مفهوم اولین سوالی که به ذهن ما میرسد این است که cycler چیست؟


سایکلر ها آرایه هایی حلقوی هستند که یک pointer(اشاره گر) به خانه صفرم آن آرایه دارند که هر بار یکی از خانه های این آرایه را میخوانیم pointer به خانه بعدی آن اشاره میکند و در این حلقه به صورت پی در پی جلو میرود و پس از خواندن خانه آخر pointerدوباره به خانه صفرم اشاره میکند.

کاربرد cycler در matplotlib :

در matplotlib برای ظاهر سازی نمودار ها که شامل رنگ و استایل نمودار میشود دو cycler پیش فرض وجود دارد که یکی از آنها برای رنگ پیش فرض است و یکی برای استایل نمودار به صورت پیش فرض میباشد.این گونه که مثلا اگر یک نمودار داشته باشیم رنگ آن قرمز و اگر دو نمودار داشته باشیم رنگ پیش فرض آنها طبق خانه اول و دوم cycler رنگ ها قرمز و سبز هستند واگر سه نمودار داشته باشیم رنگ نمودار سوم آبی است و... . cycler استایل نمودارها، برای مثال برای نمودار خطی، فقط یک خط ساده و با ضخامت پیشفرض است.

حال ما میتوانیم با تعریف دو cycler دلخواه برای رنگ و استایل نمودار ها این cycler ها پیش فرض را برای نمودار های خود تغییر دهیم.

حال یک نمودار تعریف میکنیم تا بتوانیم با تعریف دو cycler رنگ و استایل برای آن تغییر را مشاهده کنیم.سپس بعد از تعریف cycler ها cyclerدلخواه خود را به تابع matplotlib.pyplot.rc()میدهیم تا به صورت پیش فرض قرار گیرد.

این مثال دو API مختلف را نشان می دهد:

1. تنظیم پارامتر rc که چرخه ویژگی پیش فرض را مشخص می کند. این روی تمام محورهای بعدی تأثیر می گذارد (اما نه محورهایی که قبلاً ایجاد شده اند).

2.تنظیم چرخه ویژگی برای یک جفت محور

ابتدا کتابخانه های مورد نیاز را وارد و داده­های خود را تهیه میکنیم:


from cycler import cycler
 import numpy as np
 import matplotlib.pyplot as plt
 
    x = np.linspace(0, 2 * np.pi, 50)
    offsets = np.linspace(0, 2 * np.pi, 4, endpoint=False)
    yy = np.transpose([np.sin(x + phi) for phi in offsets])


بنابراین yy[:,] منحنی سینوس آفست i-ام را به شما می دهد. بیایید prop_cycle پیش فرض را با استفاده از matplotlib.pyplot.rc()تنظیم کنیم. با اضافه کردن دو سایکلر با هم، یک سایکلر رنگ و یک سایکلر استایل خط را با هم ترکیب می‌کنیم.


default_cycler = (
cycler(color=['r', 'g', 'b', 'y']) +
  cycler(linestyle=['-', '--', ':', '-.']
))
plt.rc('lines', linewidth=4)
plt.rc('axes', prop_cycle=default_cycler)
custom_cycler = (cycler(color=['c',
                 'm', 'y', 'k']) +
                 cycler(lw=[1, 2, 3, 
                 4]))

fig, (ax0, ax1) = plt.subplots(nrows=2)

ax0.plot(yy)

ax0.set_title('Set default color cycle to rgby')

ax1.set_prop_cycle(custom_cycler)

ax1.plot(yy)

ax1.set_title('Set axes color cycle to cmyk')

fig.subplots_adjust(hspace=0.3)
plt.show()

حالا یک شکل با دو نمودار (محور جداگانه)، یکی روی دیگری ایجاد می کنیم. در نمودار اول، با cycler پیش فرض رسم می کنیم. در نمودار دوم، prop_cycle را با استفاده از mpl.axes.Axes.set_prop_cycle() تنظیم می کنیم، که فقط prop_cycle را برای این نمونه matplotlib.axes.Axes تنظیم می کند. ما از چرخه‌کننده دوم استفاده خواهیم کرد که چرخه‌کننده رنگ و چرخش‌کننده پهنای خط را ترکیب می‌کند.


Legend:

همان راهنمای نمودار ها هستند و نمودار ها را توضیح مدهند و توصیف میکنند و اطلاعاتی در مورد نمودار ها به ما میدهند. که توسط تابع legend() در دسترس ما قرار میگیرند.

Legend entry:

برای کار با legend ها ما نیاز داریم چند تعریف مرتبط با این legend ها را بدانیم:

Legend key:

به نشانگر طرح دار یا رنگ استفاده شده در سمت چپ label ،key میگوییم.

Legend label:

متنی یا برچسبی که نمودار مربوط به خود را توصیف میکند.

Legend handle:

شیئی که برای ایجاد یک legend entry استفاده میشود که با استفاده از آنها label ها را کنترل میکنیم.

th = np.linspace(0, 2*np.pi, 128)

th = np.linspace(0, 2*np.pi, 128) 

plt.plot(th, np.cos(th), 'C1', label='C1')

plt.plot(th, np.sin(th), 'C2', label='C2')
plt.set_title('No Legend', color='C0')


یک قطعه کد بدون legend:


حال اینبار با استفاده از تابع legend میخواهیم برای این نمودار legend بگذاریم.

تابع legend() در matplotlib به 3 شکل میتوان آن را صدا زد.

1) تابع legend() بدون آرگمان ورودی

2) تابع legend(label) همراه با یک آرگمان ورودی ،که این آرگمان ورودی باید label باشد.

3) تابع legend(handle , label) همراه با دو آرگمان ورودی، که ورودی اول باید handle باشد و ورودی دوم تابع باید label باشد.

برای ادامه کار این سه شکل استفاده از تابع legend() را پیاده سازی میکنیم.

1. تابع legend() بدون آرگمان ورودی :

در این شکل صدا زدن تابع ما در قطعه کد قبل باید label هر نمودار را در تابع plot() مشخص کنیم.و سپس وقتی تابع legend() را صدا میزنیم وlegend ها در کوشه سمت چپ پایین نمودار نمایش داده میشوند.


th = np.linspace(0, 2*np.pi, 128) 

plt.plot(th, np.cos(th), 'C1', label='C1')

plt.plot(th, np.sin(th), 'C2', label='C2')
plt.set_title('With Legend', color='C0')
plt.legend()


2. پیش از صدا زدن legend نیازی به نام گذاری محور ها نیست. میتوان آنها را در متد لجند در قالب یک آرایه، به ترتیب، تعریف کرد.تابع legend() به ترتیب صدا زدن تابع plot() این label ها را به نمودار های آنها نسبت میدهد و خروجی مانند قبل میشود.

th = np.linspace(0, 2*np.pi, 128) 

plt.plot(th, np.cos(th), 'C1')
plt.plot(th, np.sin(th), 'C2')
plt.set_title('With Legend', color='C0')
plt.legend(['C1', 'C2'])

3)در صدا زدن تابع legend() همراه با دو ورودی ما از handle ها برای ایجاد تناظر بین label ها و نمودار ها کمک میگیریم.به صورتی که برای هر نمودار یک handle تعریف میکنیم و بعد داخل تابع legend() به ترتیب نام بردن handle ها labelهای مربوط به آنها را می آوریم .به line1 و line2 ،handle گوییم.

در این جا تابعlegend() بین line1 و squares و همچنین بین line2و cubes تناظر برقرار میکند. خروجی تابع مثل قبل میشود.

تعیین مکان legend:

برای تعیین مکان قرارگیری legend ها از کلمه کلیدی loc استفاده میکنیم.میتوانیم داخل تابع legend به صورت یک ورودی با استفاده از کلمه کلیدی loc مکان قرارگیری را مشخص کنیم.مکان پیش فرض تابع legend گوشه پایین سمت راست است.مثلا اگر بخواهیم مکان قرار گیری آن را چپ بالا قرار دهیم به شکل زیر عمل میکنیم.

th = np.linspace(0, 2*np.pi, 128)

line1, = plt.plot(th, np.cos(th), 'C1', label='C1')

line2, = plt.plot(th, np.sin(th), 'C2', label='C2')

plt.title('With Legend', color='C0')

plt.legend([line1, line2], ['C1', 'C2'], loc='upper left')


اعداد و کلمات رزرو شده برای تعیین موقعیت legend ها به صورت زیر است:



با استفاده از کلمه کلیدی bbox_to_anchor میتوان با یک دقت خوب مکان قرارگیری legend ها را تعیین کرد.

th = np.linspace(0, 2*np.pi, 128)

line1, = plt.plot(th, np.cos(th), 'C1', label='C1')

line2, = plt.plot(th, np.sin(th), 'C2', label='C2')

plt.title('With Legend', color='C0')

plt.legend([line1, line2], ['C1', 'C2'])

th = np.linspace(0, 2*np.pi, 128)

line1, = plt.plot(th, np.cos(th), 'C1', label='C1')

line2, = plt.plot(th, np.sin(th), 'C2', label='C2')

plt.title('With Legend', color='C0')

plt.legend([line1, line2], ['C1', 'C2'], loc='upper left')


با استفاده از subplot_mosaic میتوان دو لجند را جدا از هم قرار داد.

fig, ax_dict = plt.subplot_mosaic([['top', 'top'], ['bottom', 'BLANK']],

                                  empty_sentinel=&quotBLANK&quot)

ax_dict['top'].plot([1, 2, 3], label=&quottest1&quot)

ax_dict['top'].plot([3, 2, 1], label=&quottest2&quot)

ax_dict['top'].legend(bbox_to_anchor=(0., 1.02, 1., .102), loc='lower left',

                      ncol=2, mode=&quotexpand&quot, borderaxespad=0.)

ax_dict['bottom'].plot([1, 2, 3], label=&quottest1&quot)

ax_dict['bottom'].plot([3, 2, 1], label=&quottest2&quot)

ax_dict['bottom'].legend(bbox_to_anchor=(1.05, 1),

                         loc='upper left', borderaxespad=0.)

plt.show()


چند legend برای یک axes مشابه:

گاهی ما برای یک axes میخواهیم دو بار یا بیشتر تابع legend() را صدا بزنیم چون برای مثال برای هر entry میخواهیم legendجداگانه داشته باشیم و و به طور جداگانه تابع legend() را صدا بزنیم.برای این کار باید آنها را جداگانه به صورت دستی به axes اضافه کنیم.

fig, ax = plt.subplots()

line1, = ax.plot([1, 2, 3], label=&quotLine 1&quot, linestyle='--')

line2, = ax.plot([3, 2, 1], label=&quotLine 2&quot, linewidth=4)



first_legend = ax.legend(handles=[line1], loc='upper right')

ax.add_artist(first_legend)

ax.legend(handles=[line2], loc='lower right')



plt.show()

در اینجا ما ابتدا یک legend برای line1 تعریف کرده سپس آن را به صورت دستی به axes اضافه کردیم.و سپس یک legendجداگانه برای line2 میسازیم.اگر ما به صورت دستی legend قدیمی تر(خط اول ) را به axes اضافه نکرده بودیم legend قدیمی تر حذف میشد و legend جدید تر اعمال میشد.




در پایان برای کسب دانش بیشتر در زمینه ی matplotlib تمرین، دیدن فیلم های آموزشی و خواندن مطالب سایت matplotlib.org میتونه بسیار تاثیرگذار باشه، ما سعی کردیم که چکیده ­ مطالب رو به بهترین شکلی که در توانمون بود براتون جمع آوری کنیم؛ باشد که پله­ های برای شروع یادگیری هوش مصنوعی باشه.

از طرف انجمن هوش مصنوعی بهتون خسته نباشید میگم و تو دوره های بعدی منتظرتون هستیم.

موفق باشین ?

انجمن هوش مصنوعی دانشگاه اصفهان
ابولفضل شیشه­ گر
امیرمحسن براهیمی
علیرضا عشقی