2015-11-15 46 views
7

Tôi tin rằng cho đến khi C++ 14 một trường bit của cấu trúc được khai báo là int vẫn được hiểu là signed hoặc unsigned, việc diễn giải đang được thực hiện được xác định. Tham chiếu: http://en.cppreference.com/w/cpp/language/bit_field.Trường bit đã ký trong C++ 14

Đây có phải là trường hợp trong C++ 14 không? I.e, là mã dưới đây có được bảo đảm để hoạt động như inteded?

#include <iostream> 

struct X 
{ 
    int f:3; 
}; 

int main() 
{ 
    X x; 
    x.f = -2; // is this going to be indeed signed? It seems so. 
    std::cout << x.f << std::endl; // displays -2 
} 
+4

[CWG 739] (http://wg21.link/CWG739). Đó là một DR. –

+0

@ T.C. Làm thế nào để bạn biết tất cả các DR - oO (cũng, xin vui lòng xem xét đăng một câu trả lời. Điều này là hữu ích) – sehe

+0

@sehe Tôi cũng yêu cầu bản thân mình cùng một điều :) – vsoftco

Trả lời

6

Theo C++ 11 tiêu chuẩn §9.6/p3 Bit-lĩnh vực [class.bit] (Nhấn mạnh Mine):

A-trường bit sẽ không phải là một tĩnh hội viên. Trường bit phải có loại tách rời hoặc liệt kê (3.9.1). Đó là thực hiện xác định liệu một đồng bằng (không phải ký kết một cách rõ ràng và cũng không unsigned) char, short, int, long, hoặc long long bit lĩnh vực được ký kết hoặc unsigned. A bool giá trị có thể được lưu trữ thành công trong trường bit của bất kỳ kích thước nào khác. Địa chỉ của toán tử & sẽ không được áp dụng cho trường bit, do đó, không có con trỏ đến bitfields. Tham chiếu không const sẽ không bị ràng buộc vào trường bit (8.5.3). [Lưu ý: Nếu bộ khởi tạo cho tham chiếu của loại const T & là một giá trị tham chiếu đến trường bit, tham chiếu bị ràng buộc với giá trị tạm thời được giữ để giữ giá trị của trường bit ; tham chiếu không bị ràng buộc trực tiếp vào trường bit. Xem 8.5.3. —end note]

Vì vậy, bạn đã chính xác cho phần đầu tiên. Thật vậy cho đến khi C++ 14 một trường bit của một cấu trúc được khai báo là signed vẫn được hiểu là signed hoặc unsigned, việc diễn giải đang được thực hiện được xác định.

Như đã đề cập trong nhận xét này bởi @T.C. Báo cáo lỗi đề cập đến vấn đề đã được thực hiện DR739, DR675. Kết quả là độ phân giải sau trong C++ chuẩn 14:

Các từ ngữ "Đó là thực hiện xác định liệu một đồng bằng (không phải ký kết một cách rõ ràng và cũng không unsigned) char, short, int, long, hoặc long long bit lĩnh vực được ký kết hoặc chưa được ký. ", đã bị xóa và từ C++ 14 bây giờ là:

Trường bit không phải là thành viên tĩnh. Trường bit phải có loại tách rời hoặc liệt kê (3.9.1). Giá trị bool thành công có thể là được lưu trữ trong một trường bit của bất kỳ kích thước nào khác. Địa chỉ của toán tử & sẽ không được áp dụng cho trường bit, do đó không có con trỏ tới các trường bit . Tham chiếu không const sẽ không bị ràng buộc vào trường bit (8.5.3). [Lưu ý: Nếu bộ khởi tạo cho tham chiếu kiểu const T & là một giá trị tham chiếu đến trường bit, thì tham chiếu bị ràng buộc thành tạm thời được khởi tạo để giữ giá trị của trường bit; tham chiếu không bị ràng buộc trực tiếp vào trường bit. Xem 8.5.3.-end lưu ý ]

Cũng trong §C.1.8 khoản 9: lớp [diff.class] phần sau đã được bổ sung:

9,6

Thay đổi: Bit Các trường kiểu int đơn giản được ký.

Lý do: Rời lựa chọn ký kết để triển khai có thể dẫn đến các định nghĩa không nhất quán về các chuyên ngành mẫu . Để nhất quán, tự do triển khai cũng bị loại bỏ đối với các loại không phụ thuộc .

Ảnh hưởng đến tính năng ban đầu: Lựa chọn được thực hiện xác định trong C, nhưng không phải như vậy trong C++.

Khó chuyển đổi: Chuyển đổi cú pháp.

Cách sử dụng rộng rãi: Hiếm khi.

Do đó, trong C++ 14 bit lĩnh vực loại đồng bằng int được ký và mã đăng tải được đảm bảo để làm việc như dự định.

+0

Văn bản màu xanh lá cây trong CW 739 nói rằng thay đổi chỉ áp dụng cho các loại phụ thuộc. Văn bản đó có thực sự không được chấp nhận không? –

+0

@ M.M Có hai PR cho DR đó. Tháng 2 năm 2012 là ứng dụng được áp dụng. –