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

Numeric Promotion ใน Conditional Expression (C#)

Numeric Promotion = การแปลง Type เล็ก → Type ใหญ่ อัตโนมัติ ใน Expression เพื่อป้องกัน Overflow และความสูญเสีย Precision

Conditional Expression (Ternary Operator)

condition ? trueExpression : falseExpression

Type ของ Expression ทั้งสองข้างต้อง **Compatible** — Compiler จะหา **Best Common Type** และ Promote ให้อัตโนมัติ

ตัวอย่าง: short → int Promotion

using System;

class Program {
    static void Main() {
        short val1 = 99;
        int val2;
        
        // Conditional Expression: (short == int) ? int : int
        // val1 Promoted to int for Comparison
        // Both Branches are int (100, 30) → Result Type = int
        val2 = (val1 == 1) ? 100 : 30;
        
        Console.WriteLine(val2); // 30
        Console.WriteLine(val2.GetType()); // System.Int32
    }
}

Numeric Promotion Rules (Simplified)

  1. ถ้ามี decimal → ทุกตัว Promote to decimal
  2. ถ้ามี double → ทุกตัว Promote to double
  3. ถ้ามี float → ทุกตัว Promote to float
  4. ถ้ามี ulong → ทุกตัว Promote to ulong
  5. ถ้ามี long → ทุกตัว Promote to long
  6. ถ้ามี uint → ทุกตัว Promote to uint (หรือ long ถ้ามี Signed)
  7. Otherwise → ทุกตัว Promote to int (Includes short, byte, sbyte, char, ushort)

ตัวอย่าง Promotion Scenarios

short s = 10;
int i = 20;
long l = 30;
float f = 1.5f;
double d = 2.5;
decimal m = 3.5m;

// Ternary Examples
var r1 = true ? s : i;  // int (short → int)
var r2 = true ? i : l;  // long (int → long)
var r3 = true ? f : d;  // double (float → double)
var r4 = true ? i : m;  // decimal (int → decimal)
var r5 = true ? s : (short)5; // int! (Literal 5 = int, short → int)
// var r6 = true ? s : (byte)5;  // int (byte → int)

// Explicit Cast to Control
short r7 = (short)(true ? s : (short)5); // OK: Explicit Cast Back

Conditional Expression Type Rules

  • ถ้า Type ทั้งสองข้างเหมือนกัน → Type นั้น
  • ถ้าต่างกัน → หา Implicit Conversion ไป Type ร่วม
  • ถ้าไม่มี Implicit Conversion ทั้งคู่ → Compile Error
  • null มี Implicit Conversion ไป Reference/Nullable Types

ตัวอย่าง Error Cases

// ❌ Error: No Common Type (int ↔ string)
var bad1 = true ? 1 : "hello";

// ✅ OK: Common Base (object)
object ok1 = true ? 1 : "hello";

// ✅ OK: Nullable
int? ok2 = true ? 1 : (int?)null;

// ✅ OK: Explicit Cast
var ok3 = true ? (object)1 : (object)"hello";

Best Practice

  • ทำให้ Type ทั้งสองข้างตรงกันชัดเจน — หลีกเลี่ยง Surprise Promotion
  • ใช้ Explicit Cast เมื่อต้องการ Control Result Type
  • ระวัง short/byte/char → int Promotion ใน Arithmetic/Conditional