Bạn đã nghe nhầm. Nó có thể "i++"an toàn theo luồng đối với một trình biên dịch cụ thể và kiến trúc bộ xử lý cụ thể nhưng nó không bắt buộc trong các tiêu chuẩn. Trên thực tế, vì đa luồng không phải là một phần của tiêu chuẩn ISO C hoặc C ++ (a) , bạn không thể coi bất cứ thứ gì là an toàn cho luồng dựa trên những gì bạn nghĩ rằng nó sẽ biên dịch xuống.
Nó khá khả thi ++icó thể biên dịch thành một chuỗi tùy ý như:
load r0,[i] ; load memory into reg 0
incr r0 ; increment reg 0
stor [i],r0 ; store reg 0 back to memory
sẽ không an toàn theo luồng trên CPU (tưởng tượng) của tôi không có hướng dẫn tăng bộ nhớ. Hoặc nó có thể thông minh và biên dịch nó thành:
lock ; disable task switching (interrupts)
load r0,[i] ; load memory into reg 0
incr r0 ; increment reg 0
stor [i],r0 ; store reg 0 back to memory
unlock ; enable task switching (interrupts)
nơi lockvô hiệu hóa và unlockcho phép ngắt. Tuy nhiên, ngay cả khi đó, điều này có thể không an toàn theo luồng trong một kiến trúc có nhiều hơn một trong các CPU này chia sẻ bộ nhớ ( lockchỉ có thể vô hiệu hóa các ngắt cho một CPU).
Bản thân ngôn ngữ (hoặc các thư viện cho nó, nếu nó không được tích hợp sẵn trong ngôn ngữ) sẽ cung cấp các cấu trúc an toàn cho luồng và bạn nên sử dụng những cấu trúc đó thay vì phụ thuộc vào sự hiểu biết của bạn (hoặc có thể hiểu nhầm) về mã máy nào sẽ được tạo.
Những thứ như Java synchronizedvà pthread_mutex_lock()(có sẵn cho C / C ++ trong một số hệ điều hành) là những gì bạn cần xem xét (a) .
(a) Câu hỏi này được đặt ra trước khi tiêu chuẩn C11 và C ++ 11 được hoàn thành. Những lần lặp đó hiện đã giới thiệu hỗ trợ phân luồng vào các đặc tả ngôn ngữ, bao gồm các kiểu dữ liệu nguyên tử (mặc dù chúng và các luồng nói chung, là tùy chọn, ít nhất là trong C).