PHP

Strict Types e novos tipos de declaração no PHP 7

Por em

O PHP 7 introduziu mais quatro tipos de dados para a declaração de parâmetros de funções e métodos. Vamos lá!!

Antes de irmos aos exemplos, precisamos entender um outro conceito, o strict_types.

Por padrão todos os arquivos PHP estão em modo “fraco” de checagem de tipo, para entender melhor veja o exemplo abaixo:

<?php

function sum(int $num1) : int 
{
    return $num1 + 1;
}

var_dump(sum('1')); // int(2)

Percebam que nossa função foi assinada para receber um parâmetro $num1 do tipo int, e retornar também um int, sendo a soma do parâmetro passado mais 1, porém a chamada da função é feita passando a string ‘1’ e mesmo assim o PHP conseguiu interpretar, converter (string -> int) e retornar um int, que neste caso foi o número 2. E isso só foi possível devido estarmos com o modo fraco de tipo de checagem. Interessante não ?

Agora vamos ativar o modo strict_types e fazer o mesmo exemplo anterior:

<?php

declare(strict_types=1);

function sum(int $num1) : int 
{
    return $num1 + 1;
}

var_dump(sum('1'));

A única mudança feita foi a inclusão do comando declare(strict_types=1), ou seja, a partir deste momento, a checagem de tipo será feita, e é como se estivéssemos dizendo para o PHP para utilizar o modo “forte” de checagem de tipo. O exemplo acima irá produzir um fatal error, como abaixo:

PHP Fatal error:  Uncaught TypeError: Argument 1 passed to sum() must be of the type integer, string given

Agora que já sabemos como utilizar o modo “forte” de checagem de tipo do PHP, vamos ver quais são os 4 tipos de dados adicionados e que agora são permitidos como declaração de tipo de parâmetro de funções ou métodos.

Os tipos introduzidos na versão 7 do PHP, foram: int, float, string e bool. Vamos ver alguns exemplos abaixo:

<?php

declare(strict_types=1);

class Actor
{
    private $salary = 2500;
    private $name = 'Chuck Norris';

    public function getNameWithPrefix(string $sufixForName) : string 
    {
    	return $sufixForName . ' ' . $this->name;
    }

    public function getSalaryWithCommission(float $v) : float
    {
        return $this->salary * $v;
    }
}

$actor = new Actor();

var_dump($actor->getSalaryWithCommission(1.3)); // float(3250)
var_dump($actor->getNameWithPrefix('Mr.')); // string(16) "Mr. Chuck Norris"

Vejam que acima, temos uma classe Actor e dois métodos getNameWithPrefix(string $sufixForName) : string e getSalaryWithCommission(float $v) : float, percebam que cada uma delas declara um parâmetro string e float respectivamente, e logo após instanciarmos a classe, fazemos as chamadas a estes métodos passando os parâmetros corretamente. Porém, vamos fazer uma chamada ao método getSalaryWithCommission(float $v) : float passando como parâmetro um int:

var_dump($actor->getSalaryWithCommission(4)); // float(10000)

Opa! Isso deveria ter dado erro já que a função deveria ter recebido um float e o foi passado um int. Bem neste caso não, ja que int são aceitos para argumentos float, porém o contrário não será aceito.

Percebam que este recurso será muito útil principalmente para as documentações de códigos, já que agora temos uma forma de obrigar o tipo de dado que é passado para uma função ou método.

Espero que tenham gostado, um abraço e até a próxima!