Existe uma maneira de detectar em tempo de compilação se o compilador oferece suporte a determinados recursos do C ++ 11? Por exemplo, algo assim:
#ifndef VARIADIC_TEMPLATES_SUPPORTED
#error "Your compiler doesn't support variadic templates. :("
#else
template <typename... DatatypeList>
class Tuple
{
// ...
}
#endif
template <typename... Test> struct compiler_must_support_variadic_templates;
. Um erro de sintaxe revelaria rapidamente o problema. (Como um aparte, uma mensagem de erro adequada é muito melhor.)Respostas:
Há uma constante chamada
__cplusplus
que os compiladores C ++ devem definir para a versão do padrão C ++ compatível, consulte istoEle está definido como 199711L no Visual Studio 2010 SP1, mas não sei se os fornecedores serão tão ousados em aumentá-lo se eles apenas tiverem suporte (parcial) no nível do compilador versus uma biblioteca C ++ padrão com todas as alterações do C ++ 11 .
Portanto, as definições de Boost mencionadas em outra resposta continuam sendo a única maneira sensata de descobrir se há, por exemplo, suporte para threads C ++ 11 e outras partes específicas do padrão.
fonte
__cplusplus
para201103L
. Isso afirma total conformidade com o padrão de 2011; não fala sobre conformidade parcial ou extensões do compilador. Se__cplusplus
estiver definido como201103L
, o compilador está totalmente em conformidade ou ele está mentindo para você. Se não for, você não saberá quais recursos ele oferece suporte.-std=c++11
opção é especificada (também pode com-std=gnu++11
). Eles fazem isso, embora não sejam totalmente completos (4.8 nos aproxima muito). Nota - há uma lacuna entre o que o compilador suporta e o que está disponível na biblioteca padrão. Ambos 4.7.x e 4.8.x não têm suporte regex - mas isso é uma biblioteca, não um recurso de compilador.__cplusplus
para199711L
para C ++ 11.__cplusplus
como199711L
não é um compilador C ++ 11 em conformidade. Eles provavelmente têm opções para fazê-los se comportar corretamente.Conforme declarado pelo padrão C ++ 11 (§iso.16.8):
Com o valor dessa macro, você pode verificar se o compilador é compatível com C ++ 11.
Agora, se você está procurando uma maneira padrão de verificar se o compilador oferece suporte a algum subconjunto de recursos do C ++ 11, acho que não existe uma maneira portátil padrão; você pode verificar a documentação dos compiladores ou arquivos de cabeçalho da biblioteca std para obter mais informações.
fonte
Eu sei que esta é uma pergunta muito antiga, mas ela pode ser vista com frequência e as respostas estão um pouco desatualizadas.
Compiladores mais novos com o padrão C ++ 14 têm uma maneira padrão de verificar recursos, incluindo recursos do C ++ 11. Uma página abrangente está em https://isocpp.org/std/standing-documents/sd-6-sg10-feature-test-recommendations
Em resumo, cada recurso possui uma macro padrão definida com a qual você pode verificar
#ifdef
. Por exemplo, para verificar literais definidos pelo usuário, você pode usarfonte
__has_include()
macro.Para verificar o suporte C ++ 14 e outros. Testando no GCC 5.2.1.
fonte
Você pode usar isto:
Para C ++ 11, a maioria dos compiladores, exceto Visual Studio, define a
__cplusplus
macro como201103L
, mas qualquer versão do Visual Studio a define como,199711L
que é o valor usado para outros compiladores antes de C ++ 11. Este código compara a_cplusplus
macro com201103L
todos os compiladores, exceto Visual Studio, e se o compilador for Visual Studio, ele verifica se a versão do Visual Studio é posterior a 2015, a primeira versão do Visual Studio que oferece suporte total a C ++ 11 (para Visual Studio 2015, a_MSC_VER
macro tem o valor1900
, veja esta resposta ).fonte
g++ -std=c++98
GCC 4.8, ele imprime incorretamenteC++11 is supported
.Se você não quiser usar Boost.Config e precisar testar os compiladores que suportam C ++ 11, verificar o valor da constante
__cplusplus
será suficiente . No entanto, um compilador pode oferecer suporte à maioria dos recursos populares do padrão C ++ 11, mas não oferece suporte a todas as especificações. Se você deseja ativar o suporte para compiladores específicos do Visual Studio que ainda não são 100% compatíveis com as especificações do C ++ 11, use o seguinte snippet de código que permite a compilação no Visual Studio 2013:Uma lista completa de versões do compilador para Visual Studio é fornecida em Como detectar se estou compilando código com o Visual Studio 2008
fonte
No mundo Linux / Unix tradicional, o autoconf é tradicionalmente usado para testar a presença de bibliotecas e recursos de compilador e bugs, colocando-os em um config.h que você usa em seus arquivos conforme necessário.
fonte
Quando sua verificação for para a disponibilidade de uma biblioteca C ++ 11 (não um recurso de linguagem), por exemplo, o
<array>
cabeçalho, você pode#if __has_include(<array>)
.Às vezes, a verificação
#if __cplusplus >= 201103L
diria que você usa C ++ 11, mas outras configurações, como a configuração da versão da biblioteca padrão no Xcode, podem ainda não ter as novas bibliotecas disponíveis (a maioria delas estão disponíveis em nomes diferentes, por exemplo<tr1/array>
)fonte