As databases and visitors grow, sometimes ‘old code’ doesn’t work like it use to: it takes too long or times out for exceeding the maximum time allowed by your server for PHP execution. On a MySQL table with 30,000 rows (not too many), the query was checking one column for <3 and then matching a long list (10,000) of values in a second column using a long WHERE column2=’value’ clause. Here is an example of the table:
|--column1--|--column2--| | 0 | 1234 | | 3 | 5678 | -------------------------
A MySQL query took a while, but didn’t time out when the list of WHERE column2=’value’ was less than 7000, but it was just overwhelmed at 10,000. Okay, fine, time to go to phase two: in_array().
There was an existing array of values for column2, so I could simply pull a list of <3 from MySQL (quick) and then loop through (foreach) each of the results and check whether they are in_array() for the original source. If they were, just save them to a brand new array that I’ll use to work further through the problem. For clarification, that means that the system should go through 10,000+ iterations and check if each value is in_array(). If you had not already guessed, this was disastrous. In_Array() is very inefficient, and if you are dealing with an array that is more than 100 or so values, you’ll quickly learn this fact. So what to do? Use isset().
Isset(), as a function, is incredibly fast. It only checks whether something exists, and is a great way to check for whether something exists in an array. However, the trick is using isset() will look at the KEYS, while in_array() will look at the VALUES. Is that problem? Not if you build the original array as [value]=>value (set the KEY and VALUE the same). Now, as long as your values are valid keys and unique, this won’t be a problem. Then, you can use a foreach loop to check whether it is found in the original array. Here is some sample code:
$array_source = array('abc'=>'abc','def'=>'def','ghi'=>'ghi'); $array_results = array('xyz','ghi'); foreach ($array_results as $v){ if (isset($array_source[$v])){ //fast $result[] = $v; //if found, save it to a fresh array } } |
What was the final result? The query, run 6 different times for 6 different data sets, went from a total execution time exceeding 2 minutes (MySQL), to not working at all (in_array), to 0.18 seconds. Yes, less than one second! That is the power for checking whether a value is set when comparing arrays. Isset() is even faster by a notable amount when compared to array_diff().