2011-12-04 96 views
9

Trong C tại sao không có bộ định danh chuẩn để in một số ở định dạng nhị phân, sth như %b. Chắc chắn, người ta có thể viết một số chức năng/hacks để làm điều này nhưng tôi muốn biết tại sao một điều đơn giản như vậy không phải là một phần tiêu chuẩn của ngôn ngữ.Biểu diễn nhị phân trong C

Có một số quyết định thiết kế đằng sau nó không? Vì có các định dạng thông số định dạng cho bát phân% o và% x cho hệ thập lục phân là nó là bát phân và hệ thập lục phân có phần "quan trọng hơn" so với biểu diễn nhị phân.

Từ Trong C/C++ người ta thường gặp các nhà khai thác Bitwise Tôi tưởng tượng rằng nó sẽ hữu ích để có %b hoặc trực tiếp đầu vào một đại diện nhị phân của một số thành một biến (cách một đầu vào số thập lục phân như int i=0xf2)

Lưu ý: Các chủ đề như this chỉ thảo luận về phần 'cách' thực hiện việc này và không phải là 'tại sao'

+4

Tại sao in nhị phân nếu bạn có thể in hex? Về cơ bản nó giống nhau, nhưng ở mật độ 400%. Chỉ dịch, '0 = 0000',' 1 = 0001', '2 = 0010', ...,' F = 1111'. –

+0

@KerrekSB - Chỉ vì nó không phải là khó để làm cho mình không phải là một lý do thuyết phục để loại trừ nó khỏi ngôn ngữ. Đó là một nỗi đau khi phải chuyển từ viết sang luồng để ghi vào bộ đệm chuỗi, dịch và sau đó ghi vào luồng. –

+0

@TedHopp: Một khi có thể tranh cãi theo cách khác thì tại sao cần * *. Bạn có thể yêu cầu tất cả các loại công cụ được đưa vào (base-4? Base-64?), Nhưng cuối cùng không có câu trả lời đúng hay sai. Các nhà thiết kế có lẽ không nghĩ rằng nó là cần thiết. Tôi tưởng tượng ra rằng bất cứ ai trong kinh doanh của thao tác nhị phân sẽ đủ thông thạo hex ... –

Trả lời

3

Lý do chính là 'lịch sử', tôi tin. Những người triển khai ban đầu của printf() et al tại AT & T không có nhu cầu về nhị phân, nhưng đã cần bát phân và thập lục phân (cũng như số thập phân), vì vậy đó là những gì đã được triển khai. Tiêu chuẩn C89 khá cẩn thận để chuẩn hóa thực hành hiện tại - nói chung. Có một vài phần mới (ngôn ngữ, và các nguyên mẫu hàm tất nhiên, mặc dù đã có C++ để cung cấp 'kinh nghiệm thực hiện' cho những phần đó).

Bạn có thể đọc số nhị phân với strtol() et al; xác định một cơ sở của 2. Tôi không nghĩ rằng có một cách thuận tiện để định dạng số trong các căn cứ khác nhau (khác với 8, 10, 16) đó là nghịch đảo của strtol() - có lẽ nó phải là ltostr().

+3

"Những người triển khai ban đầu của printf() et al tại AT & T không có nhu cầu về nhị phân, nhưng đã cần bát phân và thập lục phân (cũng như số thập phân), vì vậy đó là những gì đã được triển khai." - Bạn có bất kỳ bằng chứng nào cho yêu cầu này không? Bạn có thể nói rằng họ chỉ đơn giản muốn chúng ta có một thời gian khó khăn khi gỡ lỗi các hoạt động bit. "Tôi không nghĩ rằng có một cách thuận tiện để định dạng số trong các căn cứ khác nhau" - Tại sao bạn nghĩ vậy? Một lần nữa, bạn tuyên bố mọi thứ mà không cần bất kỳ lời giải thích nào. – kol

+0

Nếu người triển khai đã cần đầu ra nhị phân, nó sẽ được cung cấp. Nó không được cung cấp; nó là hợp lý để suy ra họ không cần nó. Sổ tay UNIX phiên bản thứ 7 (có sẵn trực tuyến) không có bất kỳ hỗ trợ nào để chuyển đổi các chuỗi chữ số nhị phân thành số nguyên. Đối với 'định dạng số trong các căn cứ khác nhau', tôi giới thiệu bạn đến tiêu chuẩn C - có chức năng nào trong tiêu chuẩn cho phép bạn định dạng một số trong cơ sở 2 hoặc cơ sở 36 không? Tôi không nghĩ vậy. Nếu bạn muốn trích dẫn một ví dụ ngược, hãy đặt tên cho hàm đó; nó rất dễ dàng để cung cấp bằng chứng rằng tôi sai nếu tôi sai. –

+0

Hãy nhớ rằng: UNIX được viết bởi những người đã sử dụng hệ thống. Họ tự cung cấp (và chúng tôi) với các công cụ đáp ứng yêu cầu của họ. –

1

Một câu trả lời có thể là định dạng thập lục phân nhỏ gọn hơn nhiều. Xem ví dụ như xem hexa của Lister Total Commander.

% b sẽ hữu ích trong nhiều trường hợp thực tế. Ví dụ, nếu bạn viết mã để phân tích các gói mạng, bạn phải đọc các giá trị của các bit, và nếu printf sẽ có% b, việc gỡ lỗi mã đó sẽ dễ dàng hơn nhiều. Ngay cả khi bỏ qua% b có thể được giải thích khi printf được thiết kế, nó chắc chắn là một ý tưởng tồi.

