Szukaj…


Wprowadzenie

Programowanie funkcjonalne PHP opiera się na funkcjach. Funkcje w PHP zapewniają zorganizowany kod wielokrotnego użytku do wykonywania zestawu działań. Funkcje upraszczają proces kodowania, zapobiegają nadmiarowej logice i ułatwiają śledzenie kodu. W tym temacie opisano deklarację i wykorzystanie funkcji, argumentów, parametrów, instrukcji return i zakresu w PHP.

Przypisanie do zmiennych

Funkcje anonimowe można przypisać do zmiennych w celu użycia ich jako parametrów, w których oczekuje się wywołania zwrotnego:

$uppercase = function($data) {
    return strtoupper($data);
};

$mixedCase = ["Hello", "World"];
$uppercased = array_map($uppercase, $mixedCase);
print_r($uppercased);

Zmiennych tych można również używać jako samodzielnych wywołań funkcji:

echo $uppercase("Hello world!"); // HELLO WORLD!

Korzystanie ze zmiennych zewnętrznych

Konstrukcja use służy do importowania zmiennych do zakresu funkcji anonimowej:

$divisor = 2332;
$myfunction = function($number) use ($divisor) {
    return $number / $divisor;
};

echo $myfunction(81620); //Outputs 35

Zmienne można również importować przez odniesienie:

$collection = [];

$additem = function($item) use (&$collection) {
    $collection[] = $item;
};

$additem(1);
$additem(2);

//$collection is now [1,2]

Przekazywanie funkcji zwrotnej jako parametru

Istnieje kilka funkcji PHP, które akceptują zdefiniowane przez użytkownika funkcje zwrotne jako parametr, takie jak: call_user_func() , usort() i array_map() .

W zależności od tego, gdzie zdefiniowano funkcję wywołania zwrotnego zdefiniowaną przez użytkownika, istnieją różne sposoby jej przekazania:

Styl proceduralny:

function square($number)
{
    return $number * $number;
}

$initial_array = [1, 2, 3, 4, 5];
$final_array = array_map('square', $initial_array);
var_dump($final_array); // prints the new array with 1, 4, 9, 16, 25

Styl obiektowy:

class SquareHolder
{
    function square($number)
    {
        return $number * $number;
    }
}

$squaredHolder = new SquareHolder();
$initial_array = [1, 2, 3, 4, 5];
$final_array = array_map([$squaredHolder, 'square'], $initial_array);

var_dump($final_array); // prints the new array with 1, 4, 9, 16, 25

Styl obiektowy przy użyciu metody statycznej:

class StaticSquareHolder
{
    public static function square($number)
    {
        return $number * $number;
    }
}

$initial_array = [1, 2, 3, 4, 5];
$final_array = array_map(['StaticSquareHolder', 'square'], $initial_array);
// or:
$final_array = array_map('StaticSquareHolder::square', $initial_array); // for PHP >= 5.2.3

var_dump($final_array); // prints the new array with 1, 4, 9, 16, 25

Korzystanie z wbudowanych funkcji jako wywołań zwrotnych

W funkcjach, w których można callable argument jako argument, można również wstawić ciąg znaków za pomocą wbudowanej funkcji PHP. Powszechnie używa się parametru trim jako parametru array_map do usuwania array_map i końcowych białych znaków ze wszystkich ciągów w tablicy.

$arr = ['   one  ', 'two   ', '   three'];
var_dump(array_map('trim', $arr));

// array(3) {
//   [0] =>
//   string(3) "one"
//   [1] =>
//   string(3) "two"
//   [2] =>
//   string(5) "three"
// }

Funkcja anonimowa

Funkcja anonimowa to po prostu funkcja , która nie ma nazwy.

// Anonymous function
function() {
    return "Hello World!";
};

W PHP anonimowa funkcja jest traktowana jak wyrażenie i z tego powodu powinna być zakończona średnikiem ; .

Do zmiennej należy przypisać funkcję anonimową.

// Anonymous function assigned to a variable
$sayHello = function($name) {
    return "Hello $name!";
};

print $sayHello('John'); // Hello John

Lub powinien zostać przekazany jako parametr innej funkcji.

$users = [
    ['name' => 'Alice', 'age' => 20], 
    ['name' => 'Bobby', 'age' => 22], 
    ['name' => 'Carol', 'age' => 17]
];

// Map function applying anonymous function
$userName = array_map(function($user) {
    return $user['name'];
}, $users);

print_r($usersName); // ['Alice', 'Bobby', 'Carol']

Lub nawet zostały zwrócone z innej funkcji.

Samoczynne anonimowe funkcje:

// For PHP 7.x
(function () {
    echo "Hello world!";
})();

// For PHP 5.x
call_user_func(function () {
    echo "Hello world!";
});

Przekazywanie argumentu do samodzielnie wykonujących się funkcji anonimowych:

