01/10/2018, 11:55

Khai báo một biến kiểu int mà sau đó nhập từ bàn phím ta lại nhập ký tự, thì biến đó nhận giá trị là gì?

Mọi người cho em hỏi: Trong C++ mình khai báo một biến kiểu int mà sau đó nhập từ bàn phím ta lại nhập ký tự, thì biến đó nhận giá trị là gì?
Em có đoạn code dưới này, khi chạy mà nhập vào ký tự nó sẽ lặp vô tận. Ai giải thích giúp em với ?
https://pastebin.com/L6jCZzzM

Quang Minh viết 14:01 ngày 01/10/2018

Theo minh nhớ là máy sẽ nhận mã ASCII của kí tự đó.
Bài code của b là lặp câu thông báo khi giá trị của n == 0 và… mình không hiểu sao lại như vây nên chắc phải đợi các coder cao tay ấn vào giúp vậy ^^

Trần Hoàn viết 14:03 ngày 01/10/2018

Thực ra thì máy sẽ không nhận ASCII của ký tự đó đâu. Còn tại sao nó lặp vô tận thì đến nay mình cũng chưa biết
Tại sao cái ông viết C++ không cho cin quăng exception mà lại để lỗi iostream nhỉ?

Quang Minh viết 14:00 ngày 01/10/2018

Mình có nghe cô giảng một lần :)) chắc chắn là máy sẽ chuyển từ chữ sang số nhưng lại không nhớ nó là ASCII hay 01 :))
Điều kiện của vòng lặp là 0 nên theo đúng logic chắc là các giá trị của n khi là chữ thì bằng 0?? nếu muốn rõ hơn chắc chủ topic phải thêm 1 lệch dừng ct như lệnh getch()
Chắc v :))

Trần Hoàn viết 14:07 ngày 01/10/2018

getch() không được thì phải. Trước có thử xoá buffer các kiểu nó vẫn cứ chạy vèo vèo, toàn phải Ctrl C để dừng

Quang Minh viết 14:11 ngày 01/10/2018

getch() không được thì phải. Trước có thử xoá buffer các kiểu nó vẫn cứ chạy vèo vèo, toàn phải Ctrl C để dừng

Thế thì đành phải công nhận biến mà n nhận khi không phải số là 0 rồi :))

viết 13:57 ngày 01/10/2018

kiểm tra lỗi theo kiểu check cin.good() hoặc check if (!cin) tức là đọc vào bị lỗi thì xử lý:

while (true)
{
    cout << "nhap n: ";
    cin >> n;
    if (!cin) //đọc vào bị lỗi
    {
        cin.clear(); //xóa flag cin.fail(),
                     //nếu ko xóa thì sẽ bị lặp vô tận vì cin >> n tiếp theo ko đọc được
                     //do cin vẫn còn flag fail trước đó
        cin.ignore(100, '\n'); //bỏ qua các ký tự ko hợp lệ, tối đa 100 ký tự
                               //hoặc khi gặp ký tự xuống dòng thì dừng.
                               //Nếu ko bỏ qua thì lần cin >> n tiếp theo vẫn đọc phải ký tự ko hợp lệ,
                               //cũng dân tới lặp vô tận
    }
    else break;
}

muốn sợ người dùng input hơn 100 ký tự, ignore ko sạch thì xài cin.ignore(numeric_limits<streamsize>::max(), '\n'), (include thêm header <limits>)

Dao Tran viết 13:58 ngày 01/10/2018

Vẫn chưa hiểu lí do vì sao nó lặp. Khi test mà khai báo int, rồi nhập ký tự vào thì kết quả đưa ra là 0.

viết 13:56 ngày 01/10/2018

http://en.cppreference.com/w/cpp/io/basic_istream/operator_gtgt

If extraction fails (e.g. if a letter was entered where a digit is expected), value is left unmodified and failbit is set. (until C++11)
If extraction fails, zero is written to value and failbit is set. If extraction results in the value too large or too small to fit in value, std::numeric_limits::max() or std::numeric_limits::min() is written and failbit flag is set. (since C++11)

C++11 thì nó gán 0 cho n nếu đọc lỗi, còn trước C++11 thì nó ko gán gì vô n cả. int n; chỉ khai báo ko gán giá trị trước thì ko biết n chứa giá trị gì, muốn cho chắc ăn thì gán giá trị cho n khi khai báo luôn: int n = 0;

nếu đọc lỗi thì cin được set failbit, ko đọc được nữa, nên cin >> n ko làm gì cả (nếu cin ko bị gán failbit thì nó mới dừng console lấy input, còn bị gán failbit thì cin >> n nó bỏ qua luôn ko dừng console), n vẫn chứa giá trị rác nên check n == 0 trả về false nên nó lặp vô tận, phải gọi cin.clear(). Nhưng cũng chưa đủ, vì khi đọc lỗi cin nó ko bỏ qua các ký tự lỗi mà để y nguyên, nên phải bỏ qua mấy ký tự lỗi đó nữa bằng cách gọi cin.ignore(100, '\n')

Hoàng Khang Nguyễn viết 14:00 ngày 01/10/2018

mình chạy thử code của bạn thì nó ra một giá trị rác

rogp10 viết 14:08 ngày 01/10/2018

Giá trị mặc định thôi tức là không nhận.

Bài liên quan
0