Today we will learn a very interesting topic known as closure. PHP started support of closure with version 5.3.0. Before understanding closure term first we have to understand some terms. which are-
Lazy Loading: – Lazy loading terms that the loading of an object is delayed until it is really required.
Anonymous function: – An anonymous function is a function without name. It is assigned to a variable or provided as a parameter to another function. Let us see an example for anonymous function-
<?php
$webkul = function() {
return "Hi you are in anonymous function.";
};
//anonymous function have semicolon at last
echo $webkul();
?>
//output: Hi you are in anonymous function.
In this example we have created a function which have a return string and assign to a variable $webkul , this variable is then called as a function . Note that anonymous function always ends with a semicolon.
Now we can understand closure very well. A closure is an object representation of an anonymous function. We can see that the anonymous function in the above code actually returns an object of closure which is assigned to and called using the variable $webkul. You can say closure is an object oriented way to use anonymous functions. Closure can access data external to it. For example. It can access data of the class, inside class any function in which it is written or if it is not written in any class or function it can access the data directly specified. To use external data, it has to be specified in the use clause of the closure. Take a look at this example.
<?php
$user="Webkul demo";
$showMe=function() use($user){
echo "Welcome ".$user;
};
//Call $showMe variable as function to see o/p
$showMe();
?>
//output: Welcome Webkul demo
Here, we have a value “Webkul demo” in variable $user . It is accessed inside the anonymous function using use keyword. The closure object is stored in $showMe variable and then the function is called using this variable. Now If you want to change the value of external variable accessed inside the closure, you can do it by passing the value by reference so that the change occurs at the actual location of the value And actual value will be remain same. for example –
<?php
$department="Opencart";
$output=function() use(&$department){
$department="Magento";
echo "Welcome to ".$department;
};
echo "Before change in closure function:<br>";
echo "Welcome to ".$department;
// OUTPUT -> Before change in closure function: Welcome to Opencart
echo "After change in closure function:<br>";
echo "Welcome to ";
$output();
// OUTPUT -> After change in closure function: Welcome to Magento
?>
Here we have variable $department which have actual value “Opencart” .Now inside the closure we have used this variable by call by reference and change value to “magento”. Closures can also access all the private data of a class. Lets see an example for this-
<?php
class webkul
{
private $id;
private $emp;
public function __construct($id,$emp)
{
$this->id=$id;
$this->emp=$emp;
}
public function info(){
return function(){
return "ID = {$this->id} <br>Employee = {$this->emp}.";
};
}
}
$webkulEmp1 = new webkul(101,'opencartEmployee');
$webkulEmp1->info();
//output:
// ID = 101
// Employee = opencartEmployee.
Here we are accessing the private members $id and $emp in the closure, which are defined as private. But we use them with help of inside function closure. If a closure defined inside a class and if you don’t want to allow it to use the data in the class, you can use static keyword. When we use static keyword with a closure , then closure is not allowed to use the data in the class.
<?php
class staticClosure {
private $id;
public function __construct($id) {
$this->id=$id;
}
public function company($name) {
return static funciton() use($name) {
echo "This is a ".$name." staticClosure.";
};
}
}
$staticClosure=new staticClosure();
$staticClosure->company("Webkul Soft");
?>
This will help save memory needed to store the object data when used in the closure. This is more useful when you use more than one closure in a class with static keyword. Thus we have learned closure in this blog. It is very useful to use closures in place of functions when we require to perform a small task and in this task will be used only once in the script.