Is it possible to show operations being done in php? - php

For example, suppose i have this very simple function
$a = 1;
$b = 2;
function Sum()
{
global $a, $b;
$b = $a + $b;
}
Sum();
echo $b;
This normally would output 3 directly. But is it possible to make php show the operations being done, like 3 = 1 + 2? (similar to a console.log) Thanks!

You can customize the function a little bit to achieve this:
function Sum($a, $b)
{
$c = $a + $b;
return "{$c} = {$a} + {$b}";
}
$a = 1;
$b = 2;
echo sum($a, $b);
Note that I've changed the function to use parameters. Using globals is not a very good idea. See this answer to know why.
The above code outputs:
3 = 1 + 2
If you want your function to perform multiple operations, you can create a switch block and define the operations, and display the corresponding symbol (+, -, x, รท etc.)

Related

Is there a clean way to use undefined variables as optional parameters in PHP?

Is there any nice way to use (potentially) undefined Variables (like from external input) as optional Function parameters?
<?php
$a = 1;
function foo($a, $b=2){
//do stuff
echo $a, $b;
}
foo($a, $b); //notice $b is undefined, optional value does not get used.
//output: 1
//this is even worse as other erros are also suppressed
#foo($a, $b); //output: 1
//this also does not work since $b is now explicitly declared as "null" and therefore the default value does not get used
$b ??= null;
foo($a,$b); //output: 1
//very,very ugly hack, but working:
$r = new ReflectionFunction('foo');
$b = $r->getParameters()[1]->getDefaultValue(); //still would have to check if $b is already set
foo($a,$b); //output: 12
the only semi-useful method I can think of so far is to not defining the default value as parameter but inside the actual function and using "null" as intermediary like this:
<?php
function bar ($c, $d=null){
$d ??= 4;
echo $c,$d;
}
$c = 3
$d ??= null;
bar($c,$d); //output: 34
But using this I still have to check the parameter twice: Once if it is set before calling the function and once if it is null inside the function.
Is there any other nice solution?
Ideally you wouldn't pass $b in this scenario. I don't remember ever running into a situation where I didn't know if a variable existed and passed it to a function anyway:
foo($a);
But to do it you would need to determine how to call the function:
isset($b) ? foo($a, $b) : foo($a);
This is kind of hackish, but if you needed a reference anyway it will be created:
function foo($a, &$b){
$b = $b ?? 4;
var_dump($b);
}
$a = 1;
foo($a, $b);
I would do something like this if this was actually a requirement.
Just testing with sum of the supplied values just for showing an example.
<?php
$x = 1;
//Would generate notices but no error about $y and t
//Therefore I'm using # to suppress these
#$sum = foo($x,$y,4,3,t);
echo 'Sum = ' . $sum;
function foo(... $arr) {
return array_sum($arr);
}
Would output...
Sum = 8
...based on the array given (unknown nr of arguments with ... $arr)
array (size=5)
0 => int 1
1 => null
2 => int 4
3 => int 3
4 => string 't' (length=1)
array_sum() only sums up 1,4 and 3 here = 8.
Even if above actually works I would not recommend it, because then whatever data can be sent to your function foo() without you having any control over it. When it comes to user input of any kind you should always validate as much as you can in your code before using the actual data from the user.

pass and return by reference at same time in php

Now I'm trying to understand references in php
in next example I try to pass $a and returned back to $b
I expected now the $a and $b are same!
function &test(& $var){
return ++$var;
}
$a = 5;
$b = &test($a);
$b = 10;
echo $a;
echo $b;
but they different!
I expect 1010 but I get 610
please someone help me in that and what going on.

Passing by reference, $a = &$b, is $a=$n the same as $b=$n?

I'm trying to understand passing by reference. This is probably a bad analogy, but is it like Newton's 3rd law (action-reaction pairs)?
For example, for the following code
$a = 4;
$b = 2;
$n = 42;
$a = &$b;
is
$a=$n the same as $b=$n? Isn't the value of $a and $b stored in the same address?
If you assign these variables normally:
$a = 1;
$b = 2;
$c = 3;
Then the associations will look like this:
a --> 1
b --> 2
c --> 3
Now, if you make $c into a reference of $a, like this:
$a = 1;
$b = 2;
$c = &$a;
Then the associations will look like this:
a --> 1 <--.
b --> 2 |
c --------/
In other words, $a and $c point to the same value. Because they both point to the same value we can change either of the variables and they will both point to the new value.
$a = 5;
echo "$a $c"; // Output: "5 5"
$c = 10;
echo "$a $c"; // Output: "10 10"
Yes, After assigning $n to $a, $b will point $n.
This is because after executing $a=&$b both $a and $b references a same memory location and become reference variable (is_ref=1). And the reference count (refcount) of that specific memory location increases by 1. Now whatever value you assign to any of those references both will point to same value.
Executing $a=$n means value of $n will be store to the location referenced by $a. And this is same location as $b.
See the example here.
$a, $b, $n are pointing different locations
php > $a = 4;
php > $b = 2;
php > xdebug_debug_zval('a'); // they are pointing different location
a: (refcount=1, is_ref=0)=int(4)
php > xdebug_debug_zval('b'); // they are pointing different location
b: (refcount=1, is_ref=0)=int(2)
php > $n = 42;
php > xdebug_debug_zval('n');
n: (refcount=1, is_ref=0)=int(42)
$a and $b both becomes a reference now
php > $a = &$b;
php > xdebug_debug_zval('b');
b: (refcount=2, is_ref=1)=int(2)
php > xdebug_debug_zval('a'); // a too
a: (refcount=2, is_ref=1)=int(2)
Assigning new value, NOT references to any of $a and $b
php > $a = $n;
php > xdebug_debug_zval('a'); // a holds $n's value '42' now
a: (refcount=2, is_ref=1)=int(42)
php > xdebug_debug_zval('b'); // same for b
b: (refcount=2, is_ref=1)=int(42)
Usually when you create a variable $a and $b, each has a unique memory address where their data is stored.
However, if you tell the interpreter that $a = &$b, that means that $a and $b now have the same memory address. If you assign anything to $a, or to $b, they will both echo the same value, because they store data in the same place in memory.
If you want to experiment, I suggest starting up the PHP interactive interpreter from the command line:
php -a
php > $a = 1;
php > $b = 2;
php > echo $a . ' ' . $b;
1 2
php > $a = &$b;
php > echo $a . ' ' . $b;
2 2
php > $a = 1;
php > echo $a . ' ' . $b;
1 1
php > $b = 2;
php > echo $a . ' ' . $b;
2 2
$a = $b & $b = $n has the same value but are different because the value is a primitive type and primitive types pass by value.
The most quick way to test if the code is using references or not is change the value of the source var and see if the target vars change his value or not.
$n = 1;
$a = $n;
$b = $n;
echo $a; // 1
echo $b; // 1
echo $n; // 1
$n = 2;
echo $a; // 1
echo $b; // 1
echo $n; // 2
However objects always are passed by reference
$n = new Object(1);
$a = $n;
$b = $n;
$n->newValue(5);
$a->printValue(); // 5
$b->printValue(); // 5
$a->newValue(7);
$b->printValue(); // 7

PHP short sentence of stating new vairable

I wonder if there is any way can short sentence to state a variable.
Purpose: only for if you are in a situation have to state 20 variables at the time. more convenience
$a = 1; $b = 2;
//Imagination like below
$a, $b = 1, 2;
$a = 1, $b = 2;
Thank you very much for your advice of alternatives.
(If you do not have any ideas, please do not accuse the way of why have to think about this), because arrray, (object) are alternatives, but not match what I need on my question
The closest you can get to that syntax is using list():
<?php
list ($a, $b) = array(1, 2);
echo $a . ' ' . $b; // prints "1 2"
Its magic!
EDIT:
For even more magic, you can use short array notation from PHP 5.4 onwards:
<?php
list($a, $b) = [1, 2];
print $a . ', ' . $b; // prints 1, 2
How is $a = 1, $b = 2; shorter than $a = 1; $b = 2; ?
If for any reason you need two assignments in one statement, you could to it with list:
list($a,$b) = array(1,2);
However, shortening is not a valid reason for this.

php variable $a contains variable $b in it update $b and $a should automatically update

I have two variables in PHP, say $a and $b. $a is a string variable. It contains $b. I want to update $a automatically if $b is updated.
$b = 4;
$a = "value is ".$b;
echo $a; // value is 4
$b = 5;
echo $a; // should print value is 5
Yes, $a can be updated automatically if you assign $b to $a by reference, but there should not be any string concatenation assigned to $a.
Try:
$b = 4;
$a = &$b;
$c = 'Value is ';
echo $c.$a;
$b = 5;
echo $c.$a;
Here is a demo
Not possible the way you want it. You see, variables can be passed by reference, like so:
$a = &$b;
Which will cause $a to automatically update when $b changes, however, it may not contain any other value, (like the string you want), so you'll have to use a function or another variable to do it.
$b = &$a;
echo "Value is $b";
or
$b = &$a;
$description = "Value is ";
echo $description . $b;
PHP doesn't have that feature. Related features you could use are:
References, which let you alias one variable to another. The value of each variable is the same, since they're simply symbol table aliases.
$b = "I'm b."
$a =& $b;
echo $a;
Variable variables, in which one variable holds the name of the other.
$b = "I'm b."
$a = 'b';
echo $$a;
However, variable variables should generally be avoided as they generally cause needless obfuscation.
Functions (as mithunsatheesh suggests). This is closest to what you want, as a function call is an expression that will have the value you're looking for. The only place a function wouldn't work where a variable would is when interpolating the value into a double-quoted string or a heredoc. Instead, you'd have to use string concatenation, or assign the result of the function call to a local variable and interpolate that.
You should pass it by reference. How to do it ?
Make a function:
function showValue(&$b)
{
return 'value is ' . $b;
}
echo showValue($b);
I think this should work.
Take a look at http://www.php.net/manual/en/language.references.whatdo.php
$a = 4;
$b =& $a;
$a = 5;
echo $b; // should print 5;
When a php script runs it runs "line after line". When you assign like this
$b = 4;
$a = "value is ".$b;
Value of $b is already assigned to $a as a integer 4 (not $b). So, if next $b is updated to some other value. Variable $a has no idea about it.
In this kind of case you have to use function or variable reference as describe in some other answers
$a = 4;
$b =& $a;
$a = 5;
echo $b;

Categories