+ Reply to Thread
Results 1 to 9 of 9

Thread: Ticks - The PHP Construct You've Never Used

  1. #1
    Mau
    Mau is offline Banned Mau is on a distinguished road
    Join Date
    Jun 2005
    Location
    California, USA
    Age
    23
    Posts
    2,821
    Rep Power
    0

    Ticks - The PHP Construct You've Never Used

    Click here to tell your friends about ticks!

    You've probably never used it, never saw it, or never found a practical use for ticks, a underused and powerful feature of PHP that allows you to implement exceptions in PHP4, do intensive debugging and profiling, check database connections, turn PHP into an event driven language, or harness complex control over your code.

    Concept of Ticks
    From the PHP manual: "A tick is an event that occurs for every N low-level statements executed by the parser within the declare block." So, for example, if N=1, then after every statement, the tick event will be executed. Here's an example:
    PHP Code:
    // N = 1
    $pass md5('qwerty'); /* Tick executed */
    $pass strrev($pass);  /* Tick executed */
    echo $pass;  /* Tick executed */ 
    PHP Code:
    // N = 2
    $pass md5('qwerty'); 
    $pass strrev($pass); /* Tick executed */
    echo $pass
    PHP Code:
    // N = 3
    $pass md5('qwerty');
    $pass strrev($pass);
    echo 
    $pass;  /* Tick executed */ 
    The above code is showing 3 examples. In the first one, N = 1, which means that our tick will be executed after every statement. As we increase N, our tick is executed less and less.

    Enabling Ticks
    So, how do you use ticks? The above code does not have ticks enabled. To enable them, you use the exclusive declare construct. Declare is a construct for the parser to inject code after the specified "ticks" constant. The syntax for declare is:
    PHP Code:
    declare (ticks=1)
    {
         
    // Code Here

    So, to make our above example complete:
    PHP Code:
    declare (ticks=1)
    {
         
    $pass md5('qwerty'); /* Tick executed */
         
    $pass strrev($pass);  /* Tick executed */
         
    echo $pass;  /* Tick executed */
    }

    declare (
    ticks=2)
    {
         
    $pass md5('qwerty'); 
         
    $pass strrev($pass); /* Tick executed */
         
    echo $pass
    }

    declare (
    ticks 3)
    {
         
    $pass md5('qwerty');
         
    $pass strrev($pass);
         echo 
    $pass;  /* Tick executed */

    We've now enabled ticks for our code. But, it's still useless. As it is right now, nothing is executed in the tick event. Let's define something.

    Implementing a Tick
    We can define a single function or method to be called using the register_tick_function() function. This specifies the event.

    So, all together now:
    PHP Code:
    declare (ticks=1)
    {
         
    // Code Here

    So, to make our above example complete:
    PHP Code:
    function profile_memory()
    {
         echo 
    '<!--' memory_get_usage() . '-->';
    }

    register_tick_function('profile_memory');
    declare (
    ticks=1)
    {
         
    $pass md5('qwerty'); /* Tick executed */
         
    $pass strrev($pass);  /* Tick executed */
         
    echo $pass;  /* Tick executed */
    }

    register_tick_function('profile_memory');
    declare (
    ticks=2)
    {
         
    $pass md5('qwerty'); 
         
    $pass strrev($pass); /* Tick executed */
         
    echo $pass
    }

    register_tick_function('profile_memory');
    declare (
    ticks 3)
    {
         
    $pass md5('qwerty');
         
    $pass strrev($pass);
         echo 
    $pass;  /* Tick executed */

    The above code shows us how we can monitor memory usage and easily locate the memory intensive parts. We can watch where it creeps up and find ways to cut back on our memory usage. Pretty cool, eh? It sure beats manually putting in profile_memory() every so lines. We can easily disable this by removing our call to register_tick_function.

    This totally useless!
    Not so. I have found quite a few uses for this:
    • Writing something that checks to see if the database connection has been dropped. If so, throw an exception or handle it somehow.
    • Implement exceptions in PHP4. To do this, you would have a throw() function and a tick function that would check the value of the throw function.
    • Monitor memory usage and script executation time. You can easily find the slow parts using ticks.
    • Do complex buffering on your code.
    • Turn PHP into an event driven programming language. No more exception hacks.

    Ticks let you dynamically segment your code. Instead of debugging a PHP file, you can now debug PHP line numbers. You can also use ticks outside of debugging, such as turning PHP into an event driven language. Your tick function could check the value of a variable and call a function once the value has changed.

    Put it in the Global Scope
    You can have ticks work globally by putting this at the top of your script:
    PHP Code:
    declare(ticks=1); 
    Do they work in loops?
    Yes, they work in loops and will be executed in the iteration of the loops. If ticks=1 and the register_tick_function is profile(), your parser is really writing something like this:
    PHP Code:
    for ($x 0$x 990$x++)
    {
        echo 
    'Test'profile();
        echo 
    'Testing'profile();

    At first glance, profile() is only being called twice. In reality, it's being called 2*999 times. This is where the true power of ticks come in.

    Apache and Windows - Bad Match
    Avoid using this on Apache with Windows -- there have been reports of system crashes.
    Last edited by Mau; 09-20-2006 at 10:33 PM.

  2. #2
    Nick Presta is offline Forum Administrator Nick Presta is on a distinguished road
    Join Date
    Mar 2006
    Location
    Toronto, Ontario
    Posts
    2,270
    Rep Power
    10

    Re: Ticks - The PHP Construct You've Never Used

    Wow. That is actually pretty neat.

    You could totally use this as a trace type thing where your tick logs your memory useage along with the function name so you can see when your script spikes and why.

  3. #3
    callumjones's Avatar
    callumjones is offline Powered by an API. callumjones has a spectacular aura about callumjones has a spectacular aura about
    Join Date
    Mar 2005
    Location
    Perth, Australia
    Age
    22
    Posts
    3,335
    Rep Power
    13

    Re: Ticks - The PHP Construct You've Never Used

    Wow, that is quite handy. What sort of gap is the tick run depending on the N value, say if N=4 is it run every 1/4 of lines?

  4. #4
    sirjavabean is offline Err... Bean, Mister Bean sirjavabean is on a distinguished road
    Join Date
    Jul 2005
    Location
    Derbyshire, UK
    Age
    21
    Posts
    2,144
    Rep Power
    10

    Re: Ticks - The PHP Construct You've Never Used

    Nice! :)

    Why does
    PHP Code:
    <?php

    function foo()
    {
        echo(
    'foo()<br />');
    }

    register_tick_function('foo');

    declare(
    ticks 1)
    {
        echo(
    'Hello<br />');
    }

    ?>
    keep adding more foo()s every time you refresh the page?

  5. #5
    Mau
    Mau is offline Banned Mau is on a distinguished road
    Join Date
    Jun 2005
    Location
    California, USA
    Age
    23
    Posts
    2,821
    Rep Power
    0

    Re: Ticks - The PHP Construct You've Never Used

    Quote callumjones originally posted: View Post
    Wow, that is quite handy. What sort of gap is the tick run depending on the N value, say if N=4 is it run every 1/4 of lines?
    The gap is going to be whatever you specify. So, if N = 4, your tick function will execute every 4 lines.

    Quote sirjavabean originally posted: View Post
    Nice! :)

    Why does
    PHP Code:
    <?php

    function foo()
    {
        echo(
    'foo()<br />');
    }

    register_tick_function('foo');

    declare(
    ticks 1)
    {
        echo(
    'Hello<br />');
    }

    ?>
    keep adding more foo()s every time you refresh the page?
    This should only produce 1 tick and echo foo() once. Is it remembering the state between page loads?

  6. #6
    chrisxkelley's Avatar
    chrisxkelley is offline A Toddler - Don't be Fooled! chrisxkelley is on a distinguished road
    Join Date
    Jan 2005
    Location
    Arroyo Grande, California
    Age
    23
    Posts
    34
    Rep Power
    0

    Re: Ticks - The PHP Construct You've Never Used

    interesting. any idea why the following runs the function foo() three times:
    PHP Code:
    #! /usr/bin/php

    <?php
    function foo()
    {
     echo(
    'foo()<br />');
    }
    register_tick_function('foo');
    declare(
    ticks 1){}

    # prints foo()<br />foo()<br />foo()<br />
    ?>
    and also why N=2 or N=3 after that only runs foo() once, yet above N=2 or N=3, foo isnt run at all

    PHP Code:
    #! /usr/bin/php

    <?php
    function foo()
    {
     echo(
    'foo()<br />');
    }
    register_tick_function('foo');
    declare(
    ticks 3){} #try N=2-5

    # prints foo()<br />
    ?>

    i'll have to play around with this a bit. interesting find. where did you learn about this?

  7. #7
    Mau
    Mau is offline Banned Mau is on a distinguished road
    Join Date
    Jun 2005
    Location
    California, USA
    Age
    23
    Posts
    2,821
    Rep Power
    0

    Re: Ticks - The PHP Construct You've Never Used

    Remember that when you use ticks, they are after each low-level statements, whether they are stated or not. So, my bet is that the parser is adding something to the opcode which counts as a low-level statement.

  8. #8
    chugadie is offline New Born chugadie is on a distinguished road
    Join Date
    Sep 2006
    Posts
    1
    Rep Power
    0

    Re: Ticks - The PHP Construct You've Never Used

    Hmm.. I don't think you can do true exception handling with this technique, but you can come close. I say you can't do true exceptions because you can't interrupt the flow of the declare {} block. (or can you? (break/continue))

    PHP Code:



    # ERROR HANDLING
    $estack ErrorStack::_singleton();
    set_error_handler( array( &$estack'_errorHandler') );

    register_tick_function(array (&$estack,'watchErrorTicks') );

    declare(
    ticks=1) {    //try ...
       
    ErrorStack::registerCatch'myCatch' );

       echo 
    "hello world\n";
    }


    declare(
    ticks=1) {    //try ...
       
    ErrorStack::registerCatch'myCatch' );

       
    trigger_error("I don't feel like running.");
       
    trigger_error("But, I still have to run...");
    }



    function 
    myCatch($e) {
            echo 
    "*** DANGER, caught error: ".$e->toString()."\n";


    Registering a catch function first allows you to guide errors to a certain function *before* they happen, but the following statements in the declare block still run. You can only continue down the stack with function calls, or die and jump all the way back up to the top. You can't stop can get off at any level of the stack on your way up. You could encapsulate each call in a declare, but that isn't much different than just checking each return value after each call. If you have to work with other libraries that just call trigger_error(), this is a good way to capture and work with those.

  9. #9
    Mau
    Mau is offline Banned Mau is on a distinguished road
    Join Date
    Jun 2005
    Location
    California, USA
    Age
    23
    Posts
    2,821
    Rep Power
    0

    Re: Ticks - The PHP Construct You've Never Used

    That's true -- you cannot get some of the more powerful features of exceptions in PHP4, but you can simulate putting the entire script in a try...catch block. Then, when an exception is "thrown," act upon it, and exit the script if required.

+ Reply to Thread

Thread Information

Users Browsing this Thread

There are currently 1 users browsing this thread. (0 members and 1 guests)

     

Similar Threads

  1. What is PHP?
    By wizard in forum PHP Articles
    Replies: 7
    Last Post: 4 Weeks Ago, 02:24 AM
  2. PHP Tutorial for beginners
    By YoungCoder in forum PHP Articles
    Replies: 19
    Last Post: 04-23-2006, 02:31 PM
  3. Php Syntax
    By wizard in forum PHP Articles
    Replies: 1
    Last Post: 10-06-2005, 01:53 AM
  4. PHP Manual [Chris's Version]
    By Chrishasfun in forum PHP Articles
    Replies: 0
    Last Post: 01-02-2005, 02:22 PM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts