برنامهنویسی انواع مختلفی دارد. یعنی براساس ویژگیها و قابلیتهایی که زبانهای برنامهنویسی دارند میشود تقسیمشان کرد. دراصطلاح تخصصی، از پارادایمهای برنامهنویسی (Programming Paradigms) صحبت میشود. پارادایمها همان دستهها هستند که زبانهای برنامهنویسی با ویژگیهای مشترک را درون خودشان جای دادند.
زبانهای برنامهنویسی ممکن است در چند پارادایم قرار بگیرند. یعنی ممکن است یک زبان این امکان را داشته باشد که بشود با آن به چند شکل مختلف برنامهنویسی کرد. اگر بخواهم پارادایمهای مهم را نام ببرم، باید به پارادایم دستوری (Imperative programming)، پارادایم رویهای (Procedural programming)، برنامهنویسی یا پارادایم شیگرا (Object-Oriented Programming)، برنامهنویسی اعلانی ( Declarative programming) و برنامهنویسی یا پارادایم منطقی (Logic Programming) اشاره کنم. افزونبر پارادایمهایی که نام برده شد، پارادایم یا برنامهنویسی فانکشنال، تابعی یا تابع گرا (Functional) یکی از پارادایمهای اصلی و رایج در برنامهنویسی است.
در این مطلب قصد دارم شما را با برنامهنویسی یا پارادایم فانکشنال آشنا کنم. چون از مهمترین و کاربردیترین زبانهایی که در این پارادایم قرار میگیرد پایتون است، در عنوانی جداگانه دربارهی برنامهنویسی تابعگرا در پایتون نیز بحث شده است.
آنچه در این نوشته خواهیم داشت
برنامه نویسی تابع گرا یا فانکشنال چیست؟
برنامهنویسی تابعی پارادایمی است که در آن همهچیز به شیوهی ریاضی محض نوشته میشود. برنامهنویسی فانکشنال نوعی از برنامهنویسی اعلانی هم هست. در برنامهنویسی تابعی (و اعلانی) تمرکز اصلی بر این است که «چه باید حل شود» درحالیکه در برنامهنویسی دستوری تمرکز اصلی بر «چگونه حلکردن» است.
در پارادایم فانکشنال همهچیز براساس توابع ریاضی نوشته میشود. به زبان دیگر، همهچیز بهصورت جملههای شرطی بیان میشود. اگر در برنامهنویسی دستوری مجموعهای از جملات دستوری دنبال هم میآیند و با اجرای آنها ساختار و وضعیت سایت مشخص میشود، در برنامهنویسی فانکشنال ساختاری درختی و شاخهای از توابع مقادیر را بهیکدیگر پیوند میدهند. Lisp, Python, Erlang, Haskell Clojure از معروفترین زبانهای برنامهنویسی تابعی هستند. زبانهای دیگری مثل #PHP, Katlin ,Java 8 and higher, C نیز قابلیت برنامهنویسی تابعگرا را تاحدودی دارند. برهمیناساس، زبانهای برنامهنویسی فانکشنال به دو دسته تقسیم میشوند:
-
Pure Functional Languages: زبانهایی که فقط با پارادایم تابعی سازگار هستند مثل زبان Haskell و نمیشود با آنها به پارادایمهای دیگر، مثلا دستوری، نوشت.
-
Impure Functional Languages: این زبانها علاوهبر پارادایم تابعگرا با پارادایم دستوری هم سارگاز هستند، مثل زبان Lisp.
زبان پایتون زبان مهمی است. چون زبانی است که در پیشرفت هوش مصنوعی و ماشین لرنینگ سهم داشته است و درآینده هم سهم قابلملاحظهای خواهد داشت. اگر علاقهمند هستید دربارهی تاریخچه هوش مصنوعی بیشتر بدانید، «هرآنچهکه باید درباره تاریخچهی هوش مصنوعی بدانید» را مطالعه کنید.
مزایای برنامه نویسی فانکشنال
- در برنامهنویسی فانکشنال برنامهنویس فقط باید نتیجهای را که میخواهد بنویسد نه تمامی مراحلی که لازم است به آن نتیجه رسید. پس تعداد عباراتی که باید نوشته شود، بسیار کم میشود.
- خروجی تابع فقط آن مقداری است که از او خواسته شده است. توابع از مقادیر غیرقابلتغییر استفاده میکنند. در برنامهنویسی تابعی خروجی پنهان یا خروجی اضافی تولید نمیشود. همین ویژگی بسیار مهم یعنی تعداد خطاها بسیار کم میشود و همین یعنی debugging بسیار سریع و آسان.
- این نوع از برنامهنویسی برای ایجاد و اجرای همزمانیها (concurrency/parallelism) بسیار ایدهآل است. چون کار هر تابع و مقداری که باید برگرداند مشخص است، اجرای تابعی مانع اجرای تابع دیگری نیست. همین یعنی در برنامهنویسی فانکشنال و بااستفاده از زبانهای تابعی برنامهنویسی ناهمگام یا Asynchronous بهراحتی ممکن میشود.
معایب برنامه نویسی تابعی
درکنار همهی مزیتهای این نوع از برنامهنویسی باید به معایب آنهم اشاره کرد:
- گاهی ممکن است فقط به زبان توابع محض نوشتن خوانایی کدها را کمی سخت کند؛
- اگر هم نوشتن با زبان تابعی محض را کار آسانی فرض کنیم، ترکیبکردن این زبان با زبانهای دیگر کار اصلا آسانی نیست؛
- شاید برای کسانیکه خیلی با ریاضی و تابعها میانهی خوبی ندارند، یادگیری این نوع از برنامهنویسی کمی سخت باشد. چون توابع هم مانند متغیرها و عملگرهای کنترلی و منطقی از مفاهیم اولیه در زبان برنامه نویسی پایتون هستند؛
- برنامههایی که با زبانهای فانکشنال نوشته میشوند بسیار سنگین هستند و درنتیجه به فضای زیادی برای ذخیرهکردنشان نیاز است.
برنامه نویسی تابع گرا (Functional) در پایتون
همانطور که اشاره شد، زبان پایتون زبانی است فانکشنال. البته، پایتون بعضی از قابلیتها و ویژگیهای لازم برای برنامهنویسیهای دیگر را هم دارد. در پایتون همهچیز یک شئ (Object) است. تابعها هم مانند اعداد و حلقهها در پایتون شئ هستند. پس، میشود به این نتیجه رسید که هرکاری که در پایتون میشود با اعداد و حلقهها کرد با توابع هم شدنی است. البته، این نتیجهگیری چند استثنای کوچک نیز دارد. برای مثال، در پایتون با اپراتور + میشود دو شئ را بههم افزود. اما این اپراتور برای افزودن توابع بهیکدیگر تعریف نشده است.
در پایتون میشود یک متغیر را درقالب یک تابع تعریف کرد و با آن متغیر رفتاری مانند تابع داشت:
>>> def func(): ... print("I am function func()!") ... >>> func() I am function func()! >>> another_name = func >>> another_name() I am function func()!
همچنین در پایتون بهراحتی میشود مهمترین ویژگیهای برنامهنویسی فانکشنال را پیاده کرد: یک تابع را در قالب یک استدلال (Argument) به تابع دیگر منتقل کرد و یک تابع بهعنوان مقدار بازگشتی تابع دیگری فراخوانده شود. پایتون کار را برای اینکه بشود یک تابع را در درون تابع دیگری قرار داد بسیار راحت کرده و میانبری تعریف کرده است بهنام Decorator.
>>> def inner(): ... print("I am function inner()!") ... >>> def outer(function): ... function() ... >>> outer(inner) I am function inner()!
>>> def outer(): ... def inner(): ... print("I am function inner()!") ... ... # Function outer() returns function inner() ... return inner ... >>> function = outer() >>> function <function outer.<locals>.inner at 0x7f18bc85faf0> >>> function() I am function inner()! >>> outer()() I am function inner()!
اینها نمونههای سادهای هستند از کارهایی که با برنامهنویسی فانکشنال در پایتون، میشود انجام داد. کارهای پیچیدهتر به تابع و Iterableها در پایتون مربوط میشود. Iterable مجموعهای از دادههای قابلشمارش در پایتون است که میشود ازمیان اعضای آن انتخاب کرد. Iterable را تکرارگرها یا پیمایشگر ترجمه کردهاند. در سه حالت زیر میشود براساس یک تابع عضوی را از مجموعه انتخاب کرد یا مجموعه را محدود به اعضای مشخصی کرد یا حتی کل مجموعه را به یک متغیر تبدیل کرد.
map():
map(<f>, <iterable>)
filter():
filter(<f>, <iterable>)
reduce():
reduce(<f>, <iterable>)
جمعبندی و نتیجهگیری
۱. برنامه نویسی فانکشنال یا تابعی یا تابع گرا از پارادایمهای برنامهنویسی است.
۲. در زبانهای برنامهنویسی فانکشنال همهچیز با توابع ریاضی و عبارات شرطی بیان میشوند.
۳. زبان پایتون از زبانهای برنامهنویسی تابعی است. بههمیندلیل است که در آموزش پایتون علاوهبر بحثهای مربوط به توابع و اعداد و حلقهها، برنامه نویسی فانکشنال هم در سرفصلهای آموزشی گنجانده شده است.
برای نوشتن این محتوا از منابع زیر کمک گرفته شده است:
دوره تخصصی یادگیری ماشین
در یک دوره آموزشی متخصص یادگیری ماشین شوید.
از یادگیری ماشین می توان در صنایع مختلف با اهداف مختلف استفاده کرد. ماشین لرنینگ باعث افزایش بهره وری در صنایع می شود، به بازاریابی محصول کمک کرده و پیش بینی دقیق فروش را ساده تر می کند. پیش بینی های دقیق پزشکی و تشخیص ها را تسهیل می کند. دقت در قوانین و مدل های مالی را بهبود می بخشد. به سیستم های توصیه گر، الگوریتم های فرا ابتکاری و حرکت ربات ها کمک خواهد کرد. در بحث فروش میتواند محصولات مناسب تری را به مشتری پیشنهاد دهد( با کمک به تقسیم بندی بهتر و پیش بینی دقیق طول عمر محصولات ) و ...
استفاده از سیستم های ماشین لرنینگ می تواند تا حد زیادی حجم کاری ما را کاهش دهد. به خصوص کارهایی که نیاز به آنالیز حجم عظیمی از داده و تصمیم گیری بر اساس این داده ها را دارد بسیار تسهیل می کند. سیستم های مبتنی بر ماشین لرنینگ ظرفیت انجام کار صد نفر را همزمان دارد و تنها به کمک ماشین ها می توان بدون صرف وقت و انرژی زیاد، کارهای سنگین را انجام داده و در عین حال پول و درآمد بیشتری کسب کرد. ماشین لرنینگ با خودکارسازی فرایندها و صرفه جویی در زمان، به ما کمک می کند تا بتوانیم زمان و انرژی خود را بر تصمیم گیری های پیچیده تری متمرکز کنیم.
ادامه...