The Troll's factory

Geekeries & pensées
-->

PHP: USE concatenation NOT multiple echo / parameters

Print vs. Echo

I just went accross an interesting article about which of « print » or « echo » we should use in PHP.

The author has benchmarked the two solutions (though the data are certainly a bit old) shows that, although there is not much difference between the two, echo seems to be more efficient.

Great, I believe you.

Echo multiple statements / arguments vs. Concatenation

But at the end of the article, the author also suggest to use multiple parameters given to one echo statement instead of concatenation because concatenation is slow… bla bla…

As I have always been using concatenation (did not even know echo could take multiple arguments) and I never had any performance issue, I decided to check that and make a benchmark: echo 100,000 times two concatenated strings and do the same thing with two parameters and two echos statements…

The benchmark was clear: concatenation IS FASTER than the two other solutions.

String caching? Making a more relevant benchmark

As it appeared a bit weird to me, having been doing Java / C# mostly recently (with their slow concatenation that recreated a new object blabla), I thought « maybe the PHP VM is caching the result of the concatenated string, thus the benchmark is not relevant ».

OK, let’s check with a counter-possible-caching benchmark then:

$t0 = microtime(true);

define("MAX", 2000000);
File_put_ConTents("echobench._log", "");
function _log($str)
{
	File_put_ConTents("echobench._log", file_get_contents("echobench._log") . $str);
}

// Generating a bunch of string to concatenate to avoid PHP VM-caching
$strs = array();
for ($i=0; $i < MAX+1; $i++) { 
	$m = mt_rand(0, 200);
	$strs[$i] = '';
	for ($j=0; $j < $m; $j++) { 
		$strs[$i] .= chr(mt_rand(0, 255));
	}
}

