Compilador não sinalizar valor de retorno incorreto para HRESULT
-
22-07-2019 - |
Pergunta
Eu passei apenas maneira muito tempo tentando diagnosticar por que, na seguinte trecho de código, o método ProcessEvent()
parecia estar ignorando o valor false
I passado para aInvokeEventHandler
:
HRESULT
CEventManager::
Process(Event anEvent)
{
return (m_pPool->GetFsm()->ProcessEvent(anEvent), false);
}
// Definition of ProcessEvent()
HRESULT ProcessEvent(const Event& anEvent, bool aInvokeEventHandler = true);
Sempre que quebrou no método ProcessEvent()
, aInvokeEventHandler
seria sempre true
, independentemente de eu passei em false
.
Levou um colega de trabalho para apontar-me que o valor false
deve estar dentro do interior parênteses na linha return
, assim:
return m_pPool->GetFsm()->ProcessEvent(anEvent, false); // Corrected code
Assim que eu vi isso, eu me chutou. Spotting este foi obviamente mais difícil porque o redundante codificador original usado externo parênteses na linha return
.
A minha pergunta é, por que não o compilador pegar isso para mim?
O meu método está retornando um HRESULT
, ainda no código original acima, eu estou voltando claramente um conjunto composto de valores entre parênteses, ou seja:
(HRESULT, bool)
É notação assim aceitável nos padrões do C / C ++, e em caso afirmativo, qual o propósito haveria em permitir isso? Ou este é um bug no compilador?
Solução
Você está sofrendo do operador vírgula, que avalia e descarta o valor de sua mão esquerda operando, e, em seguida, avalia a sua mão direita operando como o valor da expressão.
Além disso, o valor padrão para o argumento para ProcessEvent É por isso que a sua chamada um argumento era aceitável.
Outras dicas
O que você escreveu:
return (m_pPool->GetFsm()->ProcessEvent(anEvent), false);
O que significa (aproximadamente):
bool temp = false;
m_pPool->GetFsm()->ProcessEvent(anEvent);
return temp;
A vírgula é realmente um operador válido -. Consulte este post
O problema que você está vendo mentiras em duas coisas.
-
O operador vírgula é jogar fora o valor no lado esquerdo e retornando somente o valor do lado direito (Fasle)
-
Um HRESULT é apenas um valor longo e, portanto, há uma conversão implícita do valor falso HRESULT, portanto, nenhum compilador erro.