Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Commenting interpreted code and performance

I always (well try) to comment my code. I have configured my server to remove those comments/extra white space before delivery. Would it be better not to have comments in the live systems code (Javascript/php) and therefore reduce this overhead or remove or interpretation?

If so how can I have my cake and eat it too?

like image 878
Ed Heal Avatar asked Oct 11 '11 18:10

Ed Heal


2 Answers

For PHP, it makes no difference. Your PHP code isn't sent out to the browser.

For JavaScript, it is recommended that you minify your code. This reduces its size by changing variable names, removing white space, and removing all comments as well. There are several online tools for doing this, and it is often available in your IDE.

Whatever you do, leave your code commented where you work on it. Don't remove comments from PHP, and don't minify your JS by hand.

like image 192
Brad Avatar answered Sep 29 '22 08:09

Brad


Although the general assumption is that having PHP chewing through comments causes no measurable difference, better to check it, ain't it?

(Note: by common sense, we'd expect that the sheer request processing, permission management, process control, dispatching this, delegating that, firing up the PHP runtime environment, managing various caches, fiddling with asset files, overall disk and network I/O etc. etc., oh, and BTW, also executing the code, all very likely add up to far more than any generous amount of comments.)

So I gave it a very unsophisticated go, just to get an instant feel of it.

1. Setup

Predicting the "comment impact" to be as difficult to detect as neutrinos, I was deliberately after a slightly pathological setup, trying to make the difference measurable, but still not be overly unrealistic.

I created two files. One with no comments, just ~100 bytes, straight to the point, no-comments.php:

<?php
function task() {
    ++$GLOBALS;
    echo "[$GLOBALS] Lorem ipsum dolor sit amet cosectetur...\n";
}

And another, ~60K (staying under 64K just for heap-management-related superstition), comments.php:

<?php
/* ... some 30K comments ... */
// OK, that's something, but how about:
/* ... same 30K comments again ... (Phantomjs changelog, for the curious of you. :) ) */
// Finally, do something:
function task() {
    ++$GLOBALS; // Comments are cheap, so let me tell you how much I enjoyed this instead of properly declaring a counter. :)
    echo "[$GLOBALS] Lorem ipsum with a lot of comments...\n";
}

Note: this would of course very likely test file size impact actually, not purely the comments, but that's always an inherent part of the "comments (non)issue" anyway, and also I wanted just something first. Perhaps even that's already unmeasurable, right?

The general idea was then to loop task() in various ways, just a bit (or none at all) from inside the same PHP process, and a lot from outside of it, via separate executions, to force reparsing, which is the only interesting part of this experiment.

For quickest results I did some shell runs:

#!/bin/bash
for (( i = 0; i < 1000; i++ ))
do
   php comments.php  # <-- and another batch with "no-comments.php"
done

But that turned out to be unreliable, as increasing the loop count caused inexplicable and disproportional changes in execution times. I switched to a PHP runner instead, which ran more smoothly:

#!/usr/bin/php
<?php
$t1 = microtime(true);
for ($i = 0; $i < 1000; ++$i ) {
        system("php comments.php"); // <-- and with "no-comments.php"
}
$t2 = microtime(true);
echo "Time: ", $t2 - $t1

For HTTP runs I then added this index.php:

<?php
$GLOBALS = 0; // innovative use of a dull language feature ;)

$t1 = microtime(true);

require_once (isset($_GET['no']) ? 'no-' : '') . 'comments.php';

// Played a bit with looping here, but ended up leaving it out.
// for ($i = 0; $i < 3; ++$i) {
//      task();
//      echo '<br>';
// }

$t2 = microtime(true);
echo "<hr>Time: ",  number_format($t2 - $t1, 10);

Note: at first, unfortunately, I left PHP's Zend Opcache enabled, and wasted a lot of time trying to make sense of the results... ;-o Then i disabled the cache, of course, and repeated the web tests (only).

The host is just vanilla Debian, Apache2 with some PHP5 (I guess it's FPM -- didn't even bother checking, as that's supposed to be orthogonal to the subject of the testing (please correct me if this is not true). It may actually even help exposing the difference by reducing the irrelevant PHP startup overhead masking the tiny comment parsing time.)

2. Results - shell:

Running PHP-cli was surprisingly slow, so I got quickly bored, after only a dozen loops of 1000 iterations for both variants. (Results in seconds.)

COMMENTS:

44.2015209198
39.710990905762
42.374881982803
36.29861998558
44.764121055603
38.85772395134
42.627450942993
38.342661142349
48.539611816406
39.784120082855
50.34646987915
47.782819032669
36.974604845047
45.692447900772

AVERAGE: 42.592717

NO COMMENTS:

45.617978811264
43.397685050964
46.341667175293
44.246716976166
40.348230838776
43.048954963684
38.57627081871
50.429704189301
41.811543226242
35.755078077316
53.086957931519
31.751699924469
48.388355970383
49.540207862854

AVERAGE: 43.738647

As you can see, it's all rubbish... But if we ignore the environmental fluctuations, the conclusion is use more comments, it'll make your script faster! :)

3. Results - HTTP, Zend Opcache enabled:

(Some noise was cut from the ab outputs.)

COMMENTS:

ab -qd -n 10000 'http://.../comments/?yes'

Server Software:        Apache/2.4.10
Concurrency Level:      1
Time taken for tests:   3.158 seconds
Complete requests:      10000
Failed requests:        0
Non-2xx responses:      10000
Total transferred:      7120000 bytes
HTML transferred:       4620000 bytes
Requests per second:    3166.12 [#/sec] (mean)
Time per request:       0.316 [ms] (mean)
Transfer rate:          2201.45 [Kbytes/sec] received

NO COMMENTS:

ab -qd -n 10000 'http://.../comments/?no'

Server Software:        Apache/2.4.10
Concurrency Level:      1
Time taken for tests:   3.367 seconds
Complete requests:      10000
Failed requests:        0
Non-2xx responses:      10000
Total transferred:      7120000 bytes
HTML transferred:       4620000 bytes
Requests per second:    2969.95 [#/sec] (mean)
Time per request:       0.337 [ms] (mean)
Transfer rate:          2065.04 [Kbytes/sec] received

Wow! :-o Just like the shell runs! :) OK, not believing my eyes, I repeated it a few more times, until it made sense... :) See? Here:

Benchmarking ...<"NO COMMENTS">... (be patient).....done

Time taken for tests:   2.912 seconds
Total transferred:      7120000 bytes
HTML transferred:       4620000 bytes
Requests per second:    3433.87 [#/sec] (mean)
Time per request:       0.291 [ms] (mean)
Transfer rate:          2387.61 [Kbytes/sec] received

(BTW, don't ask me, why the non-2xx responses. They were 200 OK via the web.)

Then, with ten times more iterations:

COMMENTS:

Time taken for tests:   32.499 seconds
Requests per second:    3077.04 [#/sec] (mean)
Time per request:       0.325 [ms] (mean)
Transfer rate:          2139.51 [Kbytes/sec] received

NO COMMENTS:

Time taken for tests:   28.257 seconds
Requests per second:    3538.92 [#/sec] (mean)
Time per request:       0.283 [ms] (mean)
Transfer rate:          2460.66 [Kbytes/sec] received

Phew, perfect! Comments are evil! ;)

Well, I still did a couple more, and I can only show you this no-comment result strictly off the record:

Time taken for tests:   37.399 seconds
Requests per second:    2673.84 [#/sec] (mean)
Time per request:       0.374 [ms] (mean)
Transfer rate:          1859.15 [Kbytes/sec] received

4. Results - HTTP, Zend Opcache DISABLED:

OK, after realizing that I left the cache on, I commented out the extension from the PHP-FPM config (so, indeed, that's what runs here), restarted the services, checked phpinfo(), and gathered the new results:

COMMENTS:

Time taken for tests:   34.756 seconds
Requests per second:    2877.23 [#/sec] (mean)
Time per request:       0.348 [ms] (mean)
Transfer rate:          2000.58 [Kbytes/sec] received

Once again:

Time taken for tests:   31.170 seconds
Requests per second:    3208.24 [#/sec] (mean)
Time per request:       0.312 [ms] (mean)
Transfer rate:          2230.73 [Kbytes/sec] received

NO COMMENTS:

Time taken for tests:   30.060 seconds
Requests per second:    3326.70 [#/sec] (mean)
Time per request:       0.301 [ms] (mean)
Transfer rate:          2313.10 [Kbytes/sec] received

Once again:

Time taken for tests:   32.990 seconds
Requests per second:    3031.23 [#/sec] (mean)
Time per request:       0.330 [ms] (mean)
Transfer rate:          2107.65 [Kbytes/sec] received

Well. As you can see, basically: no freaking difference from the opcache on/off state! Nor between comments on/off (apart from a tiny hint, but having seen the fluctuations...)! :-o

5. Conclusion

So... Finally, numbers! Well, useless garbage, as a matter of fact, but at least not just religions speculations. It feels a lot better being confused for the sound reason of confusing data than the lack of it! :)

Now, after I've certainly wasted more than enough time on this, the answer to the ages-old question of "how much comments cost", remains a mystery.

As neutrinos have (incredibly) been detected for years, we may justly start feeling embarrassed. Will someone eventually bring on the breakthrough and finally detect the PHP comment impact, too? Nobody knows...

like image 32
Sz. Avatar answered Sep 29 '22 10:09

Sz.