2010-09-07 5 views
6
int val = 5; 

printf("%d",++val++); //gives compilation error : '++' needs l-value 

int *p = &val; 
printf("%d",++*p++); //no error 

Ai đó có thể giải thích 2 trường hợp này? Cảm ơn.Giải thích ++ val ++ và ++ * p ++ trong C

+0

Trong những trường hợp như thế này, nó thường giúp cũng để gửi các thông báo lỗi bạn nhìn thấy và trình biên dịch (phiên bản) bạn sử dụng. – sbi

+7

Không ai có thể viết mã như thế này. – duffymo

+0

Bỏ phiếu để đóng không phải là một câu hỏi thực sự. Mã như thế này không được tìm thấy trong đời thực. Bất cứ điều gì mà chỉ là một tai nạn của cú pháp như thế này nên được chỉ vào một câu hỏi thường gặp mà chỉ nói không được ngớ ngẩn. –

Trả lời

27

++val++ giống với ++(val++). Kể từ kết quả của val++ không phải là một lvalue, điều này là bất hợp pháp. Và như Stephen Canon đã chỉ ra, nếu kết quả của val++ là một giá trị, ++(val++) sẽ là hành vi không xác định vì không có điểm chuỗi giữa ++ s.

++*p++ giống với ++(*(p++)). Vì kết quả của *(p++) một giá trị, điều này là hợp pháp.

+1

Câu trả lời xuất sắc, mặc dù tôi sẽ lưu ý rằng ngay cả khi 'val ++' là một giá trị, hành vi vẫn sẽ không được xác định. Ví dụ '(++ val) ++' trong C++ sẽ gọi hành vi không xác định. –

+0

@Stephen: Rất tốt, tôi sẽ thêm nó vào câu trả lời. – sepp2k

+1

Toán tử tăng sau luôn trả về 'rvalue' (trong C cũng như trong C++). Trong C++, '(++ val) ++' gọi hành vi Undefined bởi vì toán tử pre-increment ('++') trả về một giá trị (trong C++) và giá trị 'val' đang được sửa đổi nhiều hơn một lần giữa hai điểm chuỗi . –

0

int j = ++val++; //gives compilation error

Đó bởi vì bạn không thể xem trước increment một rvalue. ++val++ được hiểu là ++(val++) vì toán tử tăng sau có ưu tiên cao hơn toán tử tăng trước. val++ trả về một toán tử rvalue và tiền gia tăng yêu cầu toán hạng của nó là lvalue. :)

int k = ++*p++; //no error

++*p++ được hiểu như là ++(*(p++)), đó là hoàn toàn hợp lệ.

4

Biểu thức ++val++ giống với (++val)++ (hoặc có lẽ ++(val++), dù sao nó không liên quan lắm). Kết quả của toán tử ++ không phải là biến, mà là giá trị và bạn không thể áp dụng toán tử cho một giá trị.

Biểu thức ++*p++ giống với ++(*(p++)). Kết quả của p++ là giá trị, nhưng kết quả của *(p++) là vị trí bộ nhớ, có thể áp dụng toán tử ++.

+0

'++ val ++' là giống như '++ (val ++)', là ** không ** giống như '(++ val) ++'. (Mặc dù trong C, cả hai đều không hợp lệ về cú pháp) –

+0

@Stephen Canon: Vâng, nó chỉ không rõ ràng cái nào nó đánh giá. Khi biểu thức không hợp lệ, tôi không bao giờ bận tâm tìm hiểu xem hai biến thể không hợp lệ nào.:) – Guffa

+0

ah, nhưng trong C++, một trong số chúng không hợp lệ trong khi cái còn lại là hợp lệ nhưng không xác định ngữ nghĩa. (C++ là wacky!) –

1

cũng lưu ý rằng bạn đang thay đổi địa chỉ của con trỏ bởi

int k = ++*p++; 
+0

vâng tôi biết điều đó. Tôi đã sử dụng nó để đơn giản. Thay vì int val, tôi có thể đã sử dụng mảng int. – understack