Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C#

Local Functions ใน C# 7.0 คืออะไร

Local Functions เป็น Private Methods ของ Type ที่ Nested อยู่ใน Member อื่น สามารถเรียกได้เฉพาะจาก Containing Member เท่านั้น

Local Functions สามารถ Declare และ Call ได้จาก:

  • Methods (รวม Iterator Methods และ Async Methods)
  • Constructors
  • Property Accessors
  • Event Accessors
  • Anonymous Methods
  • Lambda Expressions
  • Finalizers
  • Local Functions อื่นๆ (Nested)

ตัวอย่างพื้นฐาน


class Program {
    public static void Main() {
        // Local Function Declaration
        void AddTwoNumbers(int a, int b) {
            Console.WriteLine(a + b);
        }
        
        // Call Local Function
        AddTwoNumbers(1, 2);
        Console.ReadLine();
    }
}

Output


3

ตัวอย่างกับ Out Parameter


class Program {
    public static void Main() {
        void AddTwoNumbers(int a, int b, out int c) {
            c = a + b;
        }
        
        AddTwoNumbers(1, 2, out int c);
        Console.WriteLine(c);
        Console.ReadLine();
    }
}

Output


3

Use Cases จริงของ Local Functions

1. Iterator Methods (Lazy Evaluation)


public IEnumerable GetEvenNumbers(int start, int count) {
    // Validation รันทันที (Eager)
    if (count < 0) throw new ArgumentException("Count must be positive");
    
    // Iterator Logic เป็น Local Function (Lazy)
    IEnumerable Iterator() {
        for (int i = 0; i < count; i++) {
            yield return start + i * 2;
        }
    }
    
    return Iterator();
}

// Usage: Validation รันทันที, Iteration ทีหลัง
var evens = GetEvenNumbers(2, 5); // No iteration yet
foreach (var n in evens) {        // เริ่ม Iterate ตรงนี้
    Console.WriteLine(n);         // 2, 4, 6, 8, 10
}

2. Async Methods (Eager Validation + Lazy Execution)


public async Task ProcessAsync(string input) {
    // Validate ทันที
    if (string.IsNullOrEmpty(input)) 
        throw new ArgumentException("Input required");
    
    // Async Local Function
    async Task ProcessCoreAsync() {
        var data = await FetchDataAsync(input);
        return Transform(data);
    }
    
    return await ProcessCoreAsync();
}

3. Recursive Algorithms


public int Factorial(int n) {
    if (n < 0) throw new ArgumentException();
    
    int FactorialImpl(int x) {
        return x <= 1 ? 1 : x * FactorialImpl(x - 1);
    }
    
    return FactorialImpl(n);
}

4. Encapsulation ของ Helper Logic


public class OrderProcessor {
    public OrderResult Process(Order order) {
        decimal CalculateTax(Order o) => o.SubTotal * 0.07m;
        decimal CalculateDiscount(Order o) => o.Customer.IsVip ? o.SubTotal * 0.1m : 0;
        
        var tax = CalculateTax(order);
        var discount = CalculateDiscount(order);
        var total = order.SubTotal + tax - discount;
        
        return new OrderResult { Total = total, Tax = tax, Discount = discount };
    }
}

5. 在 Constructors


public class Config {
    public string ConnectionString { get; }
    public int Timeout { get; }
    
    public Config(IConfiguration config) {
        void ValidateAndSet(string key, Action setter, string defaultValue = null) {
            var value = config[key] ?? defaultValue;
            if (string.IsNullOrEmpty(value)) 
                throw new InvalidOperationException($"Missing config: {key}");
            setter(value);
        }
        
        ValidateAndSet("ConnectionString", v => ConnectionString = v);
        ValidateAndSet("Timeout", v => Timeout = int.Parse(v), "30");
    }
}

Local Functions vs Lambda Expressions

FeatureLocal FunctionLambda Expression
Syntaxvoid Name() { }() => { }
Delegate Allocationไม่มี (Direct Call)มี (Delegate Object)
RecursionNatural (เรียกชื่อ Function)ต้องใช้ Delegate Variable
Ref/Out Paramsรองรับไม่รองรับ
Yield Returnรองรับ (Iterator)ไม่รองรับ
Asyncรองรับรองรับ
Attributesรองรับไม่รองรับ

ข้อจำกัด

  • ไม่สามารถเป็น static ได้ (ยกเว้นใน Static Method)
  • ไม่สามารถมี Access Modifiers (public, private, etc.)
  • ไม่สามารถ Overload ได้ (ใน Scope เดียวกัน)
  • ไม่สามารถเข้าถึงจากภายนอก Containing Member