the output of the following code?
echo '1' . (print '2') + 3;
I tested and the result is 214, but why 214?
if I code:
echo (print '2') + 3;
the result is 24
Then, echo '1' . '24'; should be 124.
Confused...
When the expression is parsed, the "print" statement is immediately writing its output. So there's the first 2. By definition its return value is 1.
So then the remaining expression is the character 1, followed by the numeric expression 1+3. Therefore 1 and 4.
214
Related
I was experimenting with weak/dynamic typing properties of PHP in preparation for a test and was completely baffled by the output of this string concatenation. Can someone explain how this is even possible?
<?php echo 1 . "/n" . '1' + 1 ?><br />
output:
2
Analysis:
echo 1 . "/n" . '1' + 1;
is equivalent to
//joined first 3 items as string
echo "1/n1"+1;
is equivalent to
//php faces '+' operator, it parses '1/n1' as number
//it stops parsing at '/n' because a number doesn't
//contain this character
echo "1"+1;
is equivalent to
echo 1+1;
This question already has answers here:
Why does "echo '2' . print(2) + 3" print 521? [closed]
(4 answers)
Closed 9 years ago.
This is related to:
Why does "echo '2' . print(2) + 3" print 521?
I was wondering why
print(99) + print(99) + print(99) + print(99);
shows 99100100100....
I'd like to learn about the quirks of PHP.
Print is not a function, so print(99) is the same as print 99. We can remove the parentheses for clarity.
print 99 + print 99 + print 99 + print 99;
The expression is evaluated from the right, so it becomes
print (99 + print (99 + print (99 + print 99)));
The rightmost print executes first, printing "99" and evaluating to 1.
Output:
99
Code left to be evaluated:
print (99 + print (99 + print (99 + 1)));
Again, the rightmost print is executed and it prints 99+1 ("100") and evaluates to 1.
Output:
99100
Code left to be evaluated:
print (99 + print (99 + 1));
...and so on.
The print function produces output and then (see documentation) returns the value 1. To further complicate things, the print function is a language construct (see the documentation) which does not require the parenthesis.
So, if you had the statement
print(99) + print(99);
What you are actually seeing is the printing of a 99, from the right-most print, followed by the result of print(99) + 1; which, due to the language construct, is the same as print 99 + 1; or print (99 + 1);.
Because, from the docs,
print …
Returns 1, always
Because print() always returns 1. Check the php manual
This is unlike echo() which does not return the value.
Both print() and echo() are not actual functions but language constructs.
I know the above code outputs 323
But need an explanation on how is it outputting 323
Anybody can pls explain?
Both echo and print are intended to behave more like language constructs and not functions. As such they have a flow of control. What happens here in your code is that you are calling print from inside of a language construct (echo). Meaning that print will send its output first before echo has completed its task (remember you called print from inside of echo).
To show you what's happening a bit more clearly, it actually has nothing to do with operator precedence at all.
echo ('a') . ('b' * (print 'c')); // ca0
// This is the same thing as...
echo 'a' . 'b' * print 'c'; // ca0
Notice the operators have no effect on the order of the characters in the resulting output here.
print always returns 1 so what happens here is that you performed an arithmetic operation on 'b' * 1, which is the stirng b multiplied by the return value of print. Thus why you see the output as c (print sent output before echo has even finished doing it's job), first, and then everything that echo was supposed to print.
Let me elaborate even further with the following example...
echo print 'a' . 'b' . 'c'; // abc1
Notice the 1 at the end of that output. This is because all echo did was output the return value of print and not the string. Instead, print is the one that provided the abc as output (and remember print is able to send output before echo can since echo has to wait to process everything inside of the construct before it can finish).
This makes it even more clear...
echo (print 'a') . 'b' . 'c'; // a1bc
Now the 1 comes right after a.
If you want echo to send the output for each expression individually, you can supply one argument for every expression you want processed and sent to output... So for example:
echo print 'a', 'b', 'c'; // a1bc
echo 2, 3 * print 3; // 233
I hope that clarifies it a bit more for you.
The reason is (print 3) has priority over the previous operators. If you write `echo (8) . (7 * (print 3)); you will get 387, for example.
Here
echo (2).(3*print(3));
Step1:(Starting execution)
echo (2).(3*print(3)); //Output = ''
Step 2:(Print action will take place)
echo (2).(3*1); // Will print 3 and returns 1 as per print function. Output = 3
Step 3:(Multiplication operation)
echo (2).(3); // Multiplication operation willtake place. Output = 3
Step 4:(Prints the data)
echo (2).(3); //The . Operator will used to concate the strings in php, thus Output = 323
Print has more priority then echo thus it prints 3 first later 2 and 3
echo "1" . (print '2') + 3; returns 214. How does the script end up with *14?
When you do
echo "1" . (print '2') + 3;
PHP will do (demo)
line # * op fetch ext return operands
---------------------------------------------------------------------------------
2 0 > PRINT ~0 '2'
1 CONCAT ~1 '1', ~0
2 ADD ~2 ~1, 3
3 ECHO ~2
4 > RETURN 1
In words:
print 2, return 1
concat "1" with returned 1 => "11"
add "11" + 3 => 14
echo 14
and that's 214.
The operators + - . have equal Operator Precedence, but are left associative:
For operators of equal precedence, left associativity means that evaluation proceeds from left to right, and right associativity means the opposite.
Edit: since all the other answers claim PHP does 1+3, here is further proof that it doesnt:
echo "1" . (print '2') + 9;
gives 220, e.g. 11+9 and not 1 . (1+9). If the addition had precedence over the concatenation, it would have been 2110, but for that you'd had to write
echo "1" . ((print '2') + 9);
echo "1" . (print '2') + 3;
You need to think of it in a logical order, of what happens first.
Before we can echo anything, the - "1" . (print '2') + 3 - we need to evaluate it to solve it.
First we write 1 down on a scrap of paper as the first part of our calculation.
Scrap paper: 1
Answer Sheet:
We calculate "print '2'", which as a function writes the number 2 to our sheet of answer paper and returns a 1, which we write on our scrap piece of paper.
Scrap paper: 1 . 1 +3
Answer Sheet: 2
After this we want to concatenate the next piece on to the end, due to the "."
Scrap paper: 11 + 3
Answer Sheet: 2
Now we put it together
Scrap paper: 11 + 3
Scrap paper: 14
Answer Sheet: 2
Then we echo out our scrap data to our answer sheet
Answer Sheet: 214
echo "1" . (print '2') + 3;
1.
Code--: echo "1" . (print '2') + 3;
Result:
2.
Code--: echo "1" . 1 + 3;
Result: 2
3.
Code--: echo 11 + 3;
Result: 2
4.
Code--: echo 14;
Result: 2
5.
Code--:
Result: 214
I hope that makes some sense, and remember the return of print is always 1, and any function that prints or echo's while inside another execution will echo/print before it's caller/parent does.
The 1 in between is actually a true statement.
Because print statement actually returns a true.
So you get 2 (from print), 1 (from echo print), and 4 (from 1+3)
print is executed first because of the parenthesis, so it print's 2 first, but it returns 1. Then, your echo gets executed, printing 1. You then concatenate to it the result of print (which is 1) with 3 added to it. That's 4.
print always return 1 according to: http://php.net/manual/en/function.print.php
So, because arithmetic operator has precedence over one for concatenation, so you get:
"1" . (1+3)
... that is "14" ;). And because print sends string directly to output you get '2' in front of everything....
Consider the following line of code:
<?php
$x = 10;
$y = 7;
echo '10 - 7 = '.$x-$y;
?>
The output of that is 3, which is the expected result of the calculation $x-$y. However, the expected output is:
10 - 7 = 3
My question therefore is, what happened to the string that I'm concatenating with the calculation? I know that in order to produce the result I expected, I need to enclose the arithmetic operation in parenthesis:
<?php
$x = 10;
$y = 7;
echo '10 - 7 = '.($x-$y);
?>
outputs
10 - 7 = 3
But since PHP does not complain about the original code, I'm left wondering what the logic behind the produced output in that case is? Where did the string go? If anyone can explain it or point me to a location in the PHP manual where it is explained, I'd be grateful.
Your string '10 - 7 = ' is being concatenated with $x. Then that is being interpreted as an int which results in 10 and then 7 is subtracted, resulting in 3.
For more explanation, try this:
echo (int) ('10 - 7 = ' . 10); // Prints "10"
More information on string to number conversion can be found at http://www.php.net/manual/en/language.types.string.php#language.types.string.conversion
If the string starts with valid numeric data, this will be the value used
In this code:
echo '10 - 7 = '.$x-$y;
The concatenation takes precedence, so what you're left with is this:
echo '10 - 7 = 10'-$y;
Because this is trying to perform integer subtraction with a string, the string is converted to an integer first, so you're left with something like this:
echo (int)'10 - 7 = 10'-$y;
The integer value of that string is 10, so the resulting arithmetic looks like this:
echo 10-$y;
Because $y is 7, and 10 - 7 = 3, the result being echoed is 3.
. and - have the same precedence, so PHP is reinterpreting '10 - 7 = 10' as a number, giving 10, and subtracting 7 gives 3.
PHP runs operations in the order defined here ; https://www.php.net/manual/en/language.operators.precedence.php
Take a look at this example ;
$session_period = 30;
new \DateTime('now -' . $session_period+1 . ' minutes');
Beware! This will NOT give you the time 31 minutes ago.
In this case PHP just interprets starting from the leftmost part of an expression so this simple-looking expression returns the wrong result;
Because ;
'now -' . $session_period => 'now -30'
then PHP will cast the string to 0 and add 1 to that => 1
and 1 . ' minutes' => '1 minutes'
That's why the expression above will give you the result of
new \DateTime('1 minutes')
To avoid this kind of confusion, use () like this ;
new \DateTime('now -' . ($session_period+1) . ' minutes');