2013-09-04 30 views
14

Một lần nữa, tôi đang dạy lớp học để trả lời câu hỏi của sinh viên về C. Đây là câu trả lời cho tôi: Có lý do nào sau khi chấp nhận signed làm công cụ sửa đổi mặc định cho C? Người ta có thể nghĩ rằng unsigned là sự lựa chọn tự nhiên. Vì vậy, đây thực sự là một quyết định thiết kế?được ký như mặc định trong C

+3

Bản thân "lý do" không hoàn toàn chính xác. Đối với 'char' đơn giản, nó không phải lúc nào cũng là' signed'. –

+0

Tại sao int không dấu sẽ tự nhiên hơn? Tôi nghĩ rằng hầu hết các vấn đề thế giới thực đều đối phó với cả giá trị tích cực và tiêu cực. – jxh

+0

@jxh Thêm vào vấn đề, hầu hết các vấn đề trên thế giới thực đều đối phó với số _small_ - tức là, con số tương đối gần 0. Tôi nghĩ hầu hết mọi người trong hầu hết các trường hợp đều có nhiều khả năng cần số dưới đây (hoặc ít nhất gần) 0 thì chúng cần số lớn hơn (hoặc thậm chí gần đến) MAX_INT. Các con số đã ký giữ cả hai giới hạn trên và dưới cách xa các số được sử dụng phổ biến nhất có thể. –

Trả lời

15

Xét về mặt chuẩn (vì câu hỏi của bạn được gắn thẻ như vậy), signed được đánh dấu như là mặc định vì đó là cách nó đã được với việc triển khai C đi kèm trước tiêu chuẩn.

Nhiệm vụ chuẩn ANSI/ISO ban đầu là để mã hóa thực tiễn hiện tại thay vì tạo ngôn ngữ mới. Do đó hành vi của hiện thực trước tiêu chuẩn là yếu tố quan trọng nhất, theo các tài liệu lý do:

Điều lệ X3J11 gốc được uỷ quyền rõ ràng việc hệ thống hóa thực tế đang tồn tại phổ biến, và Ủy ban C89 tổ chức nhanh để tiền lệ bất cứ nơi nào mà rõ ràng và rõ ràng.

Phần lớn ngôn ngữ được xác định bởi C89 giống hệt như đã được định nghĩa trong Phụ lục A của ấn bản đầu tiên của Ngôn ngữ lập trình C của Brian Kernighan và Dennis Ritchie, và như đã được thực hiện ở hầu hết các dịch giả C thời gian . (Tài liệu này được gọi tắt là K & R.)

Nếu bạn đang tìm kiếm để tìm hiểu lý do tại sao việc triển khai trước tiêu chuẩn ưu tiên signed, có thể bạn sẽ phải nhìn vào kiến ​​trúc của PDP- n máy UNIX và C được phát triển ban đầu.

Trang History of C cho thấy unsigned đã thực sự là một người đến trễ so với ngôn ngữ, xuất hiện đôi khi trong những năm 70 của giữa:

Trong 1973-1980, ngôn ngữ phát triển một chút: cơ cấu loại đã đạt được unsigned, các loại dài, công đoàn và đếm, và các cấu trúc trở thành các đối tượng gần như hạng nhất (chỉ thiếu một ký hiệu cho các chữ).

+0

Hah. Nó thật thú vị. Tôi đang nghiêng về phía câu trả lời này, nhưng nhận thấy rằng nó vẫn còn đặt câu hỏi một chút: tại sao các triển khai C trước đó lại có 'ký' làm mặc định? –

+2

@Dervin, Tại sao không? Loại 'signed' phù hợp với cả giá trị dương và âm, được sử dụng trong cuộc sống hàng ngày. –

+0

@Eric, Phải, chỉ là tôi nghĩ những người sửa đổi đã xuất hiện cùng một lúc (tôi đã sai khi giả định), vì vậy tôi đã ở trong giai đoạn thiết kế ngôn ngữ, tôi đã thực hiện char unsigned và yêu cầu người lập trình nói với tôi một cách rõ ràng nếu anh ta muốn khác. Lịch sử là soo interesing! –

0

Ký mặc định là char không được ngôn ngữ xác định. Nó được xác định bởi việc thực hiện. Một số CPU được ký tự nhiên hơn char, và những người khác là tự nhiên unsigned.

+0

ý của bạn là "tự nhiên" được ký? –

+0

@DervinThunk: Độ tự nhiên của các hướng dẫn để mở rộng một số lượng 8 bit đến 16 bit hoặc lớn hơn có các giả định cụ thể được tích hợp sẵn, đặc biệt là các CPU trước khoảng năm 1985 hoặc lâu hơn. Để thúc đẩy một char đến một int theo hướng * không tự nhiên * yêu cầu thêm hướng dẫn để làm cho nó như vậy. Hướng * tự nhiên * chỉ yêu cầu một lệnh duy nhất. – wallyk

