Prefix vs Postfix Operators ใน C#
ความแตกต่างหลัก: **ลำดับการคืนค่า vs การเปลี่ยนแปลงค่า**
Prefix Operator (++x, --x)
- **เปลี่ยนค่าก่อน** แล้วคืนค่าใหม่
- ค่าของนิพจน์ = ค่าหลังอัปเดต
- ใช้เมื่อต้องการค่าที่อัปเดตแล้วทันที
using System;
class Program
{
static void Main()
{
int a = 50;
Console.WriteLine($"a = {a}"); // 50
Console.WriteLine($"++a = {++a}"); // 51 (เพิ่มก่อน คืน 51)
Console.WriteLine($"a = {a}"); // 51
int b = ++a; // b = 52, a = 52
Console.WriteLine($"b = ++a → a={a}, b={b}");
}
}
ผลลัพธ์
a = 50
++a = 51
a = 51
b = ++a → a=52, b=52
Postfix Operator (x++, x--)
- **คืนค่าปัจจุบันก่อน** แล้วค่อยเปลี่ยนค่า
- ค่าของนิพจน์ = ค่าก่อนอัปเดต
- ใช้เมื่อต้องการค่าเก่าก่อนอัปเดต
using System;
class Program
{
static void Main()
{
int a = 10;
Console.WriteLine($"a = {a}"); // 10
Console.WriteLine($"a++ = {a++}"); // 10 (คืนค่าเก่า แล้ว a=11)
Console.WriteLine($"a = {a}"); // 11
int b = a++; // b = 11, a = 12
Console.WriteLine($"b = a++ → a={a}, b={b}");
}
}
ผลลัพธ์
a = 10
a++ = 10
a = 11
b = a++ → a=12, b=11
ตารางเปรียบเทียบ
| Operator | ชื่อ | ลำดับ | ค่าของนิพจน์ | ค่าตัวแปรหลัง |
|---|---|---|---|---|
++x | Pre-increment | Inc → Return | New value | New value |
x++ | Post-increment | Return → Inc | Old value | New value |
--x | Pre-decrement | Dec → Return | New value | New value |
x-- | Post-decrement | Return → Dec | Old value | New value |
ในลูป for - ใครเร็วกว่า?
// Postfix (เดิม)
for (int i = 0; i < n; i++) { }
// Prefix (แนะนำ - เล็กน้อย)
for (int i = 0; i < n; ++i) { }
// ทั้งคู่ให้ผลลัพธ์เหมือนกันใน for loop เพราะค่าที่คืนไม่ได้ถูกใช้
// แต่ ++i ไม่ต้องสร้าง temp variable เก็บค่าเก่า (micro-optimization)
ตัวอย่างนิพจน์ซับซ้อน (Operator Precedence)
int a = 5;
int result = ++a + a++ + --a - a--;
// Evaluation order (left to right):
// 1. ++a → a=6, returns 6
// 2. a++ → returns 6, a=7
// 3. --a → a=6, returns 6
// 4. a-- → returns 6, a=5
// result = 6 + 6 + 6 - 6 = 12
// Final a = 5
Console.WriteLine($"Result: {result}, a: {a}"); // Result: 12, a: 5
Best Practice
- **หลีกเลี่ยง** ใช้ ++/-- ในนิพจน์ซับซ้อน (ยากอ่าน, ยาก Debug)
- ใช้ **Prefix (++i)** ในลูป for เป็นค่าเริ่มต้น
- แยก Statement ออกเป็นบรรทัดต่างกัน เพื่อความชัดเจน
- Postfix (i++) ใช้เมื่อ **ต้องการค่าเก่า** จริงๆ (เช่น array[index++])
// ✅ Good - ชัดเจน
int index = 0;
ProcessItem(items[index]);
index++;
// ✅ Good - Idiomatic
ProcessItem(items[index++]);
// ❌ Bad - Confusing
ProcessItem(items[++index]); // Off-by-one risk