link Observe que não importa se o int corresponde a uma das constantes do tipo enum; a conversão de tipo é sempre ilegal.
Iwaz 29/03
3
Acredito que se você deseja converter para Test :: A, o valor de int aterá que ser 0, porque Test :: A tem um valor implícito de 0 e Test :: B tem um valor implícito de 1. A menos que o fato de converter especificamente para Test :: a é além do ponto ...
@ Mitch, o que eu ganho por usar autoneste caso? Existe alguma melhoria de desempenho?
Frederico Pantuzza
2
Sem melhorias de desempenho. O compilador apenas deduz o tipo automaticamente se você especificar com "auto". Se você decidir alterar seu nome de enumeração no futuro, modificará menos seu código, pois o compilador deduzirá automaticamente o nome de tipo correto.
MSDN: O operador static_cast pode converter explicitamente um valor integral em um tipo de enumeração. Se o valor do tipo integral não estiver dentro do intervalo de valores de enumeração, o valor de enumeração resultante será indefinido.
22412 Kirill Kobelev
1
@KirillKobelev se o valor integral puder ser representado pelo tipo subjacente da enumeração, a enumeração resultante deve ter esse valor. Caso contrário, o valor da enum produzido será o valor resultante da conversão da expressão no tipo subjacente da enum. Se o VC ++ faz algo diferente, acho que não é compatível.
bames53
2
o que um compilador conforme deve fazer, se enum tiver valores {1,3,5} e o código tentar fazer <static_cast> a partir do valor de 2. Como isso será diferente do C-cast?
Kirill Kobelev
6
@KirillKobelev Eu não estou usando um static_cast porque ele faz algo diferente de um estilo C, eu estou usando o static_cast porque os modelos C ++ são estilisticamente preferíveis aos modelos C.
bames53
4
@KirillKobelev " se enum tiver valores {1,3,5} " Não. O tipo de enumeração não pode ser limitado apenas a esses 3 valores possíveis: {1,3,5} são os enumeradores (nomeados valores de enumeração), não a enumeração em si . Se 1,3,5 são possíveis enumeração valores, então que assim é 2.
É uma boa idéia usar o elenco mais restritivo que você puder e evitar completamente o estilo C, para dar ao compilador a melhor chance de detectar erros. static_castseria um elenco melhor aqui.
12118 Mike Seymour
4
@ Mike Seymour, o problema é que o elenco estático não tem diferença do elenco C neste caso. Como e que erro ele pode detectar ???
Kirill Kobelev
7
@KirillKobelev: O problema é que um elenco no estilo C não é explícito. Pode ser igual a static_cast, mas também pode ser uma const_castou até pior, uma reinterpret_castou mesmo uma combinação dessas. Mesmo se você souber agora o que irá degradar, suponha que você mude apara outro tipo mais tarde, pode muito bem ser o tipo de mudança de elenco sem que você receba um aviso, você não quer isso.
KillianDS
4
@KillianDS " suponha que você mude a para outro tipo mais tarde " qual tipo?
23412
2
Sim, aqueles ou um elenco implícito, se disponível. É muito mais claro qual é a intenção do elenco.
KillianDS
8
Girando fora a questão de encerramento, "como faço para converter um para digitar Test::A" ao invés de ser rígida sobre o requisito de ter um elenco de lá, e respondendo a vários anos de atraso apenas isso parece ser uma questão que ninguém popular, mais parece ter mencionado a alternativa , pelo padrão C ++ 11:
5.2.9 Molde estático
... uma expressão epode ser explicitamente convertida em um tipo T
usando um static_castdo formulário static_cast<T>(e)se a declaração
T t(e);estiver bem formada, para alguma variável temporária inventada t(8.5). O efeito de uma conversão explícita é o mesmo que executar a declaração e a inicialização e, em seguida, usar a variável temporária como resultado da conversão.
Portanto, o uso direto do formulário t(e)também funcionará, e você pode preferir o detalhe:
esta solução funcionou no caso de a opção do compilador ter bloqueado static_cast <> (verificação semântica). Não que isso faça sentido para mim, mas ainda limpo.
Buisson
1
Test castEnum = static_cast<Test>(a-1);converterá a em A. Se você não quiser o substrato 1, poderá redefinir enum:
enumTest{
A:1, B
};
Nesse caso, `Test castEnum = static_cast (a); ' pode ser usado para converter um para A.
int a
terá que ser 0, porque Test :: A tem um valor implícito de 0 e Test :: B tem um valor implícito de 1. A menos que o fato de converter especificamente para Test :: a é além do ponto ...Respostas:
fonte
auto
neste caso? Existe alguma melhoria de desempenho?fonte
Seu código
Solução
fonte
static_cast
seria um elenco melhor aqui.static_cast
, mas também pode ser umaconst_cast
ou até pior, umareinterpret_cast
ou mesmo uma combinação dessas. Mesmo se você souber agora o que irá degradar, suponha que você mudea
para outro tipo mais tarde, pode muito bem ser o tipo de mudança de elenco sem que você receba um aviso, você não quer isso.Girando fora a questão de encerramento, "como faço para converter um para digitar
Test::A
" ao invés de ser rígida sobre o requisito de ter um elenco de lá, e respondendo a vários anos de atraso apenas isso parece ser uma questão que ninguém popular, mais parece ter mencionado a alternativa , pelo padrão C ++ 11:Portanto, o uso direto do formulário
t(e)
também funcionará, e você pode preferir o detalhe:fonte
Test castEnum = static_cast<Test>(a-1);
converterá a em A. Se você não quiser o substrato 1, poderá redefinirenum
:Nesse caso, `Test castEnum = static_cast (a); ' pode ser usado para converter um para A.
fonte