2009-07-07 18 views
5

Vì vậy, thông thường (ít nhất là VS 2005 bang) cách để xác định xuất khẩu/nhập khẩu cho một DLL là:file header Tương tự cho cả hai DLL và Thư viện tĩnh

#ifdef MY_EXPORTS 
#define MY_API __declspec(dllexport) 
#else 
#define MY_API __declspec(dllimport) 
#endif 

class MY_API MyClass { 
    ... 
}; 

này hoạt động tuyệt vời nếu tôi chỉ xây dựng của tôi mã như một DLL. Tuy nhiên, tôi muốn có tùy chọn sử dụng một thư viện tĩnh HOẶC một DLL. Bây giờ một giải pháp rõ ràng (nhưng khủng khiếp), là sao chép tất cả các mã, loại bỏ các DLL 'MY_API' định nghĩa. Bây giờ những gì có vẻ là một cách tiếp cận tốt hơn nhiều là một chuyển đổi dòng lệnh để xác định, hoặc không xác định các công cụ DLL. Tuy nhiên trong trường hợp của một thư viện tĩnh những gì nên 'MY_API' được?

#ifdef DLL_CONFIG 
    #ifdef MY_EXPORTS 
    #define MY_API __declspec(dllexport) 
    #else 
    #define MY_API __declspec(dllimport) 
    #endif 
#else 
    #define MY_API // What goes here? 
#endif 

class MY_API MyClass { 
    ... 
}; 

Bây giờ giả định rằng điều này có thể được thực hiện sẽ có vấn đề khi người dùng của thư viện bao gồm các tập tin tiêu đề (ví dụ. Họ sẽ phải xác định 'DLL_CONFIG')?

Trả lời

12

Không có gì.

Giữ nguyên trạng thái là #define MY_API và tất cả các trường hợp của MY_API sẽ biến mất.

Bạn có thể thêm cấu hình xây dựng mới, chẳng hạn như Debug - DLL và Release - DLL bắt chước các cấu hình khác ngoại trừ chúng #define DLL_CONFIG.

Để sao chép cấu hình, hãy truy cập trình quản lý cấu hình (như thả xuống hộp danh sách Gỡ lỗi/Phát hành), sau đó trong 'Cấu hình giải pháp hoạt động', hãy chọn mới. Bây giờ bạn có thể đặt tên cho nó là "Debug - DLL" và đặt Copy Settings thành Debug và bây giờ điều cần làm là xác định DLL_CONFIG.

Để thực hiện việc này, hãy chuyển đến thuộc tính dự án-> thuộc tính cấu hình-> C/C++ -> Bộ tiền xử lý và nhập DLL_CONFIG trong đó. Bạn cũng sẽ thấy đó là nơi những thứ như NDEBUGWIN32 được xác định.

Giống như haffax said, sử dụng tên dự án cụ thể. Tôi muốn giới thiệu cái gì đó như:

#ifdef THEPROJECT_USE_DLL 
    #ifdef THEPROJECT_BUILDING_PROJECT 
     #define THEPROJECT_API __declspec(dllexport) 
    #else 
     #define THEPROJECT_API __declspec(dllimport) 
    #endif 
#else 
    #define THEPROJECT_API 
#endif 

Bây giờ người dùng của DLL của bạn chỉ #define THEPROJECT_USE_DLL nếu họ đang sử dụng phiên bản DLL, giống như bạn "- DLL" cấu hình có.

3

Chỉ cần xác định MY_API là trống. Như thế này:

#ifdef DLL_CONFIG 
    #ifdef MY_EXPORTS 
    #define MY_API __declspec(dllexport) 
    #else 
    #define MY_API __declspec(dllimport) 
    #endif 
#else 
    #define MY_API 
#endif 

Trong trường hợp liên kết tĩnh không có declspec là cần thiết.

Người dùng thư viện của bạn sẽ phải xác định DLL_CONFIG nếu họ muốn sử dụng nó dưới dạng dll hoặc không xác định nó nếu họ muốn sử dụng nó làm thư viện tĩnh. Sẽ không có bất kỳ vấn đề nào. Kiểu cấu hình này được thực hiện trong nhiều thư viện.

Chỉnh sửa: Tất nhiên bạn không nên sử dụng tên MY_EXPORTSDLL_CONFIG như vậy. Sử dụng tiền tố cụ thể của dự án cho tất cả các macro của bạn, để không có xung đột tên.

1

Không làm gì cả. Không có quy ước gọi điện đặc biệt nào là cần thiết để liên kết với một thư viện tĩnh. Điều duy nhất bạn cần làm là đảm bảo rằng trình liên kết liên kết với your.lib.

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