Sự khác nhau giữa kiểu dữ liệu của 2 code dẫn đến kết quả khác nhau

Cho em hỏi em đang học về swtich case. em thấy 1 bên luaChon được gán int một bên gán char mà lúc scanf thì 1 cái để %c, 1 cái để %d. Khi em sửa %c thành %d ở bài thứ 1 thì điền kqua toàn ra đáp án không hợp lệ ạ. cho em hỏi khác nhau thế nào ạ.
Em cảm ơn ạ!

Bài code 1

#include<stdio.h>

int main()
{
	char luaChon;
	printf("Cau hoi: Con cho di chuyen bang may chan?\n");
	printf("A. 1\nB. 2\nC. 3\nD. 4\n");
	printf("Nhap vao dap an ban chon(a,b,c,d): ");
	scanf("%c", &luaChon);// nhap vao mot ki tu
	
	switch(luaChon){
		case'a':
		case'A':
		case'b':
		case'B':
		case'c':
		case'C':{
			printf("Dap an sai");
			break;
		}
		
		case'D':
		case'd':{
			printf("Dap an dung");
			break;
		}
		default:{
			printf("DAP AN KHONG HOP LE");}
			
	}
	return 0;
}

Bài code 2

#include<stdio.h>


int main(){

	int luaChon;
	do{
		printf("\n=====MENU=====\n1. Tinh tong hai so nguyen.\n2. Tinh hieu hai so nguyen."
			"\n3. Tinh tich hai so nguyen.\n4. Chia nguyen hai so nguyen."
			"\n5. Chia lay du hai so nguyen."
			"\n0. Thoat.\nBan chon ? \n");
		scanf("%d", &luaChon);
		
		switch( luaChon ){
			case 0:break;
			case 1:{
				int a, b;
				printf("\nNhap a, b: ");
				scanf("%d%d", &a, &b);
				printf( "\n%d + %d = %d", a, b, a + b );
				break;
			}
			case 2:{
				int a, b;
				printf("\nNhap a, b: ");
				scanf("%d%d", &a, &b);
				printf( "\n%d - %d = %d", a, b, a - b );
				break;
			}
			case 3:{
				int a, b;
				printf("\nNhap a, b: ");
				scanf("%d%d", &a, &b);
				printf( "\n%d * %d = %d", a, b, a * b );
				break;
			}
			case 4:{
				int a, b;
				printf("\nNhap a, b: ");
				scanf("%d%d", &a, &b);
				printf( "\n%d / %d = %d", a, b, a / b );
				break;
			}
			case 5:{
				int a, b;
				char c = '\%';
				printf("\nNhap a, b: ");
				scanf("%d%d", &a, &b);
				printf( "\n%d %c %d = %d", a, c, b, a % b );
				break;
			}
		}
	}	while(luaChon != 0);
	
	return 0;
}

Trong máy tính một khối bộ nhớ 8 bit có thể biểu diễn qua nhiều dạng: 0x61, a hay 97, bản chất đều là 8 bit 110 0001.
Việc bạn nhập %d hay %c là báo cho máy tính bạn muốn xử lý 8 bit đó như thế nào, như %c character hay %d decimal integer (số thập phân).
Chẳng hạn bạn nhập số 1 vào cửa sổ chương trình, số 1 có thể được hiểu theo 2 cách: là ký tự 1 có giá trị decimal 49 hay decimal 1 có ký tự là ? để máy tính rõ bạn phải báo cho nó biết bạn muốn nó hiểu số 1 đó như thế nào.
Hàm scanf bản thân nó không có cách nào kiểm tra được biến luachon được khởi tạo kiểu char hay kiểu int, thông qua %c ta báo cho nó luachon là kiểu char. Nếu bạn đặt %d thay vì %c chương trình vẫn sẽ chạy, lúc này bạn nhập số 1 vào thì luachon đúng ra sẽ in ra giá trị char là , nhưng bởi vì luachon định nghĩa kiểu char chiếm 8 bits bộ nhớ trong khi một decimal integer %d lại chiếm 4 bytes bộ nhớ, gán 4 bytes vào 8 bits sẽ dấn tới undefined behavior, có thể là bug.

3 Likes
83% thành viên diễn đàn không hỏi bài tập, còn bạn thì sao?