2013-03-01 11 views
14

Nếu tôi viết f(x)->g(args, ...) tôi có thể dựa vào một điểm chuỗi sau f(x) trước khi đánh giá args, ... không? Tôi có thể thấy các đối số theo cả hai cách:Có một điểm chuỗi giữa một cuộc gọi hàm trả về một đối tượng và một cuộc gọi phương thức trên đối tượng đó không?

  • §1.9.17 "Khi gọi một hàm (có hoặc không có hàm), có một điểm chuỗi sau khi đánh giá tất cả đối số hàm (nếu có) Ngoài ra còn có một điểm chuỗi sau khi sao chép một giá trị trả về và trước khi thực hiện bất kỳ biểu thức nào bên ngoài hàm. "
  • Mặt khác, đối tượng con trỏ hoàn toàn là một đối số ẩn this như thể tôi đã viết g(f(x), args, ...) cho thấy nó giống như một đối số, và do đó không xác định.

Nhà điều hành -> không phải là một nhà điều hành nhị phân bình thường, vì rõ ràng g(...)không có thể được đánh giá trước f(x) như nó có thể nếu tôi đã viết f(x) + g(...). Tôi ngạc nhiên vì tôi không thể tìm thấy một số tuyên bố cụ thể về nó.

+1

'->' là toán tử nhị phân? Nó trông giống như một toán tử đơn nhất trả về một con trỏ tới một kiểu nào đó, nếu bạn bỏ qua nó trông như thế nào. – Yakk

+1

@Yakk: Nó là một toán tử đơn nhất, nhưng những gì là * n-ary * (của các loại) là 'T :: g' có một ẩn' this' cùng với 'args'. Câu hỏi đặt ra là liệu biểu thức tạo ra ngầm 'này' được sắp xếp trước khi đánh giá phần còn lại của đối số cho hàm thành viên' g' –

+2

Có vẻ như [nó không] (https://ideone.com/IxBuui). – jrok

Trả lời

9

C++ 2003 5.2.2 p8

Thứ tự đánh giá đối số không được chỉ định. Tất cả các tác dụng phụ của việc đánh giá biểu thức đối số đều có hiệu lực trước khi hàm được nhập vào. Thứ tự đánh giá biểu thức postfix và danh sách biểu thức đối số không được chỉ định.

Điều này có nghĩa là không một điểm chuỗi giữa đánh giá f(x)args.

Trong C++ 2011 toàn bộ khái niệm về điểm chuỗi đã được thay thế (xem N1944), và từ ngữ mà bây giờ chỉ là một lưu ý:

[Lưu ý: Các đánh giá của biểu thức postfix và của các biểu thức đối số tất cả đều không liên quan đến nhau. Tất cả các tác dụng phụ của việc đánh giá biểu thức đối số được giải trình tự trước khi hàm được nhập (xem 1.9). - cuối note]

và 1,9 P15 nói

Khi gọi một hàm (có hoặc không có chức năng là inline), mỗi giá trị tính toán và phụ ảnh hưởng kết hợp với bất kỳ biểu hiện lý luận, hoặc với biểu thức postfix chỉ định hàm được gọi, được sắp xếp theo trình tự trước khi thực hiện mọi biểu thức hoặc câu lệnh trong phần thân của hàm được gọi. [Lưu ý: Tính toán giá trị và tác dụng phụ liên quan đến các biểu thức đối số khác nhau không được kết thúc. - cuối note]

này nói các biểu hiện f(x) và sự biểu hiện args được sắp xếp trước khi tất cả mọi thứ trong cơ thể của g, nhưng họ là unsequenced tương đối với nhau, đó là giống như C++ 03 quy tắc nhưng được diễn đạt khác nhau.

4

Lưu ý, tôi nghĩ rằng bạn đang đặt một câu hỏi trong tiêu đề của mình và một câu hỏi khác trong phần câu hỏi của bạn.

Vâng, nó không thực sự mâu thuẫn. Để đánh giá chức năng của bạn, những điều sau đây phải xảy ra (không nhất thiết theo thứ tự này).

  • x được đánh giá (A)
  • args được đánh giá (B)
  • ... được đánh giá (C)
  • f (x) được gọi là (D)
  • giá trị trả về của f (x) được sao chép (E)
  • return-> g (args, ...) được gọi là (F)

Bây giờ, các quy tắc bạn đã trích dẫn chỉ ra rằng

  1. (A) phải xảy ra trước (D), vì có điểm chuỗi đánh giá đối số cho hàm trước khi đánh giá.
  2. (D) xảy ra trước (E), vì không thể sao chép cho đến khi chức năng chạy.
  3. (F) xảy ra sau (E), vì con trỏ tiềm ẩn cần gọi g (args) *
  4. (B) và (C) trước (F), vì chúng là đối số.

Tuy nhiên, mối quan hệ giữa (A), (B) và (C) hoặc câu hỏi của bạn giữa (B) và (C) và (D), vì chúng không đối số cho (F), chúng có thể được đánh giá sau đó. HOẶC, chúng có thể được đánh giá trước.

* Câu hỏi thú vị. Điều gì sẽ xảy ra nếu g (args, ...) là một hàm thành viên tĩnh. Trong trường hợp này, vì con trỏ trả về từ f (x) không thực sự được truyền vào, nó có thể được sắp xếp theo trình tự trước đó không? Nhưng đó là một câu hỏi riêng.