CodeGym /Các khóa học /C# SELF /Ép kiểu tường minh và ngầm định

Ép kiểu tường minh và ngầm định

C# SELF
Mức độ, Bài học
Có sẵn

1. Giới thiệu

Bạn đã bao giờ thử nhét một quả dưa hấu vào chai chưa? C# cũng gặp tình huống tương tự mỗi lần bạn bảo nó gán biến kiểu này sang kiểu khác. Đôi khi dễ (số nhỏ sang số lớn – như bỏ táo vào vali), đôi khi phải cẩn thận (dưa hấu vào chai – không cẩn thận là toang).

Ép kiểu – là thao tác chuyển giá trị từ kiểu dữ liệu này sang kiểu khác. Thường cần khi bạn muốn cộng/trừ hoặc so sánh giá trị khác kiểu, hoặc truyền vào hàm chỉ nhận kiểu nhất định.

Thực tế lập trình ai cũng gặp: bạn thanh toán, tính giảm giá, làm toán vật lý hoặc parse số người dùng nhập từ bàn phím (toàn là chuỗi).

2. Ép kiểu ngầm định (Implicit Conversion)

Nó là gì vậy?

Ép kiểu ngầm định là khi C# tự quyết định cho bạn rằng dữ liệu có thể “chuyển” sang kiểu khác mà không vấn đề gì. Tất cả diễn ra tự động – bạn không cần viết gì, cứ dùng thôi.

  • Trình biên dịch không báo lỗi.
  • Không cần lệnh đặc biệt hay cast.
  • Không mất dữ liệu (gần như luôn vậy).

Ví dụ ép kiểu ngầm định

int a = 42;
double b = a; // Ép kiểu ngầm định int -> double

Console.WriteLine(b); // 42 (nhưng giờ là 42.0)

Ở đây a kiểu int tự động thành double khi gán cho biến b. Không mất dữ liệu vì mọi giá trị int đều nằm gọn trong double.

Ở đây a kiểu int tự động thành double khi gán cho biến b. Không mất dữ liệu vì mọi giá trị int đều nằm gọn trong double.

Khi nào dùng được?

  • Khi kiểu nhận rộng hơn kiểu nguồn – hỗ trợ dải giá trị rộng hơn.
  • Không có mất dữ liệu.
  • Ví dụ:
    • int → long
    • int → float / double
    • float → double
    • char → int

Ví dụ nữa:

byte x = 100;
int y = x; // byte -> int (mọi giá trị byte đều nằm trong dải int)

Bảng ép kiểu ngầm định cho kiểu số

From To
byte
short, ushort, int, uint, long, ulong, float, double, decimal
int
long, float, double, decimal
float
double
char
ushort, int, uint, long, ulong, float, double, decimal

3. Ép kiểu tường minh (Explicit Conversion, Type Cast)

Khi nào hết phép màu?

Đôi khi trình biên dịch không đảm bảo chuyển đổi an toàn, nên bắt bạn phải chịu trách nhiệm – báo rõ là bạn biết rủi ro.

  • Có thể mất dữ liệu.
  • Định dạng giá trị có thể thay đổi.
  • Đôi khi chuyển đổi không được – sẽ báo lỗi.

Ghi cú pháp ép kiểu tường minh thế nào?

Dùng cú pháp ngoặc (cast):

double pi = 3.1415;
int wholePi = (int)pi; // Ép kiểu tường minh double -> int

Console.WriteLine(wholePi); // 3 (phần thập phân bị bỏ!)

Khi nào dùng?

  • Khi kiểu nhận hẹp hơn kiểu nguồn – dải giá trị của nhận nhỏ hơn nguồn.
  • Có thể mất phần thập phân, dữ liệu, tràn số.
  • Ví dụ:
    • double → int
    • long → int
    • int → byte
    • Gần như mọi chuyển đổi giữa các kiểu không tương thích.

4. Phân tích ví dụ

1) Có mất dữ liệu không? Thử xem!

Ép kiểu ngầm định – ổn áp!

int small = 25;
long big = small; // Ép kiểu ngầm định (int -> long)
Console.WriteLine(big); // 25

Ép kiểu tường minh – vùng nguy hiểm!

int big = 1000;
byte small = (byte)big; // Ép kiểu tường minh (int -> byte)

Console.WriteLine(small); // 232 (!), vì 1000 không nằm trong byte (0..255)

Lưu ý::

Kết quả ở đây là “ma thuật” 232, vì 1000 % 256 == 232.

2) Với số thực (double, float)

double number = 9.99;
int approximate = (int)number; // phần thập phân bị bỏ

Console.WriteLine(approximate); // 9

3) Chuyển đổi giữa số nguyên và số thực (double ↔ int)

int apples = 5;
double exactApples = apples; // int -> double (ngầm định)
Console.WriteLine(exactApples); // 5.0

double bananaWeight = 2.77;
int weightForReport = (int)bananaWeight; // double -> int (tường minh)
Console.WriteLine(weightForReport); // 2

5. Làm gì với chuyển đổi chuỗi: Parse và Convert

Ép kiểu không hoạt động giữa số và chuỗi! Cần dùng hàm đặc biệt, ví dụ:

string strNumber = "123";
int num = int.Parse(strNumber); // hoặc Convert.ToInt32(strNumber);

Nhưng ngược lại (int → string) thì tự động khi nối chuỗi:

int number = 42;
string message = "Đáp án: " + number; // Ép kiểu ngầm định int → string

6. Lỗi khi ép kiểu

Bài học lịch sử: từng có người quên ép kiểu tường minh, kết quả thanh toán nhỏ hơn 250 lần so với cần thiết... Sinh viên nhớ cẩn thận nhé!

Lỗi hay gặp: cố ép kiểu ngầm định nơi có thể mất dữ liệu.

int big = 500;
byte small = big; // Trình biên dịch: "Không được! Có thể mất dữ liệu!"

Ở đây cần ép kiểu tường minh:

byte small = (byte)big; // Nhưng bạn có thể mất dữ liệu!

Một bug phổ biến khác – quên phần thập phân:

double x = 2.9;
int y = (int)x; // y == 2, phần thập phân biến mất

Muốn làm tròn đúng toán học, dùng Math.Round:

int y = (int)Math.Round(x); // y == 3

7. Bẫy khi chuyển đổi

  • Mất dữ liệu. Luôn kiểm tra giá trị có vượt dải hợp lệ của kiểu không. Ví dụ, int chứa từ -2 147 483 648 đến 2 147 483 647, còn byte chỉ 0–255.
  • Làm tròn. Ép kiểu thường ((int)x) chỉ bỏ phần thập phân. Muốn làm tròn đúng thì dùng Math.Round, Math.Floor, Math.Ceiling.
  • Số literal. Lưu ý, ghi 3 / 2 sẽ ra 1 (chia nguyên), còn 3.0 / 2 thì ra 1.5 (double)!
  • Phép toán kiểu hỗn hợp. Nếu trong biểu thức có cả int và double, kết quả sẽ là double.
2
Nhiệm vụ
C# SELF, mức độ, bài học
Đã khóa
Làm tròn số thực thành số nguyên
Làm tròn số thực thành số nguyên
2
Nhiệm vụ
C# SELF, mức độ, bài học
Đã khóa
Chuyển đổi số với mất dữ liệu
Chuyển đổi số với mất dữ liệu
1
Khảo sát/đố vui
, cấp độ , bài học
Không có sẵn
Số thực
Vấn đề về độ chính xác và giá trị đặc biệt
Bình luận
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION