2011-12-22 40 views
6

Nếu tôi tạo một hàm nội tuyến, nó có thay đổi liên kết của nó thành liên kết nội bộ không? Ví dụ: Tôi đang sử dụng hoặc gọi hàm nội tuyến trong hai tập tin:Việc tạo một hàm nội tuyến có ảnh hưởng đến liên kết của nó không?

file1.cpp 

//function definition 
inline void foo() {} 

file2.cpp 
//function definition 
inline void foo() {} 

Tại sao tôi cần phải xác định các chức năng nội tuyến trong mỗi tập tin để có thể gọi nó? Tôi nhận được một liên kết nội bộ? Nếu tôi sử dụng static inline thì sao?

+0

Trong khi tôi biết thẻ là C++, tốt để biết rằng nội tuyến trong C là theo liên kết nội bộ mặc định, ngược lại với C++ –

+0

@Jesse: Không, nó không ngược lại. Hàm nội tuyến C (C99) cũng có liên kết bên ngoài theo mặc định trừ khi được khai báo tĩnh. – user1086635

+0

@ user1086635: Không, trong C mặc định là liên kết nội bộ. C99 6.7.4/6 nói "Định nghĩa nội tuyến không cung cấp định nghĩa bên ngoài cho hàm, và không cấm định nghĩa bên ngoài trong một đơn vị dịch khác.", Đưa ra ví dụ tạo định nghĩa bên ngoài với khai báo bổ sung 'extern' . –

Trả lời

10

Nếu tôi tạo một hàm nội tuyến, nó có thay đổi liên kết của nó thành liên kết nội bộ không?

Không, làm cho nội tuyến không thay đổi liên kết của nó.

Tại sao tôi cần xác định hàm nội tuyến trong mỗi tệp để có thể gọi?

Vì ngôn ngữ yêu cầu. C++ 11 7.1.2/4 nói "Hàm nội tuyến phải được định nghĩa trong mọi đơn vị dịch mà nó được sử dụng không đúng và phải có chính xác cùng định nghĩa trong mọi trường hợp."

Tôi nhận được liên kết nội bộ?

Không, nó vẫn có liên kết bên ngoài: con trỏ đến hàm sẽ có cùng giá trị trong bất kỳ đơn vị dịch nào và bất kỳ đối tượng tĩnh nào được khai báo bên trong hàm sẽ là cùng một đối tượng trong bất kỳ đơn vị dịch nào.

Nếu tôi sử dụng static inline thì sao?

Điều đó sẽ cung cấp liên kết nội bộ, do static. Điều này có nghĩa là các định nghĩa trong các đơn vị dịch riêng biệt sẽ tạo ra các hàm riêng biệt, với các địa chỉ khác nhau và các bản sao riêng biệt của bất kỳ đối tượng tĩnh nào.

+0

Được rồi, Nếu tôi có từng hàm nội dòng được khai báo là 'tĩnh' trong hai tệp đó, thì nó sẽ ảnh hưởng như thế nào đến chương trình của tôi? Bởi vì ngay cả khi các hàm có liên kết mở rộng các định nghĩa của chúng vẫn cần phải có trong mỗi tệp. – user1086635

+1

@ user1086635: Nếu bạn khai báo chúng là 'tĩnh', thì mỗi hàm sẽ là một hàm riêng biệt; ví dụ, địa chỉ của chúng sẽ khác nhau và mỗi địa chỉ sẽ có bản sao riêng của bất kỳ dữ liệu tĩnh nào. Với liên kết bên ngoài, chúng sẽ có cùng địa chỉ và sẽ chia sẻ dữ liệu tĩnh. –

+0

Lưu ý về các con trỏ tới nội tuyến không được chỉ định. Nhiều bản sao của hàm nội tuyến có thể tồn tại - vì mỗi đơn vị dịch sẽ nhận được một bản sao. Sau đó nó được xác định như thế nào một _linker_ giải quyết điều đó.Nếu bạn vi phạm quy tắc ODR, bạn có thể nhận được kết quả lạ như các chức năng khác nhau đang được gọi. Vì vậy, bạn không thể giả định con trỏ sẽ giống nhau, ngay cả khi bạn làm theo ODR. –

Các vấn đề liên quan