Trong một bài báo của tờ Embedded System magazine ra tháng 7/2002 có đề cập đến một chức năng lý thú của increment và decrement operator trên những compiler. Tôi tạm dịch ngắn gọn một đoạn sau đây để các bạn tham khảo.

void f(int i, int j, int k)
{
printf("i = %d, j = %d, k = %d\n", i, j, k);
}

int main()
{
int n = 0;

f(n++, n++, n);
}

Kết quả ở trên khi tôi dùng VC++ 6.0 để compile và run nó là i = 0, j = 0, k = 0. Nhưng ngược lại khi tôi dùng một compiler khác (ARM compiler) thì kết quả lại khác: i = 1, j = 0, k = 2.
Theo như bài báo viết thì thứ tự evaluation cho function arguments không xác định, mà nó tuỳ thuộc vào compiler. Có nghĩa là mỗi compiler sẽ thực hiện chức năng đó khác nhau, và rơi vào một trong những trường hợp sau:

1) Evaluate argument từ bên trái trước và increment trước khi evaluate argument bên phải.

2) Evaluate tất cả arguments từ trái sang phải trước rồi mới increment sau cùng.

3) Evaluate tất cả arguments từ phải trước rồi mới increment.

Để xác định VC++ thuộc loại nào, tôi mới dùng decrement f(++n, ++n, n) thì kết quả là i = 2, j = 1, k = 0. Thì đúng là nó rơi vào trường hợp thứ 3, nhưng lạ một cái là trường hợp decrement thì nó decrement cho mỗi argument tại chổ chứ không chờ xong hết như trường hợp increment trên(interesting point!).

Giống như bài báo đã nói, cái ARM compiler đã cho warning: undefined behavior: 'n' khi tôi compile nó, và kết quả là nó không rơi vào một trong 3 trường hợp trên. Nó lại evaluate từ trong ra ngoài thay vì từ trái sang phải hay từ phải sang trái.

The difference between a successfull person and others is not a lack of strength, not a lack of knowledge, but rather in a lack of will.


Được biên tập bởi thiennguyen - Nguồn diendantinhoc.net