Szukaj…


Składnia

  • funkcja f (nazwa klasy $ param) {}
  • funkcja f (bool $ param) {}
  • funkcja f (int $ param) {}
  • funkcja f (float $ param) {}
  • funkcja f (ciąg $ param) {}
  • funkcja f (self $ param) {}
  • funkcja f (callable $ param) {}
  • funkcja f (tablica $ param) {}
  • funkcja f (? nazwa_typu $ param) {}
  • funkcja f (): nazwa_typu {}
  • funkcja f (): void {}
  • funkcja f ():? nazwa_typu {}

Uwagi

Wpisz podpowiedzi lub deklaracje typu są obronny praktyka programowania, który zapewnia parametry funkcji są określonego typu. Jest to szczególnie przydatne, gdy typowanie interfejsu jest możliwe, ponieważ pozwala funkcji zagwarantować, że podany parametr będzie miał te same metody, jakie są wymagane w interfejsie.

Przekazanie niepoprawnego typu do funkcji z podpowiedzią typu spowoduje błąd krytyczny:

Błąd krytyczny: Uncaught TypeError: Argument X przekazany do foo () musi być typu RequiredType , podano ProvidedType

Wpisz wskazujące typy skalarne, tablice i kallaby

Obsługę parametrów tablicy podpowiedzi typu (i zwracania wartości po PHP 7.1) dodano w PHP 5.1 z array słów kluczowych. Wszelkie tablice o dowolnych wymiarach i typach, a także puste tablice, są poprawnymi wartościami.

Wsparcie dla kalendarzy podpowiedzi typu zostało dodane w PHP 5.4. Każda wartość, która is_callable() jest ważna dla parametrów i wartości zwracanych zasugerował callable , czyli Closure obiektów, sznurki i nazwa funkcji array(class_name|object, method_name) .

Jeśli literówka występuje w nazwie funkcji tak, że nie jest to is_callable() , wyświetli się mniej oczywisty komunikat o błędzie:

Błąd krytyczny: Uncaught TypeError: Argument 1 przekazany do foo () musi być typu wywoływalnego, podano ciąg / tablicę

