Os recursos experimentais do C ++ moderno são confiáveis ​​para projetos de longo prazo?

87

Tenho um projeto que usa C ++ 11/14, mas requer algo como std::filesystem, que só está disponível em C ++ 17 e, portanto, não tenho a chance de usá-lo atualmente. Vejo, entretanto, que está disponível em meu compilador atual como std::experimental::filesystem. É uma boa ideia usar recursos experimentais, presumindo que no futuro eu possa adicionar algo como:

#ifdef CXX17 //if this is C++17
std::filesystem::something ...;
#else
std::experimental::filesystem::something ...;
#endif

Minhas preocupações são:

1. É garantido que todos os compiladores compatíveis tenham os mesmos recursos experimentais?

2. Os recursos experimentais estão sujeitos a grandes mudanças que os tornam não confiáveis?

Talvez haja mais coisas para se perguntar. Por que devo ou não usá-los? Estou intrigado com um novo projeto e não sei o que decidir.

The Quantum Physicist
fonte
25
a palavra experimental não responde às suas perguntas?
101010
6
Principalmente uma questão de gosto, mas eu evitaria bagunçar o código com #idef CXX17. IMHO, a maneira portátil é colocar todo o código relacionado ao sistema de arquivos em uma única unidade de compilação (pode ser uma classe), usá-lo em todas as partes restantes do código, codificá-lo com o padrão C ++ 11/14 atual. Documente como e por que você o escreveu dessa forma e, eventualmente, transportá-lo para C ++ 17 mais tarde durante uma fase de manutenção, se fizer sentido. (comentando sobre a pergunta original)
Serge Ballesta,
4
Era apenas "experimental" como candidato a entrar no padrão. Não é um reflexo da qualidade do código.
Galik,
5
Houve algumas mudanças entre a versão "experimental" e a versão C ++ 17 final, consulte o documento P0492R1
Bo Persson
7
No caso de filesystemvocê correr muito menos risco ao usá-lo do que outras coisas, como você já sabe que ele é padronizado em C ++ 17, e a especificação C ++ 17 exata dele está disponível publicamente. Portanto, tudo que você precisa fazer é certificar-se de usar apenas os experimental::filesystemrecursos que estão na especificação C ++ 17. E, claro, você deve saber que todas as suas plataformas direcionadas suportam um experimental::filesystemou o C ++ 17 std::filesystem.
Howard Hinnant,

Respostas:

79
  1. É garantido que todos os compiladores compatíveis tenham os mesmos recursos experimentais?

Não, os recursos experimentais são opcionais.

  1. Os recursos experimentais estão sujeitos a grandes mudanças que os tornam não confiáveis?

Sim, o comitê C ++ pode até decidir abandonar um recurso ou, no processo de padronização, pode surgir um defeito que forçaria a alteração de um recurso.

Geralmente, não é uma boa ideia depender de recursos experimentais. Os recursos experimentais são exatamente o que a palavra diz (ou seja, para experimentar).

101010
fonte
2
Referindo-se ao segundo ponto, observe que estou falando de recursos que já são aceitos, mas podem ser diferentes.
The Quantum Physicist
14
@TheQuantumPhysicist: "já aceito" é um conceito complicado. Qualquer coisa pode ser removida a qualquer momento pela aceitação posterior de uma alteração para removê-la, e isso aconteceu com todos os padrões. Você provavelmente gostaria de esperar pelo menos até o Draft International Standard para que o conjunto de recursos seja razoavelmente confiável.
Kerrek SB
1
@KerrekSB: Você não quer dizer o Final Draft International Standard também conhecido como FDIS. ? A redação é um processo bastante permanente.
MSalters de
1
@MSalters: Não, o DIS provavelmente é bom o suficiente se você estiver com pressa. E podemos não ter um FDIS desta vez.
Kerrek SB de
4
@KerrekSB: Eu era basicamente o órgão nacional da Holanda em torno do C ++ 03;). Tínhamos um secretário nacional para o SC22 que conhecia os procedimentos ISO e como responder a um FDIS, mas não o quê. Além de nosso delegado WG14, Randy Marques, nenhum de nossos delegados SC22 sabia nada sobre C ++. E Randy estava apenas zombando do fato de que C ++ precisaria de mais páginas para definir todo seu UB do que C precisava para o Comportamento Definido - não gostaria que ele respondesse a esse FDIS;)
MSalters de
50

Alguém da audiência fez uma pergunta durante a palestra "C ++ Standard Library Panel" na CppCon 2016 ( YouTube ) sobre o potencial do nome experimentalpara assustar os usuários e evitar que usem qualquer coisa dentro do namespace:

Vocês consideram a produção [o conteúdo do std::experimentalnamespace] pronto e esse é um argumento que pode ser feito, [que] está efetivamente pronto para a produção pelos próximos 3 anos, e talvez você tenha que mudar seu código 3 anos depois, talvez?

Michael Wong (presidente do SG5 e SG14 e editor do Concurrency TS) respondeu à pergunta primeiro:

