W3docs

callable

Impara il type hint callable in PHP — forme di callback, is_callable(), closure e __invoke con esempi pratici.

Il Type Hint callable in PHP

Un callback è qualsiasi valore che PHP può invocare come se fosse una funzione — un nome di funzione semplice, un metodo su un oggetto, una closure e così via. Il type hint callable ti permette di dichiarare che un parametro, una proprietà o un valore di ritorno deve essere uno di questi valori invocabili. Combinato con una chiamata reale in seguito ($callback(...)), costituisce la base delle funzioni di ordine superiore come array_map(), usort() e array_filter().

Questa pagina tratta la sintassi, ogni forma che un callable può assumere, come validarne uno a runtime con is_callable() e le insidie più comuni.

Sintassi

Aggiungi callable prima del nome del parametro (o come tipo di proprietà/ritorno) per richiedere un valore invocabile:

<?php

function run(callable $callback) {
  // $callback is guaranteed to be invocable here
  return $callback();
}

Se il chiamante passa qualcosa che non è callable, PHP lancia un TypeError prima che il corpo della funzione venga eseguito — quindi all'interno della funzione puoi fare affidamento sul fatto che $callback() funzioni.

Le cinque forme di un callable

callable accetta più di un semplice nome di funzione. Ogni riga qui sotto è un valore diverso che PHP riconosce come callback.

FormaValore di esempioChiama
Nome di funzione (string)'strtoupper'una funzione con nome
Metodo statico (string)'MyClass::myMethod'un metodo statico
Metodo statico (array)['MyClass', 'myMethod']un metodo statico
Metodo di istanza (array)[$object, 'myMethod']un metodo su $object
Closure / arrow fnfunction () { ... }una funzione anonima
Oggetto invocabile$obj con __invoke()il metodo __invoke() dell'oggetto

L'esempio qui sotto le esercita tutte con un unico helper run():

<?php

function run(callable $callback): string
{
    return $callback();
}

// 1. A named function passed by string
function greet(): string
{
    return "Hello world!";
}
echo run('greet') . PHP_EOL;

// 2 & 3. Instance method and static method
class Greeter
{
    public function instanceHello(): string
    {
        return "Hello from an instance";
    }

    public static function staticHello(): string
    {
        return "Hello from a static method";
    }
}

$greeter = new Greeter();
echo run([$greeter, 'instanceHello']) . PHP_EOL; // instance method
echo run(['Greeter', 'staticHello']) . PHP_EOL;  // static method
echo run('Greeter::staticHello') . PHP_EOL;      // static method as a string

// 4. A closure (anonymous function)
echo run(function (): string {
    return "Hello from a closure";
}) . PHP_EOL;

// 5. An invokable object (has an __invoke method)
class Loud
{
    public function __invoke(): string
    {
        return "HELLO FROM __INVOKE";
    }
}
echo run(new Loud()) . PHP_EOL;

L'esecuzione stampa:

Hello world!
Hello from an instance
Hello from a static method
Hello from a static method
Hello from a closure
HELLO FROM __INVOKE

Verificare un valore con is_callable()

Un type hint valida l'input al confine della funzione, ma a volte si riceve un valore dinamicamente (da configurazione, input utente o un registro) e si vuole verificarlo prima di chiamarlo. Usa is_callable():

<?php

$maybe = 'strtoupper';

if (is_callable($maybe)) {
    echo $maybe('hi'), PHP_EOL; // HI
} else {
    echo "Not callable", PHP_EOL;
}

var_dump(is_callable('strtoupper'));        // bool(true)
var_dump(is_callable('no_such_function'));  // bool(false)
var_dump(is_callable([new DateTime(), 'format'])); // bool(true)

is_callable() restituisce true solo se il target esiste effettivamente ed è raggiungibile — un nome di funzione scritto male restituisce false invece di andare in crash, il che lo rende ideale per codice di tipo plugin.

Sintassi callable di prima classe (PHP 8.1+)

Da PHP 8.1 puoi trasformare qualsiasi funzione o metodo in una Closure con la sintassi (...). Questo è type-safe, compatibile con i tool IDE, e evita stringhe fragili:

<?php

$upper = strtoupper(...);          // a Closure wrapping strtoupper
echo $upper('hello'), PHP_EOL;     // HELLO

$greeter = new DateTime('2020-01-01');
$fmt = $greeter->format(...);      // bound to $greeter
echo $fmt('Y'), PHP_EOL;           // 2020

Poiché il risultato è una Closure, soddisfa il type hint callable ovunque ci si aspetti un callback.

Insidie comuni

  • Metodi privati/protetti. Un callable [$object, 'method'] funziona solo se il metodo è visibile da dove viene invocato. Chiamare un metodo privato tramite stringa/array dall'esterno della sua classe fallisce.
  • callable non può essere un tipo di proprietà prima di PHP 8.2 con avvertenze. L'uso di callable come tipo di proprietà di classe non è consentito; usa invece una Closure (o \Closure), oppure accettala come parametro.
  • Chiamata statica senza oggetto. [$object, 'staticMethod'] funziona, ma per chiarezza preferisci ['ClassName', 'staticMethod'] o 'ClassName::staticMethod' per i target statici. Vedi metodi statici.
  • Stringhe vs. oggetti. Un callable stringa come 'Greeter::staticHello' funziona solo per i metodi statici, non per quelli di istanza — le chiamate di istanza richiedono la forma array [$object, 'method'].

Perché usare callable?

  • Type safety: PHP rifiuta i callback non validi al sito di chiamata con un chiaro TypeError invece di fallire in profondità all'interno della funzione.
  • Firme auto-documentanti: i lettori (e strumenti come PHPStan o Psalm) vedono immediatamente che un parametro è "qualcosa che chiamerò."
  • Flessibilità: la stessa funzione accetta un nome di funzione, un metodo o una closure — così i chiamanti scelgono la forma più comoda.

Vedi anche

Pratica

Pratica
Cosa denota 'callable' in PHP?
Cosa denota 'callable' in PHP?
Was this page helpful?