Tại sao sizeof được gọi là toán tử thời gian biên dịch?


12

Ban đầu, đây là một phần của một câu hỏi khác .

Tại sao được sizeofgọi là toán tử thời gian biên dịch? Nó không thực sự là một nhà điều hành thời gian chạy? Và nếu nó thực sự là một toán tử thời gian biên dịch, làm thế nào nó giúp tạo ra mã di động chạy giống nhau trong các máy tính khác nhau? Hãy giải thích chi tiết.


4
đã trả lời chi tiết tại SO: Tại sao sizeof (x ++) không tăng x?
gnat

3
Làm thế nào để bạn mong đợi kích thước của một loại sẽ thay đổi trong thời gian chạy?

@MichaelT: Kích thước của một thể hiện của một loại chắc chắn có thể thay đổi - xét cho cùng, đó là đa hình lớp. Tôi cho rằng sizeof(polymorphic_ptr*)việc không đổi là khá trực quan và chỉ là ngớ ngẩn. Vâng, đó là cách C ++, nhưng vẫn ngớ ngẩn.
Phục hồi Monica

@KubaOber Thật vậy. Tôi chỉ tò mò làm thế nào OP nghĩ rằng nó nên hành xử trong các trường hợp khác nhau và hy vọng nhận được một số mã sẽ chứng minh sự nhầm lẫn của mình về điều này để giúp mở rộng câu hỏi.

4
Đã đưa ra câu trả lời "bởi vì nó hoạt động vào thời gian biên dịch", đã thất vọng.
Ben Jackson

Câu trả lời:


23

sizeof()cung cấp cho bạn kích thước của kiểu dữ liệu , không phải kích thước của một thể hiện cụ thể của loại đó trong bộ nhớ.

Ví dụ: nếu bạn có một đối tượng dữ liệu chuỗi được phân bổ một mảng ký tự có kích thước thay đổi trong thời gian chạy, sizeof()thì không thể sử dụng để xác định kích thước của mảng ký tự đó. Nó sẽ chỉ cung cấp cho bạn kích thước của con trỏ.

Kích thước của một kiểu dữ liệu luôn được biết đến tại thời điểm biên dịch.


3
Bởi vì C (++) không có siêu dữ liệu đối tượng thời gian chạy, bạn cũng không thể có được những thứ đó vào thời gian chạy.
C. Ross

5
Trên thực tế, nếu bạn sử dụng sizeoftrên một mảng, bạn sẽ nhận được kích thước của mảng (đó là kích thước phần tử nhân với số lượng phần tử). Nhưng nếu bạn sử dụng nó trên một con trỏ, bạn chỉ nhận được kích thước của con trỏ. Vì vậy, vì trong hầu hết các trường hợp bạn muốn biết kích thước của một mảng, bạn chỉ có một con trỏ, nó không hữu ích lắm.
sepp2k

1
@Jens Câu hỏi được gắn thẻ [C ++] và VLA không đưa nó vào tiêu chuẩn C ++.
authchir

13

bởi vì toàn bộ "cuộc gọi" của sizeof được tính toán tại thời điểm biên dịch và bất cứ điều gì nằm giữa dấu ngoặc đơn đều bị loại bỏ và không chạy trong thời gian chạy,

kết quả hoàn toàn dựa trên thông tin loại tĩnh có sẵn cho trình biên dịch


7

Tại sao sizeof được gọi là toán tử thời gian biên dịch?

Bởi vì, tại thời gian biên dịch, trình biên dịch sẽ tính toán kích thước của biểu thức và thay thế giá trị hằng số thời gian biên dịch.

Nó không thực sự là một nhà điều hành thời gian chạy?

Không. Bạn thậm chí có thể sử dụng sizeofđể đánh giá kích thước của biểu thức mà bạn không thể thực thi một cách hợp pháp (nghĩa là điều đó sẽ phát sinh Hành vi không xác định), miễn là trình biên dịch có thể tìm ra loại biểu thức là gì.

Ngoài ra, ngay cả trước C ++ 11 constexpr, bạn có thể sử dụng sizeofbiểu thức theo cách bạn không thể sử dụng biểu thức thời gian chạy.

Và nếu nó thực sự là một toán tử thời gian biên dịch, thì nó giúp ích như thế nào trong việc tạo mã di động ...

Các loại có thể khác nhau về kích thước trên các nền tảng khác nhau. Sử dụng các sizeofbiểu thức thay vì các giả định được mã hóa cứng có nghĩa là mã của bạn sẽ không bị hỏng khi bạn biên dịch trên một nền tảng khác và các loại của bạn thay đổi kích thước.


1
Vâng, tôi thấy đây là câu trả lời hữu ích nhất;). Bro (giả sử bạn là nam), tôi có một nghi ngờ. Bạn có muốn nói rằng khi mọi người nói rằng sizeof làm cho các chương trình có thể di động được không, điều đó có nghĩa là mã nguồn có thể được biên dịch mà không có bất kỳ lỗi nào trong tất cả các máy và chúng không có nghĩa là chương trình thực thi có thể chạy trong bất kỳ máy nào. Đúng ? Nếu điều này là đúng, nghi ngờ của tôi sẽ thực sự được giải tỏa.
Bộ giải mã hòa bình

1
Vâng, là di động, theo nghĩa bạn có thể biên dịch một nhị phân chính xác (khác nhau) cho mỗi nền tảng.
Vô dụng

5

C ++ không thực sự lưu trữ siêu dữ liệu cho các đối tượng trong thời gian chạy để kiểm tra kích thước phải được biên dịch thời gian. Để biết ví dụ về cách C ++ không xác thực kích thước, hãy khai báo một mảng có intkích thước tùy ý và đọc qua phần cuối của nó. Nếu bạn may mắn, bạn sẽ nhận được segfaultnhưng nhiều khả năng bạn sẽ chỉ đọc vô nghĩa, vì C ++ không theo dõi kích thước của mảng của bạn.

Xem một lỗi phân tách chương trình C / C ++ có thể đọc qua phần cuối của một mảng (UNIX) không? cho một ví dụ từ SO.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.