البرمجة الوظيفية في TypeScript: من الألف إلى الياء

مدرب بايثون أونلاين للمبتدئين

تعلم Python بسهولة دون إرهاق نظري. حل مهام عملية مع التحقق التلقائي واكتب الكود مباشرة في المتصفح.

ابدأ الدورة

البرمجة الوظيفية في TypeScript: من الألف إلى الياء



البرمجة الوظيفية (FP) هي نموذج برمجي ينظر إلى العمليات الحسابية على أنها تقييم للدوال الرياضية ويتجنب تغيير الحالة والبيانات القابلة للتغيير. TypeScript، كونه امتدادًا صارمًا للأنواع من JavaScript، يوفر أساسًا ممتازًا لتطبيق مبادئ البرمجة الوظيفية، مما يسمح بكتابة كود أكثر قابلية للتنبؤ والاختبار والموثوقية. في هذه المقالة، سنقوم بتحليل المفاهيم الأساسية للبرمجة الوظيفية في TypeScript، بدءًا من الأساسيات وحتى التقنيات المتقدمة.



المبادئ الأساسية للبرمجة الوظيفية



قبل التعمق في الكود، من المهم فهم المبادئ الأساسية التي تقوم عليها البرمجة الوظيفية.



الدوال النقية (Pure Functions)

الدالة النقية هي دالة:

  • تعيد دائمًا نفس النتيجة لنفس الوسائط (الحتمية).
  • ليس لها آثار جانبية (لا تغير المتغيرات الخارجية، ولا تطبع بيانات في وحدة التحكم، ولا ترسل طلبات).

مثال على دالة نقية:

function add(a: number, b: number): number {  return a + b;}

// دائمًا يمكن التنبؤ بهاconsole.log(add(2, 3)); // 5console.log(add(2, 3)); // 5


مثال على دالة غير نقية:

let counter = 0;function increment(): number {  return ++counter; // تأثير جانبي: تغيير متغير خارجي}


الثبات (Immutability)

يجب ألا تتغير البيانات بعد إنشائها. بدلاً من تعديل الكائن الموجود، نقوم بإنشاء نسخة جديدة منه مع التغييرات اللازمة.

interface User {  name: string;  age: number;}

const user: User = { name: "Alice", age: 30 };

// سيء (تحوير)user.age = 31;

// جيد (ثبات)const updatedUser: User = { ...user, age: 31 };

console.log(user); // { name: "Alice", age: 30 } - الأصل لم يتغيرconsole.log(updatedUser); // { name: "Alice", age: 31 }


التركيب والكاري في TypeScript

تركيب الدوال هو عملية دمج عدة دوال بسيطة لإنشاء دالة أكثر تعقيدًا. الكاري (currying) هو تحويل دالة ذات عدة وسائط إلى سلسلة من الدوال، كل منها تأخذ وسيطًا واحدًا.



التركيب (Function Composition)

تطبيق موصوف الأنواع للتركيب في TypeScript:

function compose<A, B, C>(f: (x: B) => C, g: (x: A) => B): (x: A) => C {  return (x: A) => f(g(x));}

const toUpperCase = (str: string): string => str.toUpperCase();const exclaim = (str: string): string => `${str}!`;

const shout = compose(exclaim, toUpperCase);console.log(shout("hello world")); // "HELLO WORLD!"


الكاري (Currying)

مثال على دالة مكاريّة:

function multiply(a: number): (b: number) => number {  return (b: number) => a * b;}

const double = multiply(2);const triple = multiply(3);

console.log(double(5)); // 10console.log(triple(5)); // 15

الكاري يجعل الدوال أكثر مرونة وسهولة في التركيب.



العمل مع المونادات: Option و Result

المونادات هي نمط قوي للتعامل مع الآثار الجانبية ومعالجة الأخطاء دون انتهاك نقاء الدوال. في TypeScript، غالبًا ما تُستخدم المونادات Option (أو Maybe) و Result (أو Either).



مونادة Option (Maybe)

تسمح بالعمل بأمان مع القيم التي قد تكون null أو undefined.

type Option<T> = T | null;

function safeDivide(a: number, b: number): Option<number> { return b === 0 ? null : a / b;}

function getValue(value: Option<number>): string { if (value === null) { return "خطأ: القسمة على صفر"; } return `النتيجة: ${value}`;}

console.log(getValue(safeDivide(10, 2)

المدونات

توصيات الكتب