function foo(callable $c) {}
foo("count"); // valid
foo("Phar::running"); // valid
foo(["Phar", "running"); // valid
foo([new ReflectionClass("stdClass"), "getName"]); // valid
foo(function() {}); // valid

foo("no_such_function"); // callable expected, string given

Metody niestatyczne mogą być również przekazywane jako wywołania w formacie statycznym, co powoduje ostrzeżenie o wycofaniu i błąd E_STRICT poziomu odpowiednio w PHP 7 i 5.

Uwzględniono widoczność metody. Jeśli kontekst metody z parametrem callable nie ma dostępu do udostępnionego wywołania , zakończy się tak, jakby metoda nie istniała.

class Foo{
  private static function f(){
    echo "Good" . PHP_EOL;
  }

  public static function r(callable $c){
    $c();
  }
}

function r(callable $c){}

Foo::r(["Foo", "f"]);
r(["Foo", "f"]);

Wynik:

Błąd krytyczny: Uncaught TypeError: Argument 1 przekazany do funkcji r () musi być możliwy do wywołania, z podaną tablicą

W PHP 7. dodano obsługę typów skalarnych podpowiedzi typu. Oznacza to, że zyskujemy wsparcie podpowiedzi typu dla wartości boolean , integer , integer float i string .

<?php

function add(int $a, int $b) {
    return $a + $b;
}

var_dump(add(1, 2)); // Outputs "int(3)"

Domyślnie PHP spróbuje rzucić dowolny podany argument, aby pasował do podpowiedzi typu. Zmiana wywołania add(1.5, 2) daje dokładnie taki sam wynik, ponieważ zmiennoprzecinkowa 1.5 została rzucona na int przez PHP.

Aby zatrzymać to zachowanie, należy dodać declare(strict_types=1); na górze każdego pliku źródłowego PHP, który tego wymaga.

<?php

declare(strict_types=1);

function add(int $a, int $b) {
    return $a + $b;
}

var_dump(add(1.5, 2));

Powyższy skrypt powoduje teraz błąd krytyczny:

Błąd krytyczny: Uncaught TypeError: Argument 1 przekazany do funkcji add () musi być liczbą całkowitą, podano liczbę zmiennoprzecinkową

Wyjątek: typy specjalne

Niektóre funkcje PHP może zwracać wartość typu resource . Ponieważ nie jest to typ skalarny, ale specjalny, nie można wpisać podpowiedzi.

Na przykład curl_init() zwróci resource , a także fopen() . Oczywiście te dwa zasoby nie są ze sobą kompatybilne. Z tego powodu PHP 7 zawsze rzuca następujący błąd typu podczas błędu resource podpowiedzi typu:

TypeError: Argument 1 przekazany do sample () musi być instancją zasobu, zasobu podano

Wpisz wskazujące obiekty ogólne

Ponieważ obiekty PHP nie dziedziczą po żadnej klasie bazowej (w tym stdClass ), nie ma obsługi typu wskazującego ogólny typ obiektu.

Na przykład poniższe nie będzie działać.

<?php

function doSomething(object $obj) {
    return $obj;
}

class ClassOne {}
class ClassTwo {}

$classOne= new ClassOne();
$classTwo= new ClassTwo();

doSomething($classOne);
doSomething($classTwo);

I spowoduje błąd krytyczny:

Błąd krytyczny: Uncaught TypeError: Argument 1 przekazany do doSomething () musi być instancją obiektu, podaną instancją OperationOne

Obejściem tego problemu jest zadeklarowanie zdegenerowanego interfejsu, który nie definiuje żadnych metod, i wszystkie obiekty implementują ten interfejs.

<?php

interface Object {}

function doSomething(Object $obj) {
    return $obj;
}

class ClassOne implements Object {}
class ClassTwo implements Object {}

$classOne = new ClassOne();
$classTwo = new ClassTwo();

doSomething($classOne);
doSomething($classTwo);

Wpisz klasy i interfejsy podpowiedzi

W PHP 5 dodano podpowiedzi do klas i interfejsów.

Wskazówka dotycząca klasy

<?php

class Student
{
    public $name = 'Chris';
}

class School
{
    public $name = 'University of Edinburgh';
}

function enroll(Student $student, School $school)
{
    echo $student->name . ' is being enrolled at ' . $school->name;
}

$student = new Student();
$school = new School();

enroll($student, $school);

Powyższy skrypt generuje:

Chris jest zapisywany na University of Edinburgh


Wskazówka dotycząca rodzaju interfejsu

<?php

interface Enrollable {};
interface Attendable {};

class Chris implements Enrollable
{
    public $name = 'Chris';
}

class UniversityOfEdinburgh implements Attendable
{
    public $name = 'University of Edinburgh';
}

function enroll(Enrollable $enrollee, Attendable $premises)
{
    echo $enrollee->name . ' is being enrolled at ' . $premises->name;
}

$chris = new Chris();
$edinburgh = new UniversityOfEdinburgh();

enroll($chris, $edinburgh);

Powyższy przykład generuje to samo co poprzednio:

Chris jest zapisywany na University of Edinburgh

Wskazówki typu własnego

self słowo kluczowe może być stosowany jako wskazówka typu wskazuje, że wartość musi być instancją klasy, który deklaruje metodę.

Rodzaj Podpowiedź Bez powrotu (Void)

W PHP 7.1 dodano void return type. Chociaż PHP nie ma rzeczywistej wartości void , w językach programowania jest ogólnie zrozumiałe, że funkcja, która niczego nie zwraca, zwraca wartość void . Nie należy tego mylić ze zwracaniem null , ponieważ null jest wartością, którą można zwrócić.

function lacks_return(): void {
    // valid
}

Pamiętaj, że jeśli zadeklarujesz void zwrot, nie możesz zwrócić żadnych wartości lub otrzymasz błąd krytyczny:

function should_return_nothing(): void {
    return null; // Fatal error: A void function must not return a value
}

Jednak użycie return w celu wyjścia z funkcji jest poprawne:

function returns_nothing(): void {
    return; // valid
}

Podpowiedzi typu zerowalnego

Parametry

Podpowiedź typu zerowalnego została dodana w PHP 7.1 przy użyciu ? operator przed wskazówką dotyczącą typu.

function f(?string $a) {}
function g(string $a) {}

f(null); // valid
g(null); // TypeError: Argument 1 passed to g() must be of the type string, null given

Przed PHP 7.1, jeśli parametr ma wskazówkę dotyczącą typu, musi zadeklarować wartość domyślną null aby zaakceptować wartości null.

function f(string $a = null) {}
function g(string $a) {}

f(null); // valid
g(null); // TypeError: Argument 1 passed to g() must be of the type string, null given

Zwróć wartości

W PHP 7.0 funkcje z typem zwracanym nie mogą zwracać wartości null.

W PHP 7.1 funkcje mogą zadeklarować podpowiedź typu zerowalnego. Jednak funkcja musi nadal zwracać null, a nie void (brak / puste instrukcje return).

function f() : ?string {
    return null;
}

function g() : ?string {}
function h() : ?string {}

f(); // OK
g(); // TypeError: Return value of g() must be of the type string or null, none returned
h(); // TypeError: Return value of h() must be of the type string or null, none returned


Modified text is an extract of the original Stack Overflow Documentation
Licencjonowany na podstawie CC BY-SA 3.0
Nie związany z Stack Overflow