2009-04-16 31 views
5

Tôi có đoạn code sau'luôn đúng vì giới hạn phạm vi loại dữ liệu' trong C?

//Point.h 
#define WIDTH 8 
#define HEIGHT 8 

typedef struct Point 
{ 
    char x; 
    char y; 
} Point; 

//Board.c 
#include <stdbool.h> 

// Some other functions that we don't care about... 

bool inBounds(Point * p) 
{ 
    return p->x >= 0 
    && p->x <= WIDTH 
    && p->y >= 0 
    && p->y <= HEIGHT; 
} 

Khi tôi biên dịch này (PPU-gcc 4.1.1), tôi nhận được cảnh báo sau đây

warning: comparison is always true due to limited range of data type 

mặc dù phạm vi của char là -127 đến 127 và WIDTH là 8, cũng nằm trong phạm vi của một char. Tôi đã thử một diễn viên rõ ràng của WIDTH đến một char, nhưng vẫn có lỗi.

+0

chỉ cần thay đổi cấu trúc của bạn để int, và xem những gì happend? –

+0

Trong trường hợp của bạn, bạn cần phải atoi hoặc tĩnh đúc cho x và y, sau đó so sánh với chiều cao và chiều rộng. –

Trả lời

14

Bạn có chắc chắn rằng char đã được ký không? Hãy thử khai báo các trường explictly như signed char và xem những gì bạn nhận được.

+0

Vâng, tôi tin rằng char là unsigned, do đó, nó so sánh với 0 mà sẽ luôn luôn là sự thật. – Wedge

+13

Nó phụ thuộc vào trình biên dịch. Nếu bạn * cần * char để được ký, bạn cần khai báo nó như đã ký. –

+0

Vâng, sửa chữa nó. Tuy nhiên, các dòng mà tôi đã nhận được một lỗi trên là những dòng mà tôi đã làm một so sánh với số dương (WIDTH và HEIGHT). Lạ thật. –

1

Hummm ... không phải là thẻ của bạn chưa được ký theo mặc định? Trong trường hợp đó phạm vi sẽ là 0-255, có nghĩa là so sánh> = 0 của bạn sẽ luôn luôn đúng

+1

Phụ thuộc vào nền tảng và trình biên dịch. Ví dụ, GCC trên x86 Linux sử dụng ký char theo mặc định, trong khi GCC trên PowerPC Linux sử dụng unsigned char theo mặc định. – ephemient

3

Tôi đoán x >= 0 gây ra cảnh báo vì char có thể được thực hiện như unsigned char.

3

Loại char có thể được ký hoặc chưa ký. Nó phụ thuộc vào sự lựa chọn của nhà cung cấp trình biên dịch của bạn. Thậm chí có thể có một tùy chọn trình biên dịch có sẵn. Rõ ràng, char không được ký cho bạn, vì vậy nó luôn lớn hơn hoặc bằng không, và do đó trình biên dịch cảnh báo bạn.

Bạn đang sử dụng char tại đây để đại diện cho "loại số chiếm tối thiểu bộ nhớ". Trong trường hợp đó, tôi khuyên bạn nên sử dụng rõ ràng signed char hoặc unsigned char. (Mỗi khác biệt với đồng bằng char, mặc dù char phải được ký hoặc chưa ký.) Đặt trước char khi bạn đang nắm giữ dữ liệu ký tự. Đối với dữ liệu số, sử dụng một trong hai loại khác.

+1

điều này được xác nhận bởi: http://www.network-theory.co.uk/docs/gccintro/gccintro_71.html – dfa

0

Tiêu chuẩn C và C++ cho phép ký tự kiểu char được ký hoặc không ký, tùy thuộc vào nền tảng và trình biên dịch. Hầu hết các hệ thống, bao gồm x86 GNU/Linux và Microsoft Windows, sử dụng ký char, nhưng dựa trên bộ xử lý PowerPC và ARM thường sử dụng ký tự unsigned (29) Điều này có thể dẫn đến kết quả không mong muốn khi chuyển các chương trình giữa các nền tảng có mặc định khác nhau cho kiểu của char.

0

Hãy thử điều này:

typedef struct Point 
{ 
    signed char x; 
    signed char y; 
} Point; 
Các vấn đề liên quan