Condicionais
Doggie DaddyCondicionais ou decisões no fluxo de execução são apenas mensagens enviadas a um objeto boolean (Boolean).
As mensagens são do tipo com palavras chaves (keyword messages).
As quatro mensagens que vamos abordar são:
ifTrue:ifFalse:
ifFalse:ifTrue:
ifTrue:
ifFalse:
As quatro formas podem ser descritas como:
aBoolean ifTrue: trueBlock ifFalse: falseBlock
aBoolean ifFalse: falseBlock ifTrue: trueBlock
aBoolean ifTrue: trueBlock
aBoolean ifFalse: falseBlock
Se aBoolean
for true
os blocos que são argumentos após ifTrue:
são executados. Se for false
os blocos que são argumentos após ifFalse:
são executados. O resultado da expressão condicional é o mesmo do bloco executado. O resultado da execução de um bloco é o mesmo que da última expressão executada no bloco. Por exemplo: 5 > 2 ifTrue: [ 'Verdadeiro'. 42 ]
retornará 42
.
No caso em que não há bloco correspondente ao valor da variável booleana o valor retornado é nil
. Por exemplo: false ifTrue: [ 42 ]
retorna nil
. true ifFalse: [ 42 ]
também retorna nil
. Experimente no Playground.
Não foi dito explicitamente até agora mas você já deve ter concluido que as expressões no Smalltalk são separadas por .
.
Tente prever o resultado de cada uma das 8 expressões abaixo antes de executá-las com Print it
.
Atenção! Há uma pegadinha no uso de condicionais em que um código com erro passa despercebido pois compila e executa mas pode ter resultados inesperados. No Smalltalk os blocos que não precisam de argumentos são executados enviando-se a mensagemvalue
. Acontece que quase todos os objetos no Smalltalk sãovaluable
, isto é, respondem à mensagemvalue
. Os condicionais são mensagens que recebem argumentos que são blocos e os executam enviando a mensagemvalue
. Mas se você passar por engano um objeto que não seja um bloco pode ter surpresas ou nem perceber o erro de imediato pois tais objetos são aceitos e usados enviando a mensagemvalue
para eles.
Veja abaixo exemplos do que foi chamado à atenção acima.
O que aconteceu?
No primeiro caso em que foram usados blocos o resultado da expressão booleana determina qual bloco vai ser executado. Lembre-se que os blocos não fazem nada enquanto não recebem a mensagem value
. No caso a expressão 5 > 3
tem valor true
e por isso seleciona o bloco [ x := x + 1 ]
para execução o que faz com que o valor de x
, que é 42
, seja incrementado e o resultado é 43
.
No segundo caso a coisa é sutilmente diferente. O Smalltalk antes de executar uma expressão que tem vários argumentos avalia cada argumento.
A nossa mensagem ifTrue:ifFalse:
enviada ao objeto que é resultado da avaliação da expressão 5 > 3
(que sabemos que é true
) também avalia logo as expressões (x := x + 1)
e (x := x - 1)
. Com isso primeiro incrementa x
de 1
e depois subtrai 1
desse resultado fazendo com que x
volte a valer 42
.
Em seguida a mensagem value
é enviada ao resultado da expressão (x := x + 1)
que foi avaliada como 43
. Mas 43 value
retorna 43
pois quase todos os objetos retornam a si mesmos quando recebem a mensagem value
.
Note que não obtivemos 43
quando usamos o Print it
porque a última expressão do conjunto de expressões que realçamos é x
cujo valor é 42
.
Se você deixar a última expressão (o x
) de fora do realce vai obter 43
com o Print it
pois este é o resultado da condicional (Veja na figura abaixo).
Mas você deve já estar perguntando: Mas no caso dos blocos não é a mesma coisa? Os dois blocos serão avaliados antes que um só deles seja selecionado para execução?
É verdade mas lembre-se que a avaliação de um bloco não faz nada, como você bem viu na lição anterior. Só quando o bloco é selecionado para a execução pela condicional é que recebe a mensagem value
e então executa o seu código.
Encerrando a sessão
Encerre salvando a imagem.