Pular para o conteúdo

Operadores

OperadorDescriçãoExemplo
+Adiçãoa + b
-Subtraçãoa - b
*Multiplicaçãoa * b
/Divisãoa / b
%Resto da divisãoa % b
- (unário)Negação-a
int a = 10;
int b = 3;
mostran(a + b); // 13
mostran(a - b); // 7
mostran(a * b); // 30
mostran(a % b); // 1
mostran(-a); // -10

O % também funciona entre reais, onde dá o resto da divisão real:

num x = 7.5;
mostran(x % 2.0); // 1.5

A divisão segue o C: entre dois inteiros é inteira e trunca em direção a zero; se um dos operandos for real, a divisão é real.

int a = 7 / 2; // 3
int b = -7 / 2; // -3
num c = 7 / 2; // 3.0: a divisão é inteira, e só depois o 3 passa a real
num d = 7 / 2.0; // 3.5
num e = (num) a / 2; // 1.5

Para obter a parte decimal entre dois inteiros, converte um deles para real com um cast, como no último exemplo.

Dividir por zero, ou calcular o resto por zero, termina o programa com uma mensagem de erro, tanto entre inteiros como entre reais:

num x = 1.5;
mostran(x / 0); // programa.kriol:2: erro de execução: divisão por zero

Entre inteiros com sinal, MIN / -1 (por exemplo i8 -128 / -1) também termina o programa, com o resultado da divisão não cabe no tipo do número inteiro: o valor positivo correspondente ao mínimo não existe no tipo.

Ao contrário da divisão por zero, uma soma ou multiplicação que não caiba no tipo não para o programa: o valor dá a volta, como em C. Convém saber, porque o programa continua a correr com um número errado:

u8 cheiu = 255;
cheiu += 1;
mostran(cheiu); // 0: deu a volta ao início
int maximu = 9223372036854775807;
maximu += 1;
mostran(maximu); // -9223372036854775808

O mesmo acontece com o - unário num tipo sem sinal, que não tem onde guardar o sinal:

u8 a = 5;
mostran(-a); // 251, isto é 256 - 5

Se um valor puder chegar perto do limite do tipo, escolhe um tipo mais largo ou verifica-o antes da conta com um si ou um konfirma.

OperadorDescrição
==Igual
!=Diferente
<Menor que
>Maior que
<=Menor ou igual
>=Maior ou igual
int x = 5;
bool resultado = x > 3; // sin
bool igual = x == 5; // sin
OperadorKriolDescrição
E lógico&&Verdadeiro se ambos forem verdadeiros
Ou lógico||Verdadeiro se pelo menos um for verdadeiro
Negação!Inverte o valor lógico
bool a = sin;
bool b = nau;
mostran(a && b); // nau
mostran(a || b); // sin
mostran(!a); // nau

Tal como numa condição e como em C, os operadores lógicos também aceitam números: um número é verdadeiro quando não é zero. Assim, !n é sin quando n == 0 e nau caso contrário. O resultado é sempre um bool.

int n = 0;
mostran(!n); // sin
mostran(!5); // nau
mostran(n || 3); // sin
mostran(n && 3); // nau

&& e || avaliam o operando da direita só quando é preciso: em a && b, b só é avaliado se a for verdadeiro, e em a || b, só se a for falso.

Essa regra, a avaliação em curto-circuito, é o que torna seguro pôr a verificação e o uso na mesma condição: em si i < 3 && v[i] > 0, o v[i] nunca é lido quando i é 3 ou mais.

Os operadores de bits atuam sobre cada bit de um inteiro, e só aceitam operandos inteiros (não aceitam bool nem números reais). Para valores lógicos usa &&, || e !.

OperadorDescriçãoExemplo
&E bit a bita & b
|Ou bit a bita | b
^Ou exclusivo bit a bita ^ b
~Complemento (unário)~a
mostran(12 & 10); // 8
mostran(12 | 10); // 14
mostran(12 ^ 10); // 6
mostran(~0); // -1
u8 mascara = 15;
mostran(~mascara); // 240

Tal como um literal inteiro, ~ aplicado a um literal adapta-se ao tipo onde é usado. Num tipo sem sinal, troca os bits dentro da largura desse tipo:

u8 tudu = ~0; // 255
u8 par = mascara & ~1; // 14: limpa o bit menos significativo
i8 menos = ~0; // -1

Ao contrário do C, os operadores de bits têm maior precedência do que as comparações, por isso x & 1 == 1 lê-se (x & 1) == 1.

OperadorEquivalente aAplica-se a
+=x = x + valnúmeros
-=x = x - valnúmeros
*=x = x * valnúmeros
/=x = x / valnúmeros
%=x = x % valnúmeros
&=x = x & valinteiros
|=x = x | valinteiros
^=x = x ^ valinteiros
int n = 10;
n += 5; // n == 15
n -= 3; // n == 12
n *= 2; // n == 24
n %= 5; // n == 4
n |= 8; // n == 12
n /= 3; // n == 4 (divisão inteira)
num m = 10.0;
m /= 4; // m == 2.5

Como em C, x op= v calcula x op v no tipo comum dos dois operandos e guarda o resultado no tipo de x. Assim, num inteiro, um valor real é truncado:

int n = 9;
n /= 2.5; // 9 / 2.5 = 3.6, guardado como 3

Do maior para o menor precedência:

  1. Operadores unários -, !, ~ e casts (tipo)
  2. *, /, %
  3. +, -
  4. &
  5. ^
  6. |
  7. <, >, <=, >=
  8. ==, !=
  9. &&
  10. ||
  11. sinon (valor por omissão de uma chamada que pode falhar)
  12. =, +=, -=, *=, /=, %=, &=, |=, ^=

Usa parênteses () para forçar a ordem de avaliação desejada: 2 + 3 * 4 dá 14, e (2 + 3) * 4 dá 20. Em caso de dúvida, põe os parênteses.