I would like to create a forward-function that terminates the caller-function.
Currently I'm using "exit" in the callee-function to achieve this.
function caller (){
if($condition){
forward();
}
//code that is not executet if $condition is true
}
//current solution
function forward(){
//do something
exit;
}
I would like to omit the return-statement after calling the forward-function.
I guess there is no other way except throwing an exception?
Thanks for your help.
There are several ways:
1) Enclosing the code after if info else branch
2) As you mentioned, throwing an exception
3) or plainly doing:
function caller (){
if($condition){
forward();
return; // you return nothing (void, in PHP's case that would be NULL, I believe)
}
//code that is not executet if $condition is true
}
Throwing exceptions, using exit or some other nasty stuff is overkill no matter how you look at it (if all you want to do is conditional execution of some lines of code).
Solution 1
Use an else statement. This function will implicitly return NULL (in PHP, by default, ommiting the return statement when exiting a function, will return NULL to the caller).
function caller (){
if($condition){
forward();
}
else
{
//code that is not executet if $condition is true
}
}
Solution 2
The return statement will exit the current function.
function caller (){
if($condition){
forward();
return; //this function exits, and no other lines inside this function are executed
}
//code that is not executet if $condition is true
}
Don't use exit to terminate scripts, without passing and exit code. Exit is just like die, except instead of outputting to php://stdout (same thing as what echo does) it will return an exit code to the OS (exit is usefull only in CLI (command line) mode).
You can't terminate a "caller" function before the "called" function terminate itself.
There is a stack of calls that is allocated and return pointer issues.
I suppose that the best way to terminate a function itself is .... just terminate itself.
So
function caller (){
if($condition){
return 0;
}
//code that is not executet if $condition is true
}
I've only seen this answer in the comments, but not in any of the other answers.
To wrap up, let's consider two approaches and why they're not suitable for a forward functionality:
Use exceptions; exceptions should not be used for flow control, they're meant to handle exceptional events (when an operation has failed).
Use goto; this statement can only be used to jump within the same block of execution, which in this case would be inside the caller and the only jump target is at the end of the function.
Use exit(); this will terminate the script altogether and doesn't give any of the underlying code a chance to do anything else. It's typically used for fatal errors of some sort, or in rare cases whereby you set a few HTTP headers and then prevent any more output from being sent to the browser.
Technically speaking, a forward call should basically be used to express "say whatever he says"; and there's a perfect solution for that:
return forward();
It delivers the result of the forward() directly to the code that called the caller() while still respecting the stack execution order of your application.
Possibly, "goto" is the only solution:
function post_to_host($url, $data, $cook, $ref, &$resp_head, $type=1)
{$GLOBALS['POST_TO_HOST.TIME_START']=time();
...
stream_set_timeout($fp, 20);
fputs($fp, "Accept: */*\r\n"); if (check_timeout()) {goto timeout;}
fputs($fp, "Accept-Language: *\r\n"); if (check_timeout()) {goto timeout;}
fputs($fp, "Accept-Encoding: *\r\n"); if (check_timeout()) {goto timeout;}
while (!feof($fp))
{$line.=fgets($fp); if (check_timeout()) {goto timeout;}
}
return $line;
timeout:
{return 'POST EXCEPTION: Total timeout!';
}
}
function check_timeout()
{return time()-$GLOBALS['POST_TO_HOST.TIME_START']>60;
}
Related
Once i initiated a function i am setting a flag on DB to TRUE.
and i need to set it FALSE on the end of the function.
Ex:
Class Preprocessor extends Machine{
function process(){
$this->db->setValue(TRUE); //Setting DB flag to TRUE
//OTHER CODES
$this->close_db_value(); // Setting DB flag to FALSE
}
function close_db_value(){
$this->db->setValue(FALSE); //Setting DB flag to FALSE
}
}
As you can see that it will work in normal cases, But if some error encountered in //OTHER CODES section then it will not execute the rest of codes.
The function mainly work in background (But not as a command line,its just closing the connection and start executing on background).
How can i ensure that the close_db_value() function executed upon script termination ?
Some of possibilities
Some critical errors that which leads the script to termination
exit called somewhere on the //OTHER CODE section
PHP max_execution_time exceeded
A Force Kill
Please help.
Use the set_error_handler() function in PHP. Place the name of the callback function you want called in case of error as the first parameter. Put the level of error (optional) that you want as the trigger as the second parameter.
If you are looking to handle every other type of error (except SIGKILLs or force quits), you can also try using register_shutdown_function() with a error_get_last() and a switch-case statement with the various types of errors you wish to handle (E_NOTICE, E_DEPRECATED, etc.).
For example,
register_shutdown_function('shutdown_callback');
function shutdown_callback(){
$error_type = error_get_last();
switch($error_type){
case E_ERROR: break;
case E_WARNING: break;
}
}
The __destruct(); magic function will also execute every time the script ends, or an object is unloaded.
I have a static method named ServerResponse that basically shows a message whether on success or fail. I just want to know the proper way to actually display the message and exit the script.
Should I implement my method like this:
public static function ServerResponse($e,$m){
print(json_encode([$e,$m]));
exit;
}
//Sample use:
if(this happens){
myclass::ServerResponse($x,$y);
}
or like this:
public static function ServerResponse($e,$m){
return json_encode([$e,$m]);
}
//Sample use:
if(this happens){
print(myclass::ServerResponse($x,$y));
exit;
}
Which one is proper and better... and why?
is there any difference between them? (on execution time).
"Don't be hard on me I am not an expert (just yet)..."
For better debugging, it's advised to always make a function or method return a value. So your 2nd sample should be chosen.
exit (or die) are commonly used when the program ends with an error, giving the ability to add an exit status (as a number or a string).
I suppose there will be no significant difference about the execution time.
I don't know if this is common practice but I only use exit to debug. If your script comes to the end of execution it will exit on it's own.
If you must exit, do it in the main script, not in a function.
functions should have one task and do that task. So the function ServerResponse should send a response and not kill the script.
I have been noticing in some PHP design patterns, some authors who write code examples, have return inside the method but it doesn't specify return value .
It just says "return"
Can some one please explain me what is the purpose of doing that? Below is an example
Thank you!
function addListItem(ListItem $listItem){
if(in_array($listItem, $this->listitems, true)){
return;
}
$this->listitems[] = $listItem;
}
That's done for side-effects (IO, altering globals, or the arguments passed by reference, or an object property, like in your example -- $this->listitems[] = $listItem;), or to indicate it's impossible to yield a valid result.
return;
is equivalent to
return null;
The return statement will stop the function immediately after it has been called. Because we do not want any value to be returned like integers, string or booleans, we just stop it so the code will not continue.
This can also be compared to break in a for or while loop.
Well for starters, you may hit an if statement that makes the rest of the code in the method unnecessary.
For example:
if(user->log_in == "")
{
show_error_msg();
return;
}
The "technically more correct" way of writing such code is:
if( !in_array($listItem, $this->listitems, true)) {
$this->listitems[] = $listItem;
}
However, sometimes you may have more complex testing, and proceeding in this manner may result in a single if block spanning several lines with many &&s, or nested if statements that fall off the edge of your screen.
Therefore, it is common to see the pattern of your code, namely "check failure conditions and exit the current block if necessary". This means you can have as few or as many conditions as you want, each with their own failure conditions, and if the code manages to reach the end of it then you're good to go.
In some cases, error handling is useful. Something like:
try {
if( failure condition 1) throw new Exception("Error message 1");
if( failure condition 2) throw new Exception("Error message 2");
// ...
do something here;
}
catch(Exception $e) {
// report error here
}
I have following piece of code which I can't modify.
if ( empty($post->comment_status) ) {
do_action('comment_id_not_found', $comment_post_ID);
exit;
}
I can create function called during do_action processing (hooks in wordpress).
function my_function () {
//do something
}
add_action('comment_id_not_found', 'my_function');
Is it possible to skip the exit; command in the condition?
Thanks
One possible solution said to be ugly would be to throw exception in you function while having all code you can't modify run in try block. That is, if you can put it in try-catch.
exit is a statement, there is no way to get around it and no way to modify it. The only way to avoid it is to make sure that your code doesn't pass by it. (eg. if(FALSE) exit; won't exit but in this: do_something(); exit; do_something_else(); the function do_something_else() will not be called.)
Once i initiated a function i am setting a flag on DB to TRUE.
and i need to set it FALSE on the end of the function.
Ex:
Class Preprocessor extends Machine{
function process(){
$this->db->setValue(TRUE); //Setting DB flag to TRUE
//OTHER CODES
$this->close_db_value(); // Setting DB flag to FALSE
}
function close_db_value(){
$this->db->setValue(FALSE); //Setting DB flag to FALSE
}
}
As you can see that it will work in normal cases, But if some error encountered in //OTHER CODES section then it will not execute the rest of codes.
The function mainly work in background (But not as a command line,its just closing the connection and start executing on background).
How can i ensure that the close_db_value() function executed upon script termination ?
Some of possibilities
Some critical errors that which leads the script to termination
exit called somewhere on the //OTHER CODE section
PHP max_execution_time exceeded
A Force Kill
Please help.
Use the set_error_handler() function in PHP. Place the name of the callback function you want called in case of error as the first parameter. Put the level of error (optional) that you want as the trigger as the second parameter.
If you are looking to handle every other type of error (except SIGKILLs or force quits), you can also try using register_shutdown_function() with a error_get_last() and a switch-case statement with the various types of errors you wish to handle (E_NOTICE, E_DEPRECATED, etc.).
For example,
register_shutdown_function('shutdown_callback');
function shutdown_callback(){
$error_type = error_get_last();
switch($error_type){
case E_ERROR: break;
case E_WARNING: break;
}
}
The __destruct(); magic function will also execute every time the script ends, or an object is unloaded.