C++11

Origem: Wikipédia, a enciclopédia livre.
Ir para: navegação, pesquisa

C++11, anteriormente conhecido por C++0x é o novo padrão para a linguagem de programação C++. Ele substitui o antigo padrão do C++, o ISO/IEC 14882, que foi publicado em 1998 e atualizado em 2003. Estes predecessores foram informalmente chamados C++98 e C++03. O novo padrão incluirá muitas adições ao núcleo da linguagem (sua implementação principal), e estenderá a biblioteca padrão do C++, incluindo a maior parte da biblioteca do chamado C++ Technical Report 1 — um documento que propõe mudanças ao C++ — com exceção das funções matemáticas específicas.

Esse nome é uma referência ao ano no qual o padrão será lançado. O comitê pretendia introduzir o novo padrão em 2009,[1] a partir do que o então chamado "C++0x" passaria a se chamar "C++09", o que significa que o documento deveria estar pronto para a ratificação dos membros do comitê até o final de 2008. Para cumprir o prazo, o comitê decidiu focar seus esforços nas soluções introduzidas até 2006 e ignorar novas propostas.[2] porém ele ficou pronto apenas em 2010.

Linguagens de programação como o C++ utilizam um processo evolucionário para desenvolverem suas definições. Tal processo inevitavelmente culmina em problemas de compatibilidade com código pré-existente, o que ocasionalmente aconteceu durante o processo de desenvolvimento do C++. Entretanto, de acordo com o anúncio feito por Bjarne Stroustrup — inventor da linguagem C++ e membro do comitê — o novo padrão será quase completamente compatível com o padrão atual.[3]

Possíveis ocorrências[editar | editar código-fonte]

A maioria do trabalho foca grandes adições na biblioteca padrão e poucas na especificação da própria linguagem. Grande parte das inovações será derivada do trabalho desenvolvido pelo grupo Boost, que já provou o conceito de várias inovações em uma ampla base de utilizadores. Novas funcionalidades previstas para a biblioteca padrão incluem suporte à expressões regulares[4], suporte a tuplas[5], dedução de tipo de dado através da palavra reservada auto[6], suporte a funções lambda[7][8], delegação de construtores[9] e a adição da palavra reservada finally para tratamento de exceções, entre outras.

No desenvolvimento do novo padrão o comitê aplicou algumas diretivas ao projeto. Deseja-se manter estabilidade e compatibilidade com a versão anterior do padrão, lançada em 1998, e possivelmente com C. Deseja-se também preferir a introdução de novas funcionalidades através da biblioteca padrão ao invés de estender a linguagem por si própria. Isso porque a linguagem é historicamente conhecida por evoluir de maneira bastante conservadora, em favor da continuação de uso de código legado. A adição de palavras reservadas é um grande fator de incompatibilidade com código antigo. A biblioteca padrão possui a vantagem de poder lidar com problemas de compatibilidade e concorrência de nomes através do uso de espaço de nomes (ver a seguir).

Procura-se dar preferência a mudanças que possam melhorar as técnicas de programação. Como por exemplo, aumentar a segurança dos tipos de dados ao oferecer modelos alternativos às atuais e inseguras técnicas. Também, deseja-se aumentar o desempenho e a habilidade de se trabalhar diretamente com o hardware. Quando o desempenho não for possível, utiliza-se o princípio do "overhead zero" — suporte adicional para uma dada utilidade só será usado caso tal utilidade seja usada.

Outro desejo do comitê é facilitar o projeto de sistemas e bibliotecas ao invés de introduzir funcionalidades úteis somente à aplicações específicas (ou nichos de mercado), por ser uma linguagem de programação de propósito geral. Um dos itens relacionados à facilidade da linguagem está em tornar o C++ mais fácil de se aprender, sem remover utilitários entre especialistas. Atenção aos iniciantes é importante, porque eles sempre serão a maioria dos programadores, e porque muitos iniciantes não têm a intenção de expandir seu conhecimento em C++, limitando a si próprios a operar nos campos em que são especializados.[2] Ainda, considerando-se quão vasto é o C++ e sua utilização (incluindo áreas de aplicação e estilos de programação), mesmo os programadores mais experientes podem se tornar iniciantes em um novo paradigma de programação. Parte desse propósito está direcionado na aplicação de "conceitos", um método que tornará os erros de compilação muito mais legíveis para o desenvolvedor. Para especialistas, a facilitação de uso do C++ será aumentada ao aumentar a segurança e consistência da linguagem.

Melhorias de desempenho de tempo de execução da linguagem Padrão[editar | editar código-fonte]

Estes recursos de linguagem existem principalmente para fornecer algum tipo de benefício de desempenho, seja da memória ou da velocidade computacional.

constexpr – Expressões Constantes[editar | editar código-fonte]

C++ sempre teve o conceito de expressões constantes. Então as expressões como 3+4 sempre irá produzir os mesmos resultados, em tempo de compilação e em tempo de execução. Expressões constantes são oportunidades de otimização para os compiladores, compiladores e freqüentemente executá-los em tempo de compilação e codificar os resultados do programa. Além disso, existem um certo número de locais onde a especificação C++ requer o uso das expressões constantes. Definindo uma matriz requer uma expressão constante, e os valores de enumerador deve ser expressões constantes.

No entanto, uma expressão constante nunca foi permitido para conter uma chamada de função ou construtor objeto. Assim, um pedaço de código tão simples quanto isso é ilegal:

int get_five() {return 5;}

int some_value[get_five() + 7]; // Cria um array(vetor) de 12 inteiros. No C++ padrão!

Isso não era legal em C++03, por quê get_five() + 7 não é uma expressão constante. Um compilador C++03 não tem como saber se get_five() na verdade, é uma constante em tempo de execução. Em teoria, esta função pode afetar uma variável global, chamar outras funções constantes não-tempo de execução, etc.

No C++11 introduziram a palavra-chave constexpr, que permite ao usuário para garantir que um construtor de função ou objeto é uma constante de tempo de compilação. O exemplo acima pode ser reescrito da seguinte maneira.:

constexpr int get_five() {return 5;}

int some_value[get_five() + 7]; // Cria um array(vetor) de 12 inteiros. No C++11

Isso permite que o compilador para compreender e verificar, que get_five() é uma constante em tempo de compilação.

O uso do constexpr em uma função impõe algumas limitações sobre o que essa função pode fazer. Em primeiro lugar, a função deve ter um tipo de retorno não-nula. Em segundo lugar, o corpo da função não pode declarar variáveis ou definir novos tipos. Em terceiro lugar, o corpo pode conter apenas declarações, tomadas de nulos e uma única instrução de retorno. Deve existir valores de argumentos de tal forma que, após argumento de substituição, a expressão na instrução de retorno produz uma expressão constante.

Antes de C++11, os valores das variáveis poderia ser utilizado em expressões constantes somente se as variáveis são declarados const, tem um inicializador que é uma constante de expressão, e são do tipo integral ou enumeração. C++11 remove a restrição de que as variáveis devem ser do tipo integral ou enumeração se eles forem definidos com a palavra-chave constexpr:

constexpr double earth_gravitational_acceleration = 9.8;
constexpr double moon_gravitational_acceleration = earth_gravitational_acceleration / 6.0;

Tais variáveis de dados são implicitamente const, e deve ter um inicializador que deve ser uma expressão constante.

Para construir valores expressão de dados constantes de tipos definidos pelo usuário, os construtores também podem ser declaradas com constexpr. Um corpo da função de construtor constexpr só pode conter declarações e atestados nulos, e não pode declarar variáveis ou definir tipos, como com uma função constexpr. Deve existir valores de argumentos de tal forma que, após argumento de substituição, ele inicializa os membros da classe com expressões constantes. Os destruidores para esses tipos devem ser trivial.

O construtor de cópia para um tipo com qualquer no construtores constexpr também devem ser definido normalmente como um construtor constexpr, a fim de permitir que objetos do tipo a ser retornado pelo valor de uma função constexpr. Qualquer função membro de uma classe, como construtores de cópia, operador sobrecargas, etc., podem ser declarados como constexpr, assim desde que cumpram os requisitos para funções constexpr. Isso permite que o compilador para copiar as classes em tempo de compilação, executar operações sobre eles, etc.

Se uma função constexpr ou construtor é chamado com argumentos que não são expressões constantes, a chamada se comporta como se a função não foram constexpr, eo valor resultante não é uma expressão constante. Da mesma forma, se a expressão na instrução de retorno de uma função constexpr não avalia a uma expressão constante para uma invocação particular, o resultado não é uma expressão constante.

Range-based for loop[editar | editar código-fonte]

C++11 estende a sintaxe da função for para permitir a fácil iteração através de uma série de elementos:

int my_array[5] = {1, 2, 3, 4, 5};
// dobra o valor de cada elemento em meu_array:
for (int &x : my_array) {
    x *= 2;
}
// semelhante, mas também usando inferência de tipos de elementos de matriz
for (auto &x : my_array) {
    x *= 2;
}

Esta forma do for, chamado de “range-based for”,irá iterar sobre cada elemento da lista. Ele vai trabalhar para matrizes de estilo C, listas de inicializador, e qualquer tipo que tem as funções definidas begin() e end() definidas por isso que voltar iteradores. Todos os recipientes de biblioteca padrão que têm begin/end com pares finais irão trabalhar com a base para a declaração de gama.

Expressões e Funções Lambdas[editar | editar código-fonte]

C++11 fornece a capacidade de criar funções anônimas, chamados de funções lambda. Estes são os definidos como exemplo:

[](int x, int y) -> int { return x + y; }

O tipo de retorno está implícita; ele retorna o tipo da expressão de retorno (decltype(x+y)). O tipo de retorno de lambda pode ser omitida, desde que todos as expressões return retornem o mesmo tipo. O lambda pode opcionalmente, ser um fecho.

Referências

  1. Herb Sutter (7 de fevereiro de 2006). «ISO C++0x: Complete Public Review Draft In October 2007?» (em inglês). Consultado em 21 de abril de 2007. 
  2. a b A Brief Look at C++0x. Bjarne Stroustrup. The C++ Source, 2006.
  3. The Design of C++0x: Reinforcing C++'s proven strengths, while moving into the future. Bjarne Stroustrup, C/C++ Users Journal, 2005.
  4. John Maddock (3 de março de 2003). «A Proposal to add Regular Expressions to the Standard Library» (em inglês). Comitê de padronização do C++. Consultado em 9 de janeiro de 2008. 
  5. Jaakko Järvi (10 de setembro de 2002). «Proposal for adding tuple types into the standard library» (PDF) (em inglês). Comitê de padronização do C++. Consultado em 9 de janeiro de 2008. 
  6. Jaakko Järvi; et al. (28 de abril de 2003). «Decltype and auto» (PDF) (em inglês). Comitê de padronização do C++. Consultado em 9 de janeiro de 2008. 
  7. Jeremiah Willcock; et al. (26 de fevereiro de 2006). «Lambda expressions and closures for C++» (PDF) (em inglês). Comitê de padronização do C++. Consultado em 8 de março de 2007. 
  8. Valentin Samko (23 de fevereiro de 2006). «A proposal to add lambda functions to the C++ standard» (PDF) (em inglês). Comitê de padronização do C++. Consultado em 9 de janeiro de 2008. 
  9. Herb Sutter e Francis Glassborow (13 de fevereiro de 2004). «Delegating Constructors» (PDF) (em inglês). Comitê de padronização do C++. Consultado em 9 de janeiro de 2008. 

Ver também[editar | editar código-fonte]

Ligações externas[editar | editar código-fonte]

Ícone de esboço Este artigo sobre programação de computadores é um esboço. Você pode ajudar a Wikipédia expandindo-o.