// Loop where string concatenation caching is possible :
$t1 = microtime(true);
for ($i=0; $i < MAX; $i++) { 
	echo "Hello" . "World! 
"; } $t2 = microtime(true); _log("Concatenation, cached: " . ($t2-$t1) . "s\n"); // Loop where is is not : $t1 = microtime(true); for ($i=0; $i < MAX; $i++) { echo $strs[$i] . $strs[$i + 1]; } $t2 = microtime(true); _log("Concatenation, not cached: " . ($t2-$t1) . "s\n"); // Other ways to display stuff, with and without caching possible each time: $t1 = microtime(true); for ($i=0; $i < MAX; $i++) { echo $strs[$i]; echo $strs[$i + 1]; } $t2 = microtime(true); _log("Two echos, not cached: " . ($t2-$t1) . "s\n"); $t1 = microtime(true); for ($i=0; $i < MAX; $i++) { echo "Hello" , "
"; echo "World" , "
"; } $t2 = microtime(true); _log("Two echos, cached: " . ($t2-$t1) . "s\n"); $t1 = microtime(true); for ($i=0; $i < MAX; $i++) { echo $strs[$i], $strs[$i + 1];; } $t2 = microtime(true); _log("Two parameters, not cached: " . ($t2-$t1) . "s\n"); $t1 = microtime(true); for ($i=0; $i < MAX; $i++) { echo "Hello" , "World!" , "
"; } $t2 = microtime(true); _log("Two parameters, cached: " . ($t2-$t1) . "s\n"); $t3 = microtime(true); _log("Total benchmark time: " . ($t3-$t0)."\n");

I generated random strings at the beginning of the script. And I concatenate them after, in the loop. Thus, there is not even once the same concatenation happening, thus, no possible caching or whatever.

The benchmarked has been run on a 1.6GHz Atom processor, with the following command:

sudo nice -n -19 php -q echobanchmark.php > /dev/null

So the process was the most prioritized one on the OS and then there is no reason for any interference between the loops (moreover, the system was idle during the test (and there are 3 other virtual processors for doing whatever work the OS would need to do).

And do you know the result?

Here it goes:

Concatenation, cached: 7.4381861686707s
Concatenation, not cached: 9.9010219573975s
Two echos, not cached: 10.4353120327s
Two echos, cached: 14.883654117584s
Two parameters, not cached: 10.179102897644s
Two parameters, cached: 11.904446840286s
Total benchmark time: 928.97792601585

Conclusion: Concatenation is fast, very fast. It is rougly 30% faster than using the two parameters for echo (26.9268987% exactly) and roughly 30% faster than two echo statements as well (28.720999% exactly) and

The other conclusion here is that PHP does not seem to be caching strings very well. Both the two-parameters and two-statements echo loops are much slower when using a fresh new string and much faster when using something from the previously generated array. The difference between cached / non-cached loop for the concatenation loop is also not that impressive if we observe that my « not cached » loop is using strings of random length that can go until 200 chars whereas the « cached » one is a very short string (so the difference of 2 seconds is certainly also due to the difference in length of the strings).

If you have any suggestion to improve the benchmark, feel free to post a comment.

posté par Troll dans PHP,Scripts, astuces, dév. web avec aucun commentaire

Benchmark Dédibox V3 chez Online.net

Bon, en pleine installation serveur, je prends quand même le temps de faire quelques Benchmarks, et je me dis que ça en intéressera sûrement certains d’avoir les résultats (surtout ceux qui hésitent à choisir l’offre :) ).

La dédibox V3 est fraichement installée, rien ne tourne dessus, aucun paquet supplémentaire si ce n’est le logiciel hardinfo et ses dépendances pour le benchmark.

Tout d’abord, hdparm (débits disque) :

*:~# free -m
total used free shared buffers cached
Mem: 1980 228 1751 0 87 85
-/+ buffers/cache: 55 1924
Swap: 2047 0 2047
*:~# hdparm -t /dev/sda

/dev/sda:
Timing buffered disk reads: 238 MB in 3.01 seconds = 79.01 MB/sec
*:~# hdparm -T /dev/sda

/dev/sda:
Timing cached reads: 1374 MB in 2.00 seconds = 686.92 MB/sec
*:~# hdparm -t /dev/sda

/dev/sda:
Timing buffered disk reads: 242 MB in 3.02 seconds = 80.21 MB/sec
*:~# hdparm -T /dev/sda

/dev/sda:
Timing cached reads: 1358 MB in 2.00 seconds = 679.22 MB/sec

Espace disque et utilisation RAM à vide :

(j’ai choisir une partition de 2G de swap au lieu de 1G proposé par défaut)

Sys. de fich. Tail. Occ. Disp. %Occ. Monté sur
/dev/sda2 145G 1,8G 136G 2% /
tmpfs 991M 0 991M 0% /lib/init/rw
proc 0 0 0 - /proc
sysfs 0 0 0 - /sys
procbususb 0 0 0 - /proc/bus/usb
udev 10M 480K 9,6M 5% /dev
tmpfs 991M 0 991M 0% /dev/shm
devpts 0 0 0 - /dev/pts
/dev/sda1 190M 26M 155M 14% /boot

Maintenant, le bench HardInfo :

hardinfo
Computer
Summary
Operating System
Kernel Modules
Boots
Languages
Filesystems
Shared Directories
Display
Network Interfaces
Users
Devices
Processor
Memory
PCI Devices
USB Devices
Printers
Battery
Sensors
Input Devices
Storage
Benchmarks
CPU ZLib

*** Warning: Cannot load ZLib: /usr/lib/libz.so: Ne peut ouvrir le fichier d'objet partagé: Aucun fichier ou répertoire de ce type

CPU Fibonacci
CPU MD5
CPU SHA1
CPU Blowfish
FPU Raytracing

Computer
********

Summary
-------

-Computer-
Processor : VIA Nano processor U2250 (1.6GHz Capable)
Memory : 2028MB (70MB used)
Operating System : Debian GNU/Linux 5.0.4
User Name : root (root)
Date/Time : lun 27 déc 2010 04:22:39 CET
-Display-
Resolution : 0x0 pixels
OpenGL Renderer : Unknown
X11 Vendor : (null)
-Multimedia-
Audio Adapter : (null)
-Input Devices-
Macintosh mouse button emulation
PC Speaker
Sleep Button
Power Button
Power Button
-Printers-
No printers found
-IDE Disks-

Operating System
----------------

-Version-
Kernel : Linux 2.6.32-bpo.5-amd64 (x86_64)
Compiled : #1 SMP Mon Dec 13 17:10:39 UTC 2010
C Library : GNU C Library version 2.7 (stable)
Distribution : Debian GNU/Linux 5.0.4
-Current Session-
Computer Name : nttserv
User Name : root (root)
Home Directory : /root
Desktop Environment : Terminal
-Misc-
Uptime : 24 minutes
Load Average : 0,00, 0,00, 0,00

Kernel Modules
--------------

-Loaded Modules-
evdev : Input driver event char devices
dcdbas : Dell Systems Management Base Driver (version 5.6.0-3.2)
i2c_viapro : vt82c596 SMBus driver
snd_pcm : Midlevel PCM code for ALSA.
psmouse : PS/2 mouse driver
snd_timer : ALSA timer interface
button : ACPI Button Driver
processor : ACPI Processor Driver
shpchp : Standard Hot Plug PCI Controller Driver
serio_raw : Raw serio driver
i2c_core : I2C-Bus main module
snd : Advanced Linux Sound Architecture driver for soundcards.
pci_hotplug : PCI Hot Plug PCI Core
soundcore : Core sound module
snd_page_alloc : Memory allocator for ALSA system.
pcspkr : PC Speaker beeper driver
ext3 : Second Extended Filesystem with journaling extensions
jbd
mbcache : Meta block cache (for extended attributes)
raid10
raid456
async_raid6_recov : asynchronous RAID-6 recovery api
async_pq : asynchronous raid6 syndrome generation/validation
raid6_pq
async_xor : asynchronous xor/xor-zero-sum api
xor
async_memcpy : asynchronous memcpy api
async_tx : Asynchronous Bulk Memory Transactions API
raid1
raid0
multipath
linear
md_mod
sd_mod : SCSI disk (sd) driver
crc_t10dif : T10 DIF CRC calculation
ata_generic : low-level driver for generic ATA
pata_via : low-level driver for VIA PATA
ehci_hcd : USB 2.0 &apos;Enhanced&apos; Host Controller (EHCI) Driver
uhci_hcd : USB Universal Host Controller Interface driver
libata : Library module for ATA devices
usbcore
nls_base
scsi_mod : SCSI core
e1000e : Intel(R) PRO/1000 Network Driver
thermal : ACPI Thermal Zone Driver
fan : ACPI Fan Driver
thermal_sys : Generic thermal management sysfs support

Boots
-----

-Boots-
Mon Dec 27 03:58 - 04:22 (00:24) : Kernel 2.6.32-bpo.5-amd
Mon Dec 27 03:53 - 03:56 (00:02) : Kernel 2.6.32-bpo.5-amd
Mon Dec 27 03:04 - 03:56 (00:52) : Kernel 2.6.32-bpo.5-amd

Languages
---------

-Available Languages-
français : French locale for France
french : French locale for France
fr_FR : French locale for France
[email protected] : French locale for France with Euro
fr_FR.iso88591 : French locale for France
fr_FR.iso885915 : French locale for France with Euro

Filesystems
-----------

-Mounted File Systems-
/dev/sda2 : 144,5 GiB total, 136,3 GiB free
tmpfs : 990,3 MiB total, 990,3 MiB free
proc : 0,0 B total, 0,0 B free
sysfs : 0,0 B total, 0,0 B free
procbususb : 0,0 B total, 0,0 B free
udev : 10,0 MiB total, 9,5 MiB free
tmpfs : 990,3 MiB total, 990,3 MiB free
devpts : 0,0 B total, 0,0 B free
/dev/sda1 : 189,9 MiB total, 155,0 MiB free

Shared Directories
------------------

-SAMBA-
Cannot open /etc/samba/smb.conf
-NFS-

Display
-------

-Display-
Resolution : 0x0 pixels
Vendor : (null)
Version : (null)
-Monitors-
-Extensions-

Network Interfaces
------------------

-Network Interfaces-
lo : Sent 0,13MiB, received 0,13MiB (127.0.0.1)
eth0 : Sent 3,72MiB, received 21,99MiB (88.191.132.66)
eth1 : Sent 0,00MiB, received 0,00MiB

Users
-----

-Human Users-
pcinfoweb
-System Users-
root : root
daemon : daemon
bin : bin
sys : sys
sync : sync
games : games
man : man
lp : lp
mail : mail
news : news
uucp : uucp
proxy : proxy
www-data : www-data
backup : backup
list : Mailing List Manager
irc : ircd
gnats : Gnats Bug-Reporting System (admin)
nobody : nobody
libuuid
Debian-exim
statd
bind
ntpd
sshd

Devices
*******

Processor
---------

-Processor-
Name : VIA Nano processor U2250 (1.6GHz Capable)
Family, model, stepping : 6, 15, 3 (Centaur i386 class)
Vendor : CentaurHauls
-Configuration-
Cache Size : 1024kb
Frequency : 1595,00MHz
BogoMIPS : 3191,00
Byte Order : Little Endian
-Features-
FDIV Bug : yes
HLT Bug : yes
F00F Bug : yes
Coma Bug : yes
Has FPU : yes
-Capabilities-
fpu : Floating Point Unit
vme : Virtual 86 Mode Extension
de : Debug Extensions - I/O breakpoints
pse : Page Size Extensions (4MB pages)
tsc : Time Stamp Counter and RDTSC instruction
msr : Model Specific Registers
pae : Physical Address Extensions
mce : Machine Check Architeture
cx8 : CMPXCHG8 instruction
apic : Advanced Programmable Interrupt Controller
sep : Fast System Call (SYSENTER/SYSEXIT)
mtrr : Memory Type Range Registers
pge : Page Global Enable
mca : Machine Check Architecture
cmov : Conditional Move instruction
pat : Page Attribute Table
clflush : Cache Line Flush instruction
acpi : Thermal Monitor and Software Controlled Clock
mmx : MMX technology
fxsr : FXSAVE and FXRSTOR instructions
sse : SSE instructions
sse2 : SSE2 (WNI) instructions
ss : Self Snoop
tm : Thermal Monitor
pbe : Pending Break Enable
syscall : SYSCALL and SYSEXIT instructions
nx : No-execute Page Protection
lm
constant_tsc
up
rep_good
pni
monitor
vmx
est
tm2
ssse3
cx16
xtpr
rng
rng_en
ace
ace_en
ace2
phe
phe_en
lahf_lm

Memory
------

-Memory-
Total Memory : 2028088 kB
Free Memory : 1786444 kB
Buffers : 10888 kB
Cached : 171048 kB
Cached Swap : 0 kB
Active : 139536 kB
Inactive : 67096 kB
Active(anon) : 24704 kB
Inactive(anon) : 484 kB
Active(file) : 114832 kB
Inactive(file) : 66612 kB
Unevictable : 0 kB
Mlocked : 0 kB
Virtual Memory : 2096472 kB
Free Virtual Memory : 2096472 kB
Dirty : 8 kB
Writeback : 0 kB
AnonPages : 24704 kB
Mapped : 9004 kB
Shmem : 492 kB
Slab : 19132 kB
SReclaimable : 13572 kB
SUnreclaim : 5560 kB
KernelStack : 560 kB
PageTables : 2108 kB
NFS_Unstable : 0 kB
Bounce : 0 kB
WritebackTmp : 0 kB
CommitLimit : 3110516 kB
Committed_AS : 87912 kB
VmallocTotal : 34359738367 kB
VmallocUsed : 274392 kB
VmallocChunk : 34359458584 kB
HardwareCorrupted : 0 kB
HugePages_Total : 0
HugePages_Free : 0
HugePages_Rsvd : 0
HugePages_Surp : 0
Hugepagesize : 2048 kB
DirectMap4k : 7488 kB
DirectMap2M : 2056192 kB

PCI Devices
-----------

-PCI Devices-
Host bridge : VIA Technologies, Inc. VX800 Host Bridge
Host bridge : VIA Technologies, Inc. VX800/VX820 Error Reporting
Host bridge : VIA Technologies, Inc. VX800/VX820 Host Bus Control
Host bridge : VIA Technologies, Inc. VX800 PCI to PCI Bridge
Host bridge : VIA Technologies, Inc. VX800/VX820 Power Management Control
PIC : VIA Technologies, Inc. VX800/VX820 APIC and Central Traffic Control
Host bridge : VIA Technologies, Inc. VX800/VX820 Scratch Registers
Host bridge : VIA Technologies, Inc. VX800/VX820 North-South Module Interface Control
VGA compatible controller : VIA Technologies, Inc. Device 1122
PCI bridge : VIA Technologies, Inc. VX800/VX820 PCI Express Root Port
PCI bridge : VIA Technologies, Inc. VX800/VX820 PCI Express Root Port
PCI bridge : VIA Technologies, Inc. VX800/VX820 PCI Express Root Port
IDE interface : VIA Technologies, Inc. VX800 Serial ATA and EIDE Controller
USB Controller : VIA Technologies, Inc. VT82xxxxx UHCI USB 1.1 Controller
USB Controller : VIA Technologies, Inc. VT82xxxxx UHCI USB 1.1 Controller
USB Controller : VIA Technologies, Inc. USB 2.0
ISA bridge : VIA Technologies, Inc. VX800/VX820 Bus Control and Power Management
Host bridge : VIA Technologies, Inc. VX800/VX820 South-North Module Interface Control
PCI bridge : VIA Technologies, Inc. Device b353
Ethernet controller : Intel Corporation 82574L Gigabit Network Connection
Ethernet controller : Intel Corporation 82574L Gigabit Network Connection

USB Devices
-----------

Printers
--------

-Printers-
No printers found

Battery
-------

-No batteries-
No batteries found on this system

Sensors
-------

Input Devices
-------------

-Input Devices-
Macintosh mouse button emulation
PC Speaker
Sleep Button
Power Button
Power Button

Storage
-------

-IDE Disks-

Benchmarks
**********

CPU ZLib
--------

-CPU ZLib-
This Machine : 0,000
PowerPC 740/750 (280.00MHz) : 2150.597408
Intel(R) Celeron(R) M processor 1.50GHz : 8761.604561

CPU Fibonacci
-------------

-CPU Fibonacci-
This Machine : 5,583
Intel(R) Celeron(R) M processor 1.50GHz : 8.1375674
PowerPC 740/750 (280.00MHz) : 58.07682

CPU MD5
-------

-CPU MD5-
This Machine : 39,310
PowerPC 740/750 (280.00MHz) : 7.115258
Intel(R) Celeron(R) M processor 1.50GHz : 38.6607998

CPU SHA1
--------

-CPU SHA1-
This Machine : 35,914
PowerPC 740/750 (280.00MHz) : 6.761451
Intel(R) Celeron(R) M processor 1.50GHz : 49.6752776

CPU Blowfish
------------

-CPU Blowfish-
This Machine : 21,352
Intel(R) Celeron(R) M processor 1.50GHz : 26.1876862
PowerPC 740/750 (280.00MHz) : 172.816713

FPU Raytracing
--------------

-FPU Raytracing-
This Machine : 19,973
Intel(R) Celeron(R) M processor 1.50GHz : 40.8816714
PowerPC 740/750 (280.00MHz) : 161.312647

Voilà, bonne soirée :)

posté par Troll dans Administration serveur,Geekeries avec aucun commentaire