Tại sao là ++ ++ ++ ++ không hợp lệ trong khi (++ i) ++ là hợp lệ?


14

Hãy xem xét các mã sau đây:

int main() {
    int i = 2;
    int b = ++i++;
    return 3;
}

Nó biên dịch với lỗi sau:

<source>: In function 'int main()':

<source>:3:16: error: lvalue required as increment operand

    3 |     int b = ++i++;

      |                ^~

Điều này nghe có vẻ công bằng với tôi. Gia tăng tiền tố có mức độ ưu tiên cao hơn mức tăng tiền tố, do đó mã được phân tích cú pháp dưới dạng int b = ++(i++);ilà một giá trị. Do đó có lỗi.

Bây giờ chúng ta hãy xem xét biến thể này với dấu ngoặc đơn để ghi đè các ưu tiên mặc định:

int main() {
    int i = 2;
    int b = (++i)++;
    return 3;
}

Mã này biên dịch và trả về 3. Bản thân nó, điều này nghe có vẻ công bằng với tôi nhưng có vẻ mâu thuẫn với mã đầu tiên.

Câu hỏi: tại sao (++i)lvaluekhi ikhông?

Cảm ơn!

CẬP NHẬT: thông báo lỗi hiển thị ở trên là từ gcc (x86-64 9.2). Đây là kết xuất chính xác: lỗi với gcc

Clang x86-64 9.0.0 có một thông báo khá khác: lỗi với tiếng kêu

<source>:3:13: error: expression is not assignable

    int b = ++i++;

            ^ ~~~

Với GCC, bạn có ấn tượng rằng vấn đề xảy ra với toán tử postfix và sau đó bạn có thể đi lang thang tại sao ++ivẫn ổn trong khi ikhông, vì vậy câu hỏi của tôi. Với Clang, rõ ràng hơn là vấn đề với toán tử tiền tố.


Điều này ban đầu được gắn thẻ với C, nó chắc chắn không hợp lệ C.
Antti Haapala

Quả thực xin lỗi! Tôi cho rằng hành vi tương tự trong C ...
Bktero

Câu trả lời:


23

i++ilà cả hai giá trị, nhưng i++là một giá trị .

++(i++)không thể hợp lệ, vì tiền tố ++đang được áp dụng i++, đó là một giá trị. Nhưng (++i)++vẫn ổn vì ++ilà một giá trị.

Lưu ý rằng trong C, tình hình là khác nhau; i++++ilà cả hai giá trị. (Đây là một ví dụ về lý do tại sao mọi người nên ngừng giả định rằng C và C ++ có cùng quy tắc. Mọi người chèn các giả định này vào câu hỏi của họ, sau đó phải được bác bỏ.)


4

Tuyên bố này

int b = ++i++;

tương đương với

int b = ++( i++ );

Toán tử gia tăng hậu tố trả về giá trị của toán hạng trước khi tăng.

Từ Tiêu chuẩn C ++ 17 (8.2.6 Tăng và giảm)

1 Giá trị của biểu thức postfix ++ là giá trị của toán hạng của nó ... Kết quả là một giá trị .

Trong khi toán tử gia tăng đơn nguyên trả về giá trị sau khi tăng. Vì vậy, tuyên bố này

int b = (++i)++;

có giá trị Bạn có thể viết ví dụ

int b = (++++++++i)++;

Từ Tiêu chuẩn C ++ 17 (8.3.2 Tăng và giảm)

1 Toán hạng của tiền tố ++ được sửa đổi bằng cách thêm 1. Toán hạng sẽ là một giá trị có thể sửa đổi. Loại toán hạng phải là loại số học khác với cv bool hoặc con trỏ tới loại đối tượng được xác định hoàn toàn. Kết quả là toán hạng cập nhật; nó là một giá trị và nó là trường bit nếu toán hạng là trường bit ....

Hãy chú ý rằng trong C, cả hai toán tử trả về một giá trị thay vì giá trị. Vì vậy, trong C tuyên bố này

int b = (++i)++;

không có hiệu lực.


3

vì vậy mã được phân tích cú pháp là int b = ++ (i ++); và tôi là một giá trị.

Số ikhông phải là một giá trị. ilà một giá trị. i++là một giá trị (prvalue là cụ thể).

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.