2009-04-07 20 views
5

Chúng tôi đang lập trình một thư viện ghi nhật ký tự lưu giữ trong tệp .hpp. Chúng tôi muốn bao gồm <tr1/unordered_map> (nếu trình biên dịch hỗ trợ TR1,) hoặc tiêu chuẩn <map> nếu không. Có cách kiểm tra chuẩn nào tại thời gian biên dịch nếu tr1 có sẵn hay không?Làm thế nào để kiểm tra TR1 trong khi biên dịch?

Tôi đã nghĩ rằng giống như biểu tượng xác định "__cplusplus" hiện diện, có thể đã được xác định là "__cxx__tr1" hoặc một cái gì đó tương tự. Tôi đã không thấy điều đó trong các bản nháp cho TR1, vì vậy tôi cho rằng nó không có mặt, nhưng tôi muốn hỏi trước tiên trong trường hợp.

Là một lưu ý, nếu những định nghĩa đó không tồn tại, sẽ không có ý tưởng tồi khi đưa chúng vào các đề xuất.

Trả lời

2

Nếu bạn đang sử dụng bất kỳ công cụ cấu hình như autotools bạn có thể thử viết một bài kiểm tra như:

AC_CHECK_HEADER(tr1/unordered_map,[AC_DEFINE([HAVE_TR1],[],["Have tr1"])],[]) 
AC_CHECK_HEADER(unordered_map,[AC_DEFINE([HAVE_CXX0X],[],["Have C++0x"])],[]) 

Và sau đó sử dụng các định nghĩa trong mã của bạn.

Nói chung, __cplusplus macro phải cung cấp cho bạn số phiên bản tiêu chuẩn, nhưng không có trình biên dịch nào cung cấp cho bạn 100% triển khai chuẩn ... Vì vậy, hãy ghi macro cấu hình.

Thật không may đây chỉ là cách khá đáng tin cậy để kiểm tra những việc như vậy, trừ khi bạn muốn viết 1001 #ifdef cho mỗi trình biên dịch (những gì thúc đẩy thực hiện)

Và sau đó:

#include "config.h" 
#ifdef HAVE_CXX0X 
# include <unordered_map> 
    typedef std::unordered_map<foo,bar> my_map; 
#elif HAVE_TR1 
# include <tr1/unordered_map> 
    typedef std::tr1::unordered_map<foo,bar> my_map; 
#else 
# include <map> 
    typedef std::map<foo,bar> my_map; 
#endif 
+0

OK, đó là một tùy chọn tôi muốn tránh, vì tôi chỉ muốn phát hành tệp .hpp và chạy. Đối với những điều "gần như tiêu chuẩn", tôi thích một so sánh đơn giản hơn là phải chạy một cấu hình chính thức. –

+0

Tôi chấp nhận câu trả lời này vì dường như không có cách nào, và điều này có vẻ là cách tốt hơn ... –

2

GCC-4.3 có:

#define __GXX_EXPERIMENTAL_CXX0X__ 1 

Nhưng, điều này rõ ràng là không chuẩn.

+0

Macro này được xác định nếu bạn sử dụng g ++ -std = C++ 0x và sau đó bạn có unordered_map trong std :: unordered_map. Nếu không (no -std = C++ 0x) bạn không có định nghĩa này nhưng bạn vẫn có thể sử dụng include và std :: tr1 :: unordered_map class. – Artyom

+0

Có, nhưng như những người khác đã chỉ ra, đây là một cái gì đó mà chỉ có thể được kiểm tra trong khi cấu hình. Tất cả các phiên bản khác của GCC trước 4.3 sẽ phát sinh lỗi khi chuyển đổi -std đó được đưa ra. – greyfade

1

Một thư viện mà tôi xử lý với nhu cầu sử dụng một số lớp đã được thêm vào TR1 từ Boost, thích TR1 nếu có. Giải pháp (là một thư viện dựa trên Unix) là để đẩy các kiểm tra vào kịch bản cấu hình.

Vì vậy, nói cách khác, không, không có gì di động mà tôi biết. Điều đó nói rằng, nếu bạn đang trên Unix, kịch bản cấu hình kiểm tra công việc cũng đủ.

2

Xem ISO C++ (WG21) giấy N1575. Bài báo này đã bị loại bỏ khỏi TR1, không có sự thay thế. Vì vậy, không có cách nào chính thức để phát hiện TR1.

+0

+1. Hấp dẫn. Tôi không biết ... Đáng tiếc. –

0

Giả sử ai sử dụng VS2010, hoặc bất kỳ bộ có TR1 sẵn, những gì sẽ xảy ra nếu ai đó để làm

#include "boost/tr1/unordered_map.hpp" 
... 
std::tr1::unordered_map<...> uMap; 

Điều gì sẽ là loại uMap được?

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