Acho que há um forte consenso dentro do comitê de que está praticamente pronto para produção. Como eu disse antes, na maioria dos casos, 99% dele é descartado. Queremos ter certeza de que não é um impedimento para você usá-lo. Você pode entender porque queremos colocar grandes recursos, grandes grupos de recursos, em tal contexto, de modo que não perturbe o resto do sistema de biblioteca inteiro, mas também torna mais fácil para você usá-lo. Agora você pode ativar o GCC com um sinalizador específico para Conceitos, você sabe, que na verdade torna mais fácil para você segmentá-lo.

Alisdair Meredith (ex-presidente do LWG) então acompanhou:

Vou assumir a posição contrária aqui. Uma das coisas que Herb [Sutter] disse como organizador do WG21, o grupo padrão, quando começamos o caminho dos TSes é que ele não achava que os TSes teriam sucesso até que não trouxéssemos algo adiante, porque significa que não estamos sendo experimentais o suficiente, não estamos sendo ambiciosos o suficiente no que estamos usando os TSes. Nós realmente queremos issoexperimentalpara ser uma dica de que, sim, essas coisas estão sujeitas a mudanças, não estamos vinculados a isso e podemos errar. Isso é para diminuir nossa barreira para as coisas que consideramos ser tão ambiciosas e abrangentes quanto podemos [...] Agora o padrão parece estar em um ciclo de lançamento de três anos, devemos ser muito mais ambiciosos em colocar recursos realmente experimentais no TS, e talvez avançando as coisas mais rapidamente no próprio padrão principal. Mas, novamente, este será um tópico divertido para discutirmos nas próximas reuniões [do comitê padrão C ++].

Stephan T. Lavavej (mantenedor da implementação STL da Microsoft) foi o último a responder:

É importante fazer uma distinção entre a experimentalidade da interface e a experimentalidade da implementação, porque quando você diz "produção pronta", o que isso significa? Normalmente, "pronto para produção", você pensaria nisso falando sobre a implementação. É bem possível que uma implementação [de algo em std::experimental] seja absolutamente [...] à prova de balas. [...] Algo como [...] o <random>cabeçalho em TR1, [era] muito, muito bom em TR1, e você poderia ter uma implementação absolutamente à prova de balas disso, mas descobriu-se que a interface agitou substancialmente [antes do lançamento do] C ++ 11 e [...] se soubéssemos naquela época o que fazemos agora, colocar um experimentalteria sido um sinal melhor para as pessoas: "Ei, talvez você não queira usarstd::experimental::variate_generator porque, ha-ha, vai desaparecer no C ++ 11 ".

Portanto, parece que há algum desejo entre os desenvolvedores de biblioteca padrão e membros do comitê de que, pelo menos no futuro, o conteúdo do std::experimentalnamespace seja verdadeiramente "experimental" por natureza, e não deve ser dado como certo que algo std::experimentalserá torná-lo no padrão C ++.

E não, tanto quanto eu entendo, depende dos fornecedores de bibliotecas padrão se eles fornecem implementações para os vários recursos internos std::experimental.

Joseph Thomson
fonte
47
10 anos depois de ler o nome pela primeira vez, o fato de o mantenedor da STL da Microsoft se chamar STL ainda me faz rir.
Jörg W Mittag de
19
@ JörgWMittag você deve conhecer o mantenedor do compilador, Michael Sam Victor Collins
MM de
28

"Experimental" é um termo um pouco exagerado. A filesystembiblioteca teve origem no Boost e passou por algumas iterações lá, antes de ser submetida à ISO.

No entanto, os padrões ISO são intencionalmente muito conservadores. Chamar de experimental significa que a ISO não promete explicitamente que a nomenclatura será estável; está bastante claro que você precisará endereçar novamente seu código em algum momento no futuro. Mas, conhecendo a ISO, é provável que haja orientação sobre como.

Quanto à compatibilidade entre compiladores, espere que seja razoável. Mas haverá casos extremos (pense nos caminhos relativos à unidade do Windows, por exemplo), e é exatamente por isso que um padrão futuro pode quebrar seu código existente. Idealmente, isso quebraria seu código se e somente se você dependesse desse caso, mas isso não é uma garantia.

MSalters
fonte
8

Talvez haja mais coisas para se perguntar.

Alguns pontos a considerar:

  • Quão multiplataforma é o seu projeto? Se houver apenas um compilador envolvido, você pode inspecionar sua implementação e histórico para decidir. Ou pergunte a eles!

  • Qual é o tamanho da sua base de código? Quão grande seria o impacto das mudanças?

  • Quão fundamentais para o seu projeto são os recursos fornecidos pela API / biblioteca / recurso?

  • Quais são as alternativas?

    • Use o recurso experimental e adapte o código às modificações quando / se ele se tornar padronizado. Pode ser tão fácil quanto excluir experimental::ou tão difícil quanto forçar soluções alternativas.
    • Adicione uma camada de abstração (comentário de Serge Ballesta). Se o recurso experimental mudar, suas reescritas serão isoladas. Para um recurso padrão, pode ser um exagero (std :: filesystem já é uma camada de abstração ...).
    • Use outra API / biblioteca. Mesmas perguntas: maturidade? robustez? estabilidade? portabilidade? fácil de usar? características?
  • No caso de std :: filesystem (ou o TS de rede), há boost :: filesystem (resp. Boost :: asio) como alternativa ou fallback, no caso de experimentalum falhar ou desaparecer.
Pablo H
fonte