3

Bạn hỏi "tại sao" như thể phải có lý do rõ ràng và thuyết phục, nhưng thực tế là không có lý do kỹ thuật để không hỗ trợ định dạng %b.

K & R C được tạo ra là những người đóng khung ngôn ngữ để đáp ứng những gì họ nghĩ sẽ là trường hợp sử dụng phổ biến của họ. Một lực lượng đối lập đang cố giữ thông số ngôn ngữ càng đơn giản càng tốt.

ANSI C được chuẩn hóa bởi một ủy ban có thành viên có sở thích đa dạng. Rõ ràng %b không kết thúc là ưu tiên chiến thắng.

Ngôn ngữ do nam giới tạo ra.

2

Lý do chính khi tôi thấy đó là biểu diễn nhị phân nào nên sử dụng? bổ sung của ai? bổ sung của hai? bạn đang mong đợi các bit thực tế trong bộ nhớ hoặc đại diện số trừu tượng?

Chỉ điều kiện thứ hai có ý nghĩa khi C không yêu cầu kích thước từ hoặc đại diện số nhị phân. Vì vậy, vì nó sẽ không được các bit trong bộ nhớ, chắc chắn bạn muốn đọc số trừu tượng trong hex?

Đòi một đại diện trừu tượng là "nhị phân" có thể dẫn đến niềm tin rằng -0b1^0b1 == 0 có thể đúng hoặc -0b1 | -0b10 == -0b11


cơ quan đại diện có thể:

Trong khi chỉ có một đại diện hex ý nghĩa - - phần tóm tắt, số -0x79 có thể được thể hiện dưới dạng nhị phân dưới dạng:

  • -1111001 (số trừu tượng)
  • 11111001 (bổ sung của một người)
  • 10000111 (bổ sung hai nhân)

@ Eric đã thuyết phục tôi rằng endianness! = Trái sang phải theo thứ tự ...

vấn đề còn phức tạp hơn khi số không phù hợp với một byte. cùng một số có thể là:

  • 1000000001111001 như một bổ sung cho one's lớn-endian số 16bit
  • 1111111110000111 như một two's-bổ sung lớn về cuối nhỏ số 16bit
  • 1000011110000000 như một của một người -hoàn thành số 16 bit ít người kết thúc
  • 1000011111111111 là số 16 bit nhỏ bổ sung của hai số

Khái niệm về tính xác thực và biểu diễn nhị phân không áp dụng cho số hex vì không có cách nào chúng có thể được xem là biểu diễn bit trong bộ nhớ thực tế.

Tất cả những ví dụ giả một byte 8-bit, mà C không đảm bảo của (máy lịch sử thực sự đã có với byte 10 bit)


Tại sao không có quyết định là tốt hơn so với bất kỳ quyết định:

Rõ ràng người ta có thể tùy ý chọn một đại diện hoặc để nó được thực hiện xác định. Tuy nhiên:

  • nếu bạn đang cố gắng sử dụng này để gỡ lỗi Bitwise hoạt động, (mà tôi xem như là lý do thuyết phục duy nhất để sử dụng hệ nhị phân trên hex) bạn muốn sử dụng một cái gì đó gần gũi những gì các phần cứng sử dụng, mà làm cho nó không thể tiêu chuẩn hóa, vì vậy bạn muốn thực hiện được xác định.
  • Ngược lại nếu bạn đang cố gắng đọc chuỗi bit, bạn cần định dạng chuẩn, không được triển khai.
  • Và bạn chắc chắn muốn printf và scanf sử dụng như nhau.

Vì vậy, có vẻ như với tôi không có phương tiện vui vẻ nào.

+1

Làm thế nào để biểu diễn nhị phân? "? – Eric

+0

@Eric vì chỉ có một biểu diễn hex --- phần tử trừu tượng. xem chỉnh sửa của tôi – tobyodavies

+0

Endianess không liên quan đến các khái niệm về bên phải hoặc trái - bạn có thể chọn bất cứ thứ tự nào bạn muốn hiển thị các bit.Nếu tôi viết '0xAACC', đó là rõ ràng' 0b1010101011001100'. Tôi vẫn không làm theo những gì làm cho nhị phân trong một lớp khác nhau để hex, khi có một 1-1 bản đồ giữa chúng. – Eric

0

Tôi đồng ý. Tôi là một người tham gia trong ủy ban ANSI C ban đầu và đưa ra đề xuất để bao gồm một biểu diễn nhị phân trong C. Tuy nhiên, tôi đã bỏ phiếu xuống, vì một số lý do được đề cập ở trên, mặc dù tôi vẫn nghĩ rằng nó sẽ khá hữu ích khi thực hiện, ví dụ , hoạt động bitwise, v.v.

Điều đáng lưu ý là ủy ban ANSI là phần lớn bao gồm các nhà phát triển trình biên dịch, chứ không phải người dùng và lập trình viên C. Mục tiêu của họ là làm cho các nhà phát triển trình biên dịch dễ hiểu đối với các lập trình viên C, và có thể làm như vậy với một tài liệu không còn cần thiết nữa, ngay cả khi điều này có nghĩa là nó khó đọc đối với các lập trình viên C.

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