Skip to content

Instantly share code, notes, and snippets.

@Mattamorphic
Last active February 5, 2017 11:25
Show Gist options
  • Save Mattamorphic/c84c2e3a0e784f530a6e3cce86e37fce to your computer and use it in GitHub Desktop.
Save Mattamorphic/c84c2e3a0e784f530a6e3cce86e37fce to your computer and use it in GitHub Desktop.
Memory Usage / Time Testing PHP Hash Storing
<?php
/**
* This is tested in PHP 7.1
* As part of a system I'm looking to store a series of hashes, and look these up.
* There could be many hashes, and I don't need to use these, I just need to know if they exist.
*
* The following tests pit arrays against strings to see which is the fastest.
* I'll be searching for MTIzNDY5MTI1Njc4 which is the number 12345678 * 1000 base 64 encoded
**/
/**
* Profiler
*
* @author Matt Barber <[email protected]>
**/
class Profiler
{
// The current state of the data
private $data = null;
// The initial time (used to calculate overall)
private $time = 0;
// The initial memory (used to calculate overall)
private $memory = 0;
/**
* Upon instantiation, setup the initial memory and time, and register the
* tick method as the method to call on each line execution
*
* @return void
**/
public function __construct()
{
// store the start time
$this->data = new StdClass();
$this->time = microtime(true);
$this->memory = memory_get_usage() / 1024 / 1024;
// register the tick method on this class as the tick function (call it on each line execution)
register_tick_function([$this, 'tick']);
declare(ticks = 1);
}
/**
* On unsetting (garbage collection) unregister the method as the tick function
*
* @return void
**/
public function __destruct()
{
unregister_tick_function([$this, 'tick']);
}
/**
* On each 'tick' call this method and update the current memory and time state of
* the profiler
*
* @return void
**/
public function tick() : void
{
$this->data->memory = memory_get_usage() / 1024 / 1024 - $this->memory;
$this->data->time = microtime(true) - $this->time;
}
/**
* Return the state of the profiler at any given time
*
* @return object
**/
public function getData() : \stdClass
{
return $this->data;
}
}
/**
* Array Testing
******************************************************************************
**/
echo "Testing Array Hashing....\n==================================\n";
$profiler = new Profiler();
$array = [];
// Foreach number in 1 to 1000000, store the hash as a key, and the value as true
foreach (range(1, 1000000) as $number) {
$array[base64_encode(12345678 * $number)] = true;
}
// array_key_exists has a complexity of O(n) but really close to O(1) -
// this is because of linear polling in collisions, but because the chance of collisions is very small,
// the coefficient is also very small
echo 'Found MTIzNDY5MTI1Njc4 : ' . array_key_exists('MTIzNDY5MTI1Njc4', $array) . "\n";
$data = $profiler->getData();
echo "Memory Usage : {$data->memory} mb\n";
echo "Time taken: {$data->time} seconds\n\n\n";
// Reset values
unset($profiler);
/**
* String Testing
******************************************************************************
**/
echo "Testing String Hashing....\n==================================\n";
$profiler = new Profiler();
$str = '';
// Foreach number in 1 to 1000000 store the hash as a string concatenated with a string option
// we use a delimiter that will be highly unlikely to exist in our encoding
foreach (range(1, 1000000) as $number) {
$str .= '::::' . base64_encode((12345678 * $number));
}
// We use strstr to see if our string exists in our string, this will probably have a complexity of
// O(n)
echo 'Found MTIzNDY5MTI1Njc4 in ' . strpos($str, 'MTIzNDY5MTI1Njc4') . "\n";
$data = $profiler->getData();
echo "Memory Usage : {$data->memory} mb\n";
echo "Time taken: {$data->time} seconds\n\n\n";
// Reset values
unset($profiler);
/*
| => php memoryTests.php
Testing Array Hashing....
==================================
Found MTIzNDY5MTI1Njc4 : 1
Memory Usage : 88.788681030273 mb
Time taken: 0.84828591346741 seconds
Testing String Hashing....
==================================
Found MTIzNDY5MTI1Njc4 in 199680
Memory Usage : 22.582824707031 mb
Time taken: 2.640704870224 seconds
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment