switch..case
switch..case ก็เป็นการเขียน if clause แบบหนึ่งที่ง่ายขึ้น มีรูปแบบ syntax ดังนี้switch(<expression>) {
case <value> : <statement>
case <value> : <statement>
case <value> : <statement>
..........................
[default : <statement>]
}
ตรง expression นั้นจะเป็นตัวแปร หรือ method ใด ๆ ก็ได้case <value> : <statement>
case <value> : <statement>
case <value> : <statement>
..........................
[default : <statement>]
}
โดย default นั้นเปรียบเสมือน else ... ซึ่งจะเป็น option ที่จะมีก็ได้ ไม่มีก็ได้
ลองมาดูตัวอย่างเพื่อความเข้าใจดีกว่า
int grade = Int32.Parse(Console.ReadLine());
string gradeString;
switch(grade) {
case 4 : gradeString = "A";
case 3 : gradeString = "B";
case 2 : gradeString = "C";
case 1 : gradeString = "D";
case 0 : gradeString = "F";
default : gradeString = "Incorrect number";
}
Console.WriteLine(gradeString);
ก็ควรจะมีผลเหมือนกับ string gradeString;
switch(grade) {
case 4 : gradeString = "A";
case 3 : gradeString = "B";
case 2 : gradeString = "C";
case 1 : gradeString = "D";
case 0 : gradeString = "F";
default : gradeString = "Incorrect number";
}
Console.WriteLine(gradeString);
int grade = Int32.Parse(Console.ReadLine());
string gradeString;
if(grade == 4) {
gradeString = "A";
} else if(grade == 3) {
gradeString = "B";
} else if(grade == 2) {
gradeString = "C";
} else if(grade == 1) {
gradeString = "D";
} else if(grade == 0) {
gradeString = "F";
} else {
gradeString = "Incorrect number";
}
Console.WriteLine(gradeString);
ถ้านำตัวอย่างนี้ไปรันในภาษาอย่าง C,C++ หรือ Java แล้วสมมุติว่าใส่ input เป็น 3 ผลที่ได้คือ string gradeString;
if(grade == 4) {
gradeString = "A";
} else if(grade == 3) {
gradeString = "B";
} else if(grade == 2) {
gradeString = "C";
} else if(grade == 1) {
gradeString = "D";
} else if(grade == 0) {
gradeString = "F";
} else {
gradeString = "Incorrect number";
}
Console.WriteLine(gradeString);
B
C
D
F
Incorrect number
นั่นเพราะว่า ถ้า case ใดตรงกับค่าใน switch expression มันก็จะทำงานที่ case อื่น ๆ ข้างล่างทั้งหมดเลย ดังนั้น C# จึงแก้ความสับสนนี้ โดยการให้ code ด้านบนนั้นไม่ผ่านการ compile C
D
F
Incorrect number
วิธีแก้ปัญหากรณีนี้ก็คือใส่ประโยค break; ลงไปในแต่ละ case ดังนี้
int grade = Int32.Parse(Console.ReadLine());
string gradeString;
switch(grade) {
case 4 :
gradeString = "A";
break;
case 3 :
gradeString = "B";
break;
case 2 :
gradeString = "C";
break;
case 1 :
gradeString = "D";
break;
case 0 :
gradeString = "F";
break;
default :
gradeString = "Incorrect number";
}
Console.WriteLine(gradeString);
คนที่เคยเขียน pascal มาแล้วคงสงสัย ว่าทำไมต้องใส่ break ด้วยล่ะ ทำไมไม่ทำ ประโยค switch..case ให้มันทำงานแค่ case เดียวแล้วออกเลย นั่นเพราะมันมีประโยชน์บ้างครับ ลองมาดูกัน string gradeString;
switch(grade) {
case 4 :
gradeString = "A";
break;
case 3 :
gradeString = "B";
break;
case 2 :
gradeString = "C";
break;
case 1 :
gradeString = "D";
break;
case 0 :
gradeString = "F";
break;
default :
gradeString = "Incorrect number";
}
Console.WriteLine(gradeString);
int grade = Int32.Parse(Console.ReadLine());
string message;
switch(grade) {
case 4 :
case 3 :
message = "You 're good";
break;
case 2 :
case 1 :
message = "You should pratice more";
break;
case 0 :
message = "try try and try";
break;
default :
message = "Incorrect number";
}
Console.WriteLine(message);
นั่นคือถ้าได้เกรด 4 หรือเกรด 3 message ก็จะเป็นข้อความว่า You 're good แต่ถ้าได้ 2 หรือ 1 ก็จะเป็นข้อความว่า You should pratice more string message;
switch(grade) {
case 4 :
case 3 :
message = "You 're good";
break;
case 2 :
case 1 :
message = "You should pratice more";
break;
case 0 :
message = "try try and try";
break;
default :
message = "Incorrect number";
}
Console.WriteLine(message);
*ในภาษาอื่น ๆ นั้นตรง expression นั้นต้องเป็น integral type เท่านั้น นั่นคือจะต้องเป็นพวก int short,... หรือ char แต่ว่าใน C# นั้นสามารถใส่ expression เป็น string ได้ด้วย
string gradeString = Int32.Parse(Console.ReadLine());
string message;
switch(gradeString.ToUpper()) {
case "A" :
message = "Excellent";
break;
case "B" :
message = "Good";
break;
case "C" :
message = "Cool";
break;
case "D" :
message = "Try";
break;
case "F" :
message = "Get out!!";
break;
default :
message = "Incorrect grade";
}
Console.WriteLine(message);
string message;
switch(gradeString.ToUpper()) {
case "A" :
message = "Excellent";
break;
case "B" :
message = "Good";
break;
case "C" :
message = "Cool";
break;
case "D" :
message = "Try";
break;
case "F" :
message = "Get out!!";
break;
default :
message = "Incorrect grade";
}
Console.WriteLine(message);
Formatting String
คุ้น ๆ code ด้านล่างนี้ใช่มั้ยครับConsole.WriteLine("Hi {0}\nYou 're {1} years old", name, age);
มันมาจาก tutorial ตอนที่ 1 เป็นสไตล์การเขียนแบบ C ครับ ถ้าเป็นใน C ก็คงเป็นอย่างนี้ printf("Hi %s\nYou 're %s years old\n", name, age);
โดย %s บอกว่าให้เอา string มาใส่ตรงนี้นะ(s คือ string ถ้าเป็น int ก็จะเป็น %d, float ก็ %f, char ก็ %c) การเขียนอย่างนี้ไม่ได้ช่วยให้การอ่านประโยคนั้นต่อเนื่องเพียงอย่างเดียว แต่มันยังสามารถจะ format ได้อีกด้วย ลองดูตัวอย่างกัน
Console.WriteLine("{0,5}{1,5}", 123, 456); // Right-aligned
Console.WriteLine("{0,-5}{1,-5}", 123, 456); // Left-aligned
ผลลัพธ์ Console.WriteLine("{0,-5}{1,-5}", 123, 456); // Left-aligned
123 456
123 456
อันนี้คือการจัดชิดซ้ายชิดขวา โดยการระบุความกว้าง(จำนวนตัวอักษร)ลงไป123 456
ถ้าเป็น C จะเขียนอย่างนี้ (ใน C ถ้าจะขึ้นบรรทัดใหม่ ต้องใส่ '\n' เองเสมอ)
printf("%5d%5d\n", 123, 456); // Right-aligned
printf("%-5d%-5d\n", 123, 456); // Left-aligned
ถ้าเป็น Pascal printf("%-5d%-5d\n", 123, 456); // Left-aligned
writeln(123:5, 456:5); { Right-aligned }
writeln(123:-5, 456:-5); { Left-aligned }
ประโยชน์ที่เห็นได้จากการจัดความกว้างก็เช่นการโชว์ข้อมูลเป็นบล็อก ๆ ให้ตรงกัน เพื่อความสวยงามwriteln(123:-5, 456:-5); { Left-aligned }
Console.WriteLine("{0,-10}{1,-3}", "Name","Salary");
Console.WriteLine("----------------");
Console.WriteLine("{0,-10}{1,6}", "Bill", 123456);
Console.WriteLine("{0,-10}{1,6}", "Polly", 7890);
Console.WriteLine("----------------");
Console.WriteLine("{0,-10}{1,6}", "Bill", 123456);
Console.WriteLine("{0,-10}{1,6}", "Polly", 7890);
Name Salary
----------------
Bill 123456
Polly 7890
----------------
Bill 123456
Polly 7890
นอกจากการกำหนดความกว้างแล้ว เรายังกำหนดรูปแบบได้อีกด้วย โดยการใส่ :(colon) แล้วตามด้วยตัวอักษรลงไปหลังตัวเลขระบุตำแหน่ง ดังนี้
Character | ความหมาย |
---|---|
C หรือ c | Currency(เงิน) |
D หรือ d | Decimal(แปลว่าเลขฐาน 10 นะ อย่าสับสนกับ ตัวแปรประเภท decimal) |
E หรือ e | Exponent(ระบบวิทยาศาสตร์) |
Fหรือ f | Floating poing(ทศนิยม) |
G หรือ g | General |
N หรือ n | Number(เหมือน F แต่จะใส่ comma คั่นตัวเลขทุก ๆ 3 หลัก |
P หรือ p | Percentage |
R หรือ r | Round-trip ใช้กับ floating-point value เท่านั้น โดยจะ guaruntee ว่าค่าที่ถูกเปลี่ยนไปจะมีค่าเท่ากับตัวเดิม |
X หรือ x | Hexadecimal(เลขฐาน 16) |
int i = 123456;
Console.WriteLine("{0:C}", i);
Console.WriteLine("{0:D}", i);
Console.WriteLine("{0:E}", i);
Console.WriteLine("{0:F}", i);
Console.WriteLine("{0:G}", i);
Console.WriteLine("{0:N}", i);
Console.WriteLine("{0:P}", i);
Console.WriteLine("{0:X}", i);
Console.WriteLine("{0:C}", i);
Console.WriteLine("{0:D}", i);
Console.WriteLine("{0:E}", i);
Console.WriteLine("{0:F}", i);
Console.WriteLine("{0:G}", i);
Console.WriteLine("{0:N}", i);
Console.WriteLine("{0:P}", i);
Console.WriteLine("{0:X}", i);
฿123,456.00
123456
1.234560E+005
123456.00
123456
123,456.00
12,345,600.00 %
1E240
123456
1.234560E+005
123456.00
123456
123,456.00
12,345,600.00 %
1E240
Console.WriteLine("{0:D6} {1:D4}", 123, 456);
000123 0456
เราสามารถรวมการจัดความกว้างและฟอร์แม็ตไปพร้อม ๆ กันได้ดังนี้
Console.WriteLine("{0,-10:D6}{1,-10:F4}", 123, 456.0000);
Console.WriteLine("{0,-12:N2}{1,9:X4}", 1234567, 240);
Console.WriteLine("{0,-12:N2}{1,9:X4}", 1234567, 240);
000123 456.0000
1,234,567.00 00F0
1,234,567.00 00F0
อ้อ ลองมาดูความแตกต่างของ F กับ R กันตรงนี้เลยครับ
double d = 1.2345678901234567890;
Console.WriteLine("{0:F16}", d);
Console.WriteLine("{0:R16}", d);
Console.WriteLine("{0:F16}", d);
Console.WriteLine("{0:R16}", d);
1.2345678901234600
1.2345678901234567
ตาม definition ของ R เป็นอย่างนี้1.2345678901234567