+0

@wallyk, Bạn có chắc là tiêu chuẩn không ủy quyền cho sự ký kết của 'int' đơn giản? Tôi nhớ tiêu chuẩn không ủy thác phạm vi nhỏ nhất của các giá trị có thể được reprensented bởi 'int'. Xem http://stackoverflow.com/questions/6155784/range-of-values-in-c-int-and-long-32-64-bits –

3

Theo The Development of the C Language, khái niệm về unsigned là một mở rộng của ngôn ngữ khi tính năng đã được thêm vào nó giữa 1973 và 1980. Mặc dù không quy định rõ ràng, câu chuyện cho thấy nó không được giới thiệu đến năm 1977 (xem Tính di động, khoản 3).

Vì vậy, mặc định là đã ký do thực tế là ngôn ngữ ban đầu chỉ có các loại đã ký.

5

Phần lớn về khả năng tương thích ngược và nguồn gốc của C từ các ngôn ngữ trước đó không thể dễ dàng hỗ trợ cả số nguyên đã ký và chưa ký.

C có nguồn gốc từ một ngôn ngữ cũ hơn được gọi là B, được bắt nguồn từ một ngôn ngữ cũ hơn gọi là BCPL (là phiên bản CPL đơn giản).

BCPL đa ngôn ngữ untyped.Một khai báo biến không xác định kiểu của một đối tượng; thay vào đó, một hoạt động trên một biến nhất định sẽ xử lý nó như thể nó là một kiểu đã cho.

Các nhà khai thác BCPL +, -, *, /, và REM điều trị toán hạng của họ như số nguyên, và mang lại kết quả số nguyên.

Nếu BCPL đã hỗ trợ số nguyên chưa được ký, thì có thể phải có một toán tử toán tử chưa ký khác hoặc không thể đại diện cho số âm. (Lưu ý rằng BCPL không hỗ trợ dấu phảy động.)

Cú pháp của B hoàn toàn khác với cú pháp của BCPL (và gần hơn với C), nhưng nó vẫn giữ được nhiều ngữ nghĩa giống nhau. Cụ thể, các biến và hàm là kiểu số nguyên theo mặc định - và không có từ khóa unsigned.

Sớm, dựa trên B, cũng không có từ khóa unsigned. Nó chỉ có bốn loại số cơ bản: char, int, floatdouble. (unsigned đã được thêm, cùng với long, unionenum, một số thời gian từ năm 1973 đến 1980.) Do tính chất yếu kém của ngôn ngữ, các lập trình viên đôi khi sử dụng con trỏ khi chúng cần số học chưa ký.

Tính năng "" mà một thực thể không có loại tuyên bố là hoàn toàn thuộc loại int được giữ lại trong C cho đến khi tiêu chuẩn ISO 1999 cuối cùng đã loại bỏ quy tắc "ngụ ý int".

Ngoài ra, các loại số nguyên đã ký chỉ có xu hướng nhiều hơn hữu ích hơn loại chưa ký. Khả năng biểu diễn các giá trị âm có thể cực kỳ tiện lợi. Với ngữ nghĩa bao quanh điển hình, một lỗi trong phép trừ chưa ký của hai giá trị nhỏ có thể mang lại giá trị dương lớn (ví dụ: 3 - 4 == 65535, đối với loại không dấu 16 bit). Ngay cả trong miền lập trình hệ thống là mục tiêu chính của tất cả các ngôn ngữ này, đôi khi cần thiết để biểu thị các giá trị âm (ví dụ: thay đổi về một số lượng).

Tài liệu tham khảo:

0

unsigned ngữ nghĩa được đảm bảo đơn giản hơn: modulo base-2 n không có ngoại lệ. Nhưng đừng đưa ra giả định về những gì n là: kích thước của phạm vi không bắt buộc phải bằng với loại tương ứng đã ký.

Yêu cầu duy nhất là tất cả các giá trị đã ký tích cực cũng có thể được thể hiện bằng loại không dấu tương ứng.

Việc triển khai hợp lệ unsigned sẽ là sử dụng số học có chữ ký bổ sung của hai và không sử dụng bit dấu sau mỗi thao tác.Điều này không có khả năng xuất hiện trong cuộc sống thực, nhưng các máy có số học bổ sung không hai có thể gặp nhiều rắc rối hơn khi cố gắng bỏ qua logic số âm.

Trong thực tế, số âm là một tính năng thiết yếu của bất kỳ nền tảng phần cứng nào, nhưng khả năng xử lý toàn bộ đăng ký dưới dạng số dương chỉ là đóng băng trên bánh. C được thiết kế để quấn chặt chẽ nhất xung quanh phần hiệu quả nhất của phần cứng.

Các vấn đề liên quan