Lazy and Eager Loading in PHP 5

As you may know, design patterns are proven, well-trusted solutions that tackle a specific problem that occurs frequently in software development. As with many other principles and paradigms in this area, some patterns are more popular and easier to learn than others, and when applied properly, can considerably improve the efficiency and performance of an application. This five-part article series will discuss two of these.

In the case of PHP 5, which is better suited for developing web-based programs, there are two complementary design patterns that can be of great help in  building faster and more reliable applications. Of course, as this article’s title suggests, I’m talking about the lazy and eager loading patterns. Despite their rather funny names, they are pretty easy to implement in PHP 5-controlled environments.

But before I start coding some functional examples in the next few lines, it would be useful to explain briefly what these patterns actually are, so you’ll understand their underlying logic. First, the expression “lazy loading” refers to the ability of a program to load a specific resource only at the time it’s required, and not before.

In this case, a resource can be anything that fits in into a program’s context, ranging from one or multiple classes, functions, database result sets, one or more objects, and so forth (feel free to add your own to the list). Naturally, lazy loading is a powerful pattern that very often is used in PHP 5 to speed up the performance of database-driven applications.

For instance, it’s possible to “delay” or defer the instantiation of a certain class until a program really requests this process, thus preventing the overhead of storing an object in memory that will remain unused most of the time. In this  example, this procedure would be called “lazy initialization.”

On the other hand, eager loading is the opposite of lazy loading. It simply refers to the process of loading or prefetching a resource with anticipation, regardless of whether or not it will be required by a program. At first glance, it seems to be a rather inefficient approach, but this is merely a misconception, trust me. Certainly, one common use of eager loading is when processing database result sets retrieved from two or more related tables. In a situation like this, it would be possible to prefetch all of the child records associated with a row in a parent table, in this way avoiding the need to perform additional queries.

At this time, are you capable of spotting the differences between using lazy and eager loading? I hope so. But to clear up your doubts, in this group of articles I’m going to show you how to apply these powerful design patterns in some concrete situations using PHP 5. So start reading!

{mospagebreak title=Eager loading in PHP 5: an example class}

As I mentioned in the introduction, lazy and eager loading are complementary patterns that have their own pros and cons, logically depending on the context where they’re applied. However, in this first part of the series I’m going to focus my attention specifically on the latter technique, so you can quickly grasp its rationale and decide where and when to use it.

Having clarified that point, it’s time to demonstrate a basic usage of eager loading. I’m going to build a simple class. It will do nothing special except for storing data on some fictional users in the form of properties. Please, pay attention to the initial definition of this class, which is as follows:

// define ‘User’ class

class User {

 

private $fname = ‘Alejandro';

private $lname = ‘Gervasio';

private $email = ‘alejandro@mydomain.com';

 

public function __construct($fname = ”, $lname = ”, $email = ”)

{

if (is_string($fname) and !empty($fname))

{

$this->fname = $fname;

}

if (is_string($lname) and !empty($lname))

{

$this->lname = $lname;

}

if (is_string($email) and !empty($email))

{

$this->email = $email;

}

}

}  

Certainly, it’s very easy to understand the way that the brand new “User” class functions. As I explained previously, it actually does nothing but save basic data on a particular user to their declared properties. Period.

For this example, the assignment of new values to those properties is performed exclusively through the class’s constructor, but logically it’s possible to create some setter methods that do the same thing.

So far, so good, right? At this stage, the “User” class in its current state is admittedly pretty useless, for the reason given earlier. If the class is only capable of storing user-related data, then it would be desirable to code a few additional getter methods that permit it to retrieve the data from the outside world.

But, wait a minute! You might be wondering what this class has to do with implementing the eager loading pattern, after all. Well, bear with me for the moment and read the following section, where I’m going to add to the class the aforementioned getter methods. Then, once the development of the class has been completed, you’ll see how it fits into the schema imposed by the pattern.

Now, click on the link that appears below and keep reading.

{mospagebreak title=Completing the User class} 

In the previous segment, I started building a trivial class whose functionality was reduced to storing only data on some hypothetical users. The definition of this class is still incomplete, though, since it’s necessary to add to it a few getter methods that allow it to retrieve the values assigned to its properties.

Indeed, coding these additional methods within the class is as simple as this:

// get user’s first name

public function getFirstName()

{

return $this->fname;

}

 