// For PHP 7.x
(function ($name) {
    echo "Hello $name!";
})('John');

// For PHP 5.x
call_user_func(function ($name) {
    echo "Hello $name!";
}, 'John');

Zakres

W PHP anonimowa funkcja ma swój własny zakres, jak każda inna funkcja PHP.

W JavaScript anonimowa funkcja może uzyskać dostęp do zmiennej spoza zakresu. Ale w PHP jest to niedozwolone.

$name = 'John';

// Anonymous function trying access outside scope
$sayHello = function() {
    return "Hello $name!";
}

print $sayHello('John'); // Hello !
// With notices active, there is also an Undefined variable $name notice

Domknięcia

Zamknięcie jest anonimową funkcją, która nie może uzyskać dostępu poza zakresem.

Definiując anonimową funkcję jako taką, tworzysz „przestrzeń nazw” dla tej funkcji. Obecnie ma dostęp tylko do tej przestrzeni nazw.

$externalVariable = "Hello";
$secondExternalVariable = "Foo"; 
$myFunction = function() { 
  
  var_dump($externalVariable, $secondExternalVariable); // returns two error notice, since the variables aren´t defined 

}

Nie ma dostępu do żadnych zmiennych zewnętrznych. Aby przyznać to uprawnienie dla tego obszaru nazw w celu uzyskania dostępu do zmiennych zewnętrznych, należy wprowadzić je za pomocą zamknięć ( use() ).

$myFunction = function() use($externalVariable, $secondExternalVariable) {
   var_dump($externalVariable, $secondExternalVariable); // Hello Foo
}

Jest to w dużej mierze przypisywane ścisłemu określaniu zakresu zmiennych PHP - jeśli zmienna nie jest zdefiniowana w zakresie lub nie jest wprowadzana z global wówczas nie istnieje.

Uwaga:

Dziedziczenie zmiennych z zakresu nadrzędnego to nie to samo, co używanie zmiennych globalnych. Zmienne globalne istnieją w zasięgu globalnym, który jest taki sam bez względu na wykonywaną funkcję.

Zakres nadrzędny zamknięcia jest funkcją, w której zostało zadeklarowane zamknięcie (niekoniecznie funkcja, z której został wywołany).

Na podstawie dokumentacji PHP dla funkcji anonimowych


W PHP zamknięcia używają wczesnego wiązania . Oznacza to, że zmienne przekazywane do przestrzeni nazw zamknięcia za use słowa kluczowego use będą miały takie same wartości, gdy zdefiniowane zostanie zamknięcie.

Aby zmienić to zachowanie, należy przekazać zmienną przez odniesienie .

$rate = .05;

// Exports variable to closure's scope
$calculateTax = function ($value) use ($rate) {
    return $value * $rate;
};

$rate = .1; 

print $calculateTax(100); // 5
$rate = .05;

// Exports variable to closure's scope
$calculateTax = function ($value) use (&$rate) { // notice the & before $rate
    return $value * $rate;
};

$rate = .1;

print $calculateTax(100); // 10

Domyślne argumenty nie są domyślnie wymagane przy definiowaniu anonimowych funkcji z / bez zamknięć.

$message = 'Im yelling at you';

$yell = function() use($message) {
    echo strtoupper($message);
};

$yell(); // returns: IM YELLING AT YOU

Czyste funkcje

Funkcja czysta to funkcja, która przy takim samym wejściu zawsze zwraca tę samą moc wyjściową i nie powoduje skutków ubocznych .

// This is a pure function
function add($a, $b) {
    return $a + $b;
}

Niektóre skutki uboczne to zmiana systemu plików , interakcja z bazami danych , drukowanie na ekranie .

// This is an impure function
function add($a, $b) {
    echo "Adding...";
    return $a + $b;
}

Obiekty jako funkcja

class SomeClass {
    public function __invoke($param1, $param2) {
        // put your code here
    }
}

$instance = new SomeClass();
$instance('First', 'Second'); // call the __invoke() method

Obiekt z metodą __invoke może być używany dokładnie tak samo, jak każda inna funkcja.

Metoda __invoke będzie miała dostęp do wszystkich właściwości obiektu i będzie mogła wywoływać dowolne metody.

Typowe metody funkcjonalne w PHP

Mapowanie

Zastosowanie funkcji do wszystkich elementów tablicy:

array_map('strtoupper', $array);

Należy pamiętać, że jest to jedyna metoda listy, w której oddzwanianie jest pierwsze.

Zmniejszenie (lub złożenie)

Zmniejszenie tablicy do jednej wartości:

$sum = array_reduce($numbers, function ($carry, $number) {
   return $carry + $number;
});

Filtracja

Zwraca tylko elementy tablicy, dla których callback zwraca true :

$onlyEven = array_filter($numbers, function ($number) {
    return ($number % 2) === 0;
});


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