Three most effective ways to boost performance

When thinking about performance, there are three key things that you could do that work wonders on your performance. In this entry we are going to explore them.

Loops

A loop is a fundamental construct in all major computer languages and for a good reason too. You wouldn’t be able to do much without it. It’s uses are varied including:

  • Core part of Divide and Conquer algorithms
  • Unpacking results from database
  • Acting on multiple inputs
  • etc

Their prominent place in our world is not carte blanche to spate our code with it, regulation is key! The reason for that lies in how running time relates to loops.

Without going into details, it suffices to say that a simple loop takes n time to complete, a loop nested within it would take n^2 time by the time you get to another loop the time is now n^3. At this level of complexity it would be impossible to run the program in any kind of production system.

As such we need to find ways to either eliminate loops, make them run in a serial fashion or use recursive methods.

Here is an example, suppose we have an array of names.


$names = ['Rachel', 'Ben','Justin','Gloria'];

We would like to attach information about say gender and nickname to the data.

The most obvious way of doing it would be

foreach($names as $name){
        $name['gender']= determineGender($name);
}
foreach($names as $name){
        $name['nickname']= determineNickname($name);
}

This code is not too bad and in fact could potentially work if data set remains small, however we can make it much faster by simply combining the two operations as such

foreach($names as $name){
        $name['gender']= determineGender($name);
        $name['nickname']= determineNickname($name);
}

Minimize calls to external systems

Modern applications requires an entire host of supporting services to make them work. The most common include:

  • Databases
  • Search engines
  • File systems

What may seem blazingly fast may not work so well when your system needs to scale.

In the example below we think of a situation where we retrieve names and then display them alongside with people of a related gender.


$names = DB::findByName("Julia");
foreach($names as $name){
        $names['gender']=determineGender($name);
        $names['related']=Db::findByGender($namesWithGender['gender']);
}

In the above case we are calling the database each time the loop runs. For large loops this process would become more expensive.

Instead of that mess, we instead need to make all our database calls first and then bring in the extra information.


$names = DB::findByName("Julia");
$femaleNames = Db::findByGender('female');
$maleNames = Db::findByGender('male');
foreach($names as $name){
        $names['gender'] = determineGender($name);
        if($names['gender']=='male'){
                $names['related']=$maleNames;
        }
        else{
                $names['related']=$femaleNames;
        }
}

While a tad more complex, the above code greatly minimizes outside calls.

Cache cache cache

Never do the same work more than once! If it can be cached, let it be cached.

Even light tasks can be cached for incredible performance. When your App’s popularity skyrockets you will be thanking the code gods for the blessing of caches.

Some candidates for caching include:

  • Database results
  • Computation results
  • HTML rendered

Using an external service has to be balanced with the cost of calling the said service. Sound judgment and good engineering taste will help you determine the best cause of action.

Should you decide to cache, I highly recommend the popular service memcached.

Have you ever had performance issues on your own application? How did you deal with it? Tell us in the comment section below.

Facebooktwittergoogle_plusredditpinterestlinkedinmail

Isolating Change In Software Projects

Software more than any other human creation has had the largest impact in human society in a very short period of time.

It’s strength lies in its softness that is the ability to adapt, reuse and even re purpose existing software to build better and better products for cheap. But hidden in this strength is a weakness, change very quickly degrades systems to a mess no one can understand. As we have already discussed before in The heart of software engineering this kind of complexity is the death knell of the project.

Our best defense against this particular blow is to actively manage the areas which our software is likely to change. As such I have prepared a tickler list of such areas as I have experienced in my own practise.

Database

From File based to relational to object oriented to NoSQL, the world of persistence has changed a lot in the last 15 years. If your codebase was tightly coupled to any one of this paradigms, at best the product may not be taking advantage of advances in the field at worst it may have already been wiped out! Yet the effects are not always so grandiose, sometimes you may realize that another database in the same paradigm may serve you better, say Postgres over MySQL for GIS data.

For this reason it makes sense to decouple your code from your DB. This is usually the easiest to do because any good ORM would do the trick.

Hardware

Better hardware comes out every year, I am not talking about just Moore’s law but rather entirely new hardware or new specifications for existing hardware.

You should wrap all code that interacts with the hardware in a class or module then access that via a standard interface. That way you can easily switch out implementations as need be.

Business rules

Business that thrive have learned the value of evolving to adapt to the current trends in its industry. The product owner will expect the codebase to evolve to meet the changing business model.

The topic of adapting your code is covered well by Eric Evans in his book Domain Driven Design. This is a must read for anyone engaging in the business of software consulting.

However we can still take care of the basics including things like

  • Giving meaningful names to entities in your application
  • Encapsulating business rules in classes
  • Accessing constants such as tax rate from environment variables

Framework dependency

It’s considered heresy to write code without using a framework. Countless flame wars have been waged on the topic yet what the commandos in this war fail to see is that a framework is just a set of libraries meant to support your code. You should wrap any exotic functionality provided by the framework in packages or at very least define interfaces which then the framework would support. Otherwise when a better framework comes along the cost of the transition maybe prohibitive and your project will thus be married to its original framework.

Have you identified other areas in your code that seem to change frequently? Talk to us in the comment section below.

Facebooktwittergoogle_plusredditpinterestlinkedinmail

Yes you should version your database

There is one major process that your team is likely ignoring that holds a large stake in your application, can you guess what it is?

Did I hear someone say Database migration woop woop top of the class!

More often than not, we properly version code but deploy the database as one big sql dump. Practically all teams I have interacted with during deployment present a .sql file with instructions that Mysqldump or a similar tool should be put to employ.

The biggest disadvantage to this method is that the database and the application don’t remain in sync for the various versions available. At first glance this may not seem like that much of an issue since most of the time we are only concerned about the final version of the db. However when you think about it you realize that if the version of db you have is only the latest, then earlier versions of the code are practically unusable since they work with the implicit assumption of how the schema of the database is structured.

Application <-> Database mismatch maybe your biggest problem but other problems quickly become apparent when you deploy and need to scale your app. Since the entire db is just one big dump, you can not easily automate the task of scaling it over the cloud.

Well now that we have talked of the evils of the dump, what can we do?

The easiest option is to store diffs of the database. Here I don’t mean in the sense that git does but rather storing ALTER scripts in an orderly incremental manner in a folder called migrations. Sample contents would be:

  • 001_Users.sql
  • 002_Products.sql

And when say we alter the users table then:

  • 001_Users.sql
  • 002_Products.sql
  • 003_Altered_users.sql

etc

We then commit the files to our code repository of choice.

This ensures that at whatever point you checkout your code, you can also be able to generate the necessary schema.

Other considerations

For those who work with frameworks, your framework probably ships with a schema builder in one form or another. For those cases you may wish to version the schema files rather that the sql file.

For those of us who prefer the db to be framework agnostic, the following tools can be a great help to help you run your diffs

How do you manage database migrations within your own team? Tell us in the comment section below.

Facebooktwittergoogle_plusredditpinterestlinkedinmail