// get user’s last name

public function getLastName()

{

return $this->lname;

}

 

// get user’s email

public function getEmail()

{

return $this->email;

}

 

// display user data

public function __toString()

{

return ‘First Name: ‘ . $this->fname . ‘<br />Last Name: ‘ . $this->lname . ‘<br />Email: ‘ . $this->email;

}

Done. Now the above “User” class provides a basic, yet consistent, API that permits it to retrieve easily the value of its “fname,” “lname” and “email” properties. In addition, I implemented the magic “__toString()” method included with PHP 5, which comes in handy for outputting those properties to the screen in one single go.

After adding the previous getter methods, the finished version of the “User” class looks like this:

class User {

 

private $fname = ‘Alejandro';

private $lname = ‘Gervasio';

private $email = ‘alejandro@mydomain.com';

 

public function __construct($fname = ”, $lname = ”, $email = ”)

{

if (is_string($fname) and !empty($fname))

{

$this->fname = $fname;

}

if (is_string($lname) and !empty($lname))

{

$this->lname = $lname;

}

if (is_string($email) and !empty($email))

{

$this->email = $email;

}

}

 

// get user’s first name

public function getFirstName()

{

return $this->fname;

}

 

// get user’s last name

public function getLastName()

{

return $this->lname;

}

 

// get user’s email

public function getEmail()

{

return $this->email;

}

 

// display user data

public function __toString()

{

return ‘First Name: ‘ . $this->fname . ‘<br />Last Name: ‘ . $this->lname . ‘<br />Email: ‘ . $this->email;

}

}

 

All right, I have to admit that until now nothing special has happened, since all I did was build a basic class that can be used for storing data on some users. However, the question that comes up here is: where does the eager loading pattern fit in the context of this example? I asked you before to be patient, and hopefully you’ll be properly rewarded.

Now that the “User” class is available for testing purposes, the next step that must be taken is developing a script that uses it for implementing eager loading.

Want to see how this script will be built? Then read the following segment. It’s only one click away.

{mospagebreak title=Applying the eager loading design pattern} 

Given that in the previous section I finished developing an example class that could store basic information on some users, it’s time to demonstrate how this class can be used within the schema imposed for the eager loading pattern.

So, take a close look at the following script. Despite its simplicity, it shows in a nutshell the logic that stands behind using eager loading:

 

<?php

require_once ‘user.php’

/* rest of script code

 goes here

*/

// create instance of ‘User’ class

$user = new User();

// display user data

echo $user;

?>

What’s the big deal with this script? Not too much, really. But in this particular case, there’s a couple of things that are worth noting. The first one is the use of the “require_once” PHP function at the beginning, which naturally includes the previous “User” class, provided that its definition has been saved to a file called “user.php.”

Then, the script performs other tasks; in the end it creates an instance of the class in question and displays the values of its properties on the screen. This simple sequence of steps shows very clearly the rationale behind eager loading; since the class is included “eagerly,” before the script really needs to spawns an object from it.

What’s more, if the rest of the script is modified, the whole class still would be included, regardless of whether or not it is used at a later time. This particular example recreates a situation where eager loading is implemented inefficiently, but as I mentioned in the introduction, there are cases where this pattern can be extremely useful, particularly when it’s necessary to “prefetch” database rows.

But for the moment, I’m only scratching the surface when it comes to exploring the facets of the eager loading pattern. It’s a huge topic that I plan to cover in upcoming tutorials of this series. In the meantime, feel free to edit all the code samples shown in this article, so you can acquire a more solid background in using this design pattern with PHP 5.

Final thoughts

In this introductory installment of the series, I provided you with a basic example of how to implement the eager loading design pattern in a few simple steps when working with PHP 5. In this case, the pattern was applied thanks to the eager inclusion of a basic class within a script, regardless of whether or not it was directly requested by the script, which in this particular case introduced an unnecessary overhead.

Does this mean that eager loading is a bad thing? Not at all; this depends strongly on the context where the pattern is applied. But if the example shown previously didn’t dissipate your doubts on the implementation of this pattern, in the next article I’m going to create for you another program that will use a stricter object-oriented approach for eager loading with the earlier “User” class.

Don’t miss the following part!

[gp-comments width="770" linklove="off" ]

antalya escort bayan antalya escort bayan Antalya escort diyarbakir escort