2013-07-15 30 views
6

Tôi không chắc về bảo đảm thực hiện cho toán tử bậc ba C/C++.
Ví dụ nếu tôi đưa ra một địa chỉ và một boolean mà nói nếu địa chỉ đó là tốt cho việc đọc tôi có thể dễ dàng tránh xấu nội dung đã sử dụng if/else:C++ điều kiện thực thi điều hành bậc ba

int foo(const bool addressGood, const int* ptr) { 
    if (addressGood) { return ptr[0]; } 
    else { return 0; } 
} 

Tuy nhiên có thể một nhà điều hành ternary (?:) đảm bảo rằng ptr sẽ không được truy cập trừ khi addressGood là đúng?
Hoặc một trình biên dịch tối ưu có thể tạo mã truy cập ptr trong mọi trường hợp (có thể làm hỏng chương trình), lưu trữ giá trị trong thanh ghi trung gian và sử dụng gán điều kiện để thực hiện toán tử bậc ba?

int foo(const bool addressGood, const int* ptr) { 
    // Not sure about ptr access conditions here. 
    return (addressGood) ? ptr[0] : 0; 
} 

Cảm ơn.

+0

AFAIK, vâng, nó không được đánh giá chi nhánh khác. – chris

+0

Kiểu thiết kế: API thực sự không nên có 'addressGood'. Biểu diễn chuẩn của địa chỉ không đúng là '0'. I E. 'int foo (const const int * ptr) {return ptr? * ptr: 0; } ' – MSalters

+0

Không chắc chắn nếu' const const int * 'thực sự có ý nghĩa. – rsp1984

Trả lời

8

Có, tiêu chuẩn đảm bảo rằng ptr chỉ được truy cập nếu addressGood là đúng. Xem this answer về chủ đề, trích dẫn tiêu chuẩn:

Cụm từ biểu thức điều kiện từ phải sang trái. Biểu thức đầu tiên được chuyển ngữ cảnh thành bool (Điều 4). Nó được đánh giá và nếu nó là đúng, kết quả của biểu thức điều kiện là giá trị của biểu thức thứ hai, nếu không thì biểu thức thứ ba. Chỉ một trong các biểu thức thứ hai và thứ ba được đánh giá. Mọi tính toán giá trị và tác dụng phụ liên kết với biểu thức đầu tiên được sắp xếp theo trình tự trước mỗi lần tính toán giá trị và tác dụng phụ liên quan đến biểu thức thứ hai hoặc thứ ba.

(C++ 11 tiêu chuẩn, đoạn 5,16/1)

0

C++ 11/[expr.cond]/1

Conditional expressions group right-to-left. The first expression is contextually converted to bool (Clause 4). 
It is evaluated and if it is true, the result of the conditional expression is the value of the second expression, 
otherwise that of the third expression. Only one of the second and third expressions is evaluated. Every value 
computation and side effect associated with the first expression is sequenced before every value computation 
and side effect associated with the second or third expression 
1

Các điều kiện (ternary) đảm bảo vận hành chỉ đánh giá toán hạng thứ hai nếu toán hạng đầu tiên so sánh không bằng với 0 và chỉ đánh giá toán hạng thứ ba nếu toán hạng đầu tiên so sánh bằng 0. Điều này có nghĩa là mã của bạn an toàn.

Ngoài ra còn có một điểm chuỗi sau khi đánh giá toán hạng đầu tiên.

Nhân tiện, bạn không cần các dấu ngoặc đơn - addressGood ? ptr[0] : 0 cũng được.

+0

Điểm tốt với các dây đeo. Tôi viết chúng cho sự nhất quán nhưng cảm ơn vì đã chỉ ra nó. – rsp1984

1

Tôi xin nói, ngoài các câu trả lời rằng "vâng, nó được đảm bảo bằng C++ chuẩn":

Vui lòng sử dụng các hình thức đầu tiên. Đó là MUCH rõ ràng hơn những gì bạn đang cố gắng đạt được.

Tôi gần như có thể đảm bảo rằng bất kỳ trình biên dịch lành mạnh nào (với số lượng tối ưu hóa tối thiểu) tạo chính xác mã giống nhau cho cả hai ví dụ. Vì vậy, trong khi nó rất hữu ích để biết rằng cả hai hình thức này đạt được cùng một "bảo vệ", nó chắc chắn là ưa thích để sử dụng các hình thức đó là dễ đọc nhất.Nó cũng có nghĩa là bạn không cần phải viết bình luận giải thích rằng nó là an toàn vì đoạn như vậy và như vậy trong tiêu chuẩn C++, do đó làm cho cả hai mất cùng một lượng mã-không gian - bởi vì nếu bạn didn ' Trước tiên, bạn có thể dựa vào người khác C ALNG không biết rằng điều này là an toàn, và sau đó dành nửa giờ tiếp theo tìm câu trả lời qua google, hoặc chạy vào chủ đề này, hoặc hỏi câu hỏi một lần nữa!