AndAlso / OrElse no VBA

Eu estou tentando obter uma avaliação preguiçosa com ‘And’ na minha macro do Excel, fazendo o seguinte:

If Not myObject Is Nothing *And* myObject.test() Then 'do something' Else 'do something else' End If 

Eu sei avaliação preguiçosa existe em VB.NET como AndAlso e OrElse mas não consigo encontrar nada semelhante no VBA. Se a avaliação preguiçosa não existir no VBA, qual é a melhor maneira de estruturar o código para que ele avalie a maneira esperada?

O único curto-circuito (de uma espécie) está dentro Case avaliação da expressão Case , então a seguinte declaração desajeitada faz o que eu acho que você está pedindo;

 Select Case True Case (myObject Is Nothing), Not myObject.test() MsgBox "no instance or test == false" Case Else MsgBox "got instance & test == true" End Select End Sub 

Esta é uma questão antiga, mas esta questão ainda está viva e bem. Uma solução alternativa que usei:

 Dim success As Boolean ' False by default. If myObj Is Nothing Then ' Object is nothing, success = False already, do nothing. ElseIf Not myObj.test() Then ' Test failed, success = False already, do nothing. Else: success = True ' Object is not nothing and test passed. End If If success Then ' Do stuff... Else ' Do other stuff... End If 

Isso basicamente inverte a lógica na pergunta original, mas você obtém o mesmo resultado. Eu acho que é uma solução mais limpa do que os outros aqui que usam apenas instruções If . A solução usando uma instrução Select é inteligente, mas se você quiser uma alternativa usando apenas instruções If , acho que esta é a única a ser usada.

Ou você poderia criar uma function que toma seu object como um parâmetro e retorna booleano para qualquer um dos casos. Isso é o que eu costumo fazer.

ou seja

 if Proceed(objMyAwesomeObject) then 'do some really neat stuff here else 'do something else, eh end if ... end sub private function Proceed(objMyAwesomeObject as Object) if not objMyAweseomeObject is nothing then Proceed = true elseif objMyAwesomeObject.SomeProperty = SomeValue then Proceed = true else Proceed = false endif end function 
 If Not myObject Is Nothing Then If myObject.test() Then 'do something' End If Else 'do something else' End If 

Eu acho que é assim que você tem que fazer isso.

Editar

Talvez assim

 Dim bTestsFailed as Boolean bTestsFailed = False If Not myObject Is Nothing Then If myObject.test() Then 'do something' Else bTestsFailed = True End If Else bTestsFailed = True End If If bTestsFailed Then 'do something else End If 

Não é VBA grande?

Como a seguinte syntax funciona

 If myObject.test() Then do something 

Você poderia tentar

 If Not myObject Is Nothing Then If myObject.test() Then 'do something' Else 'do something else' End If 

Claro, se você quiser ‘fazer outra coisa’ se myObject Is Nothing, então isso pode não funcionar.

Melhorando esta resposta para uma pergunta diferente sobre o mesmo problema básico, aqui está o que eu escolhi fazer:

 dim conditionsValid as boolean conditionsValid = myObject Is Nothing if conditionsValid then conditionsValid = myObject.test() if conditionsValid then conditionsValid = myObject.anotherTest() if conditionsValid then 'do something' else 'do something else' end if 

Eu acho que este código é mais claro do que as outras respostas que foram sugeridas, e você (geralmente) não precisa de uma variável diferente para cada validação, que é a melhoria em relação à resposta original para a outra questão. A propósito, cada nova condição que você precisa adiciona apenas mais uma linha de código.