Dark mode
Functional Programming
แนวคิดหลัก
Pure Functions: ฟังก์ชันที่ไม่มีผลข้างเคียง (side effects) และให้ผลลัพธ์เดียวกันเสมอเมื่อรับอินพุตเดียวกัน
ts
// Pure function
const add = (a: number, b: number): number => a + b;
// Impure function (has side effect)
let total = 0;
const addToTotal = (value: number): number => {
total += value; // modifies external state
return total;
};
Immutability: ข้อมูลไม่สามารถเปลี่ยนแปลงได้หลังจากสร้างขึ้น ต้องสร้างข้อมูลใหม่แทนการแก้ไข
ts
// Immutable approach
const originalArray: number[] = [1, 2, 3];
const newArray: number[] = [...originalArray, 4]; // creates new array
// Mutable approach (avoid in functional programming)
const array: number[] = [1, 2, 3];
array.push(4); // modifies original array
Higher-Order Functions: ฟังก์ชันที่รับฟังก์ชันเป็นอาร์กิวเมนต์หรือคืนค่าเป็นฟังก์ชัน
ts
// Function that takes a function as argument
const map = <T, U>(array: T[], fn: (item: T) => U): U[] => array.map(fn);
const double = (x: number): number => x * 2;
console.log(map([1, 2, 3], double)); // [2, 4, 6]
// Function that returns a function
const multiply = (x: number) => (y: number): number => x * y;
const triple = multiply(3);
console.log(triple(4)); // 12
Function Composition: การรวมฟังก์ชันหลายตัวเข้าด้วยกันเพื่อสร้างฟังก์ชันใหม่
ts
// Simple composition
const compose = <T, U, V>(f: (x: U) => V, g: (x: T) => U) => (x: T): V =>
f(g(x));
const addOne = (x: number): number => x + 1;
const double = (x: number): number => x * 2;
const addOneThenDouble = compose(double, addOne);
console.log(addOneThenDouble(3)); // 8 (3 + 1 = 4, then 4 * 2 = 8)
// More flexible composition with reduce
const pipe = <T>(...fns: Array<(x: T) => T>) => (x: T): T =>
fns.reduce((acc, fn) => fn(acc), x);
const add = (a: number, b: number): number => a + b;
const square = (x: number): number => x * x;
const addThenSquare = pipe(
(x: number) => add(x, 5), // Add 5
square, // Then square the result
x => x / 2, // Then divide by 2
);
console.log(addThenSquare(5)); // 50 ((5 + 5)² / 2 = 100 / 2 = 50)
Recursion: การเรียกฟังก์ชันตัวเองซ้ำๆ แทนการใช้ลูป
ts
// Recursive factorial
const factorial = (n: number): number => {
if (n <= 1) return 1;
return n * factorial(n - 1);
};
console.log(factorial(5)); // 120
// แบบใช้ลูป (ไม่ใช่ functional style)
const factorialImperative = (n: number): number => {
let result = 1;
for (let i = 2; i <= n; i++) {
result *= i;
}
return result;
};
// ตัวอย่างการใช้งาน Tail Recursion
const factorialTailRec = (n: number, accumulator: number = 1): number => {
if (n <= 1) return accumulator;
return factorialTailRec(n - 1, n * accumulator);
};
console.log(factorialTailRec(5)); // 120
เหมาะสำหรับ
- การประมวลผลข้อมูลแบบขนาน (Parallel Processing)
- การจัดการกับโครงสร้างข้อมูลขนาดใหญ่
- ระบบที่ต้องการความน่าเชื่อถือและทดสอบง่าย
- การพัฒนาซอฟต์แวร์ที่ซับซ้อนและต้องการบำรุงรักษาในระยะยาว
- ระบบที่ต้องการความปลอดภัยสูงและลดข้อผิดพลาด