خوب در قسمت قبلی، خیلی وارد خود بحث بهینهسازی نشدم و بیشتر به مقدمه و حاشیهی کار پرداختم. ولی امروز میخواهم کم کمک وارد بحث اصلی بشوم.
یک نکتهای که دفعهی قبلی بیان آن فراموش شد، این بود که وقتی میگوییم «بهینهسازی»، منظورمان بهینهسازی الگوریتم نیست. بلکه من فرض کردهام شما به دلیلی یک الگوریتم خاص را انتخاب کردهاید و حالا فقط تمایل دارید که آن را به سریعترین شکل ممکن پیادهسازی کنید. و یا اینکه یک تکه کد کند دارید و میخواهید سرعت اجرای آن را بهتر کنید.
موارد ۱ و ۲ را که در پست قبلی نوشته بودم. پس حالا میرویم سراغ مورد سوم:
۳- مشخص کردن گلوگاههای برنامه را میتوان به عنوان گام بعدی برای هر گونه بهینهسازی بیان کرد. زیرا معمولا در هر برنامه یک یا چند نقطهی گلوگاهی وجود دارد که باعث میشوند بهینهسازی سایر نقاط تاثیر چندانی بر عملکرد برنامه نداشته باشند. به عنوان مثال، تصور کنید که برنامهی شما ۲ تابع داشته باشد. که یکی ۹۸% زمان اجرا را به خود اختصاص بدهد و دیگری فقط ۲%. اگر شما حدس بزنید که با یک ساعت کلنجار رفتن با کد تابع اول میتوانید آن را ۲ برابر سریعتر کنید و یا با صرف همین زمان بر روی تابع دوم میتوانید آن را ۲۰ برابر سریعتر کنید، ترجیح میدهید بر روی بهینهسازی کدام تابع کار کنید؟ ( بهینهسازی تابع اول زمان کلی را تفریبا نصف میکند ولی بهینهسازی تابع دوم تقریبا تاثیری روی زمان اجرای برنامه ندارد). وقتی شما یک تکه کد نوشته شده و آماده دارید دستور profiler در matlab میتواند بسیار کارگشا باشد. روش کار هم بسیار ساده است.
ابتدا در خط دستور بنویسید
>>profiler on
>>profiler clear
سپس برنامهی خودتان را اجرا کنید و پس از اجرای آن بنویسید
>>profiler view
با اجرای این خط دستور، profiler سهم هر قسمت از برنامه را از کل زمان مصرف شده نشان میدهد و به راحتی میتوان نقاط گلوگاهی برنامه را مشخص میکرد.
حالا که گلوگاه مشخص شد، باید دید چگونه میتوان آن را بر طرف کرد.
۳- شاید سادهترین و اولین گامی که باید در راستای تسریع برنامههای matlab برداشت، تخصیص حافظه به آرایهها و ماتریسها قبل از شروع محاسبات باشد که اصطلاحا preallocation نامیده میشود. در matlab این امکان وجود دارد که در حین اجرای برنامه، سایز آرایهها و ماتریسها آن را تغییر داد. ولی از آنجایی که این عمل خیلی بهینه نمیباشد و تغییر اندازه آرایهها به صورت پویا و در حین اجرای برنامه بسیار کند انجام میشود، انجام مکرر آن به راحتی میتواند تبدیل به گلوگاه اجرای برنامه شود.
۴- یکی از توانمندیهای مهم matlab انجام محاسبات برداری و ماتریسی با سرعت و بازده بالا میباشد و بر خلاف این گونه محاسبات، اجرای حلقهها (مانند for و یا while) و دسترسی به خانههای یک آرایه از طریق اندیس به شدت کند و غیر بهینه میباشد. به همین دلیل با حذف دسترسی با اندیس به المانهای آرایهها و ماتریسها و همچنین حذف حلقهها و به جای آنها پیاده سازی الگوریتم به کمک عملیات برداری میتوان سرعت اجرا به مقدار قابل توجهی افزایش داد.
بسیاری از محاسبات برنامه را به راحتی میتوان به صورت برداری و ماتریسی نوشت ولی برای تبدیل عدهای دیگر نیاز به لمها و تکنیکهایی است که در قسمت بعدی این پست به تعدادی از آنها اشاره خواهم کرد.
*قسمت بعدی احتمالا قسمت آخر این مجموعه میباشد.