PHP char coding, #==0, 0==NULL, #!=NULL - php

I need to use a special character as a stop/break signal for my program. I was trying out '#' '&' '#' and kept on receiving errors.
After some messing around, I discovered that all characters including the ones above all had the numeric value 0! I did so by comparing their values with numerics, because at first I thought it used ASCII codes.
Wait a minute, that's not right, because NULL also equals to 0! But the characters definitely does not equal to NULL!
So, what kind of char coding does PHP use? Is it impossible to compare chars with numbers?
Thanks in advance!

I'm just assuming you're doing something like:
var_dump("#" == 0);
// bool(true)
When comparing to numbers, strings are cast into numbers to deal with situations like '123' == 123. The string '#', or in fact pretty much every non-numeric string, casts to 0.
That's why there's the === operator:
var_dump("#" === 0);
// bool(false)
Welcome to weakly typed languages.
http://www.php.net/manual/en/language.types.type-juggling.php

It has nothing to do with ascii or char coding, it is just php implicit casting while comparisons.
http://www.php.net/manual/en/language.operators.comparison.php

When you compare a string with an integer, the string will be casted to int and give 0.
You might want to use ord:
<?php
$str = "\n";
if (ord($str) == 10) {
echo "\$str is a line feed.\n";
}
?>

Related

PHP object property false evaluation with operator "==" [duplicate]

I'm really confused as to why this operation works. Can someone explain it?
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
$test2 = "3581169b064f71be1630b321d3ca318f";
if ($test1 == 0)
echo "Test 1 is Equal!?";
if ($test2 == 0)
echo "Test 2 is Equal!?";
// Returns: Test 1 is Equal!?
For clarification, I am trying to compare the string "0" to the $test variables. I already know to fix the code I can just enclose (as I should have) the 0 in ""s
I'm wondering if this is a PHP bug, a server bug, or somehow a valid operation. According to http://us3.php.net/types.comparisons this should not have worked.
Edit: Scratch that, apparently it does mention that Loose comparisons between string and 0 is true. But I still don't know why.
Edit 2: I've revised my question, why does the $test2 value of "3581169b064f71be1630b321d3ca318f" not work?
From the PHP manual:
String conversion to numbers
When a string is evaluated in a
numeric context, the resulting value
and type are determined as follows.
The string will be evaluated as a
float if it contains any of the
characters '.', 'e', or 'E'.
Otherwise, it will be evaluated as an
integer.
The value is given by the initial
portion of the string. If the string
starts with valid numeric data, this
will be the value used. Otherwise, the
value will be 0 (zero). Valid numeric
data is an optional sign, followed by
one or more digits (optionally
containing a decimal point), followed
by an optional exponent. The exponent
is an 'e' or 'E' followed by one or
more digits.
Type conversion using the == operator
The == operator is a loosely-typed comparison. It will convert both to a common type and compare them. The way strings are converted to integers is explained here.
Note that the page you linked to doesn't contradict this. Check the second table, where it says that comparing the integer 0 to a string "php" using == shall be true.
What happens is that the string is converted to integer, and non-numeric strings (strings that do not contain or begin with a number) convert to 0.
Numeric vs non-numeric strings
A string that consists of a number, or begins with a number, is considered a numeric string. If the string has other characters after that number, these are ignored.
If a string starts with a character that cannot be interpreted as part of a number, then it is a non-numeric string and will convert to 0. This doesn't mean that a numeric string has to start with a digit (0-9) - for example "-1" is a numeric string because the minus sign is part of a number in that case.
So for example, your string "d85d1d81b25614a3504a3d5601a9cb2e" does not start with a number, so it would convert to 0. But your second string "3581169b064f71be1630b321d3ca318f" would be converted to integer 3581169. So that's why your second test does not work the same way.
What you should do
You probably want:
if ($test1 === "0")
Notice the use of triple equals instead of a double equals. This ensures that what you are comparing is a string that contains the digit zero only, and prevents any type conversion.
After some investigation, it turns out aidan from the PHP manual mentioned that any strings that do not start with a number will be converted to 0 when casted as an integer.
This means that:
("php" == 0) === true
("1php" == 0) === false
Very annoying and not well documented. It was at the bottom of the comments on the type comparison page.
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
this string starts with a "d", which is not valid number, the var will resolve to 0 and your test#1 will pass.
$test2 = "3581169b064f71be1630b321d3ca318f";
this string starts with 3581169 which is a valid number, so the var will resolve to that value which is not equal to 0.
So your test#2 will not pass.
I've been using some conversions and comparisons to test if a numeric string is a number:
$test1="19de6a91d2ca9d91721d82f1bd8102b6";
echo (float)$test1==$test1; //TRUE
echo is_float($test1); //FALSE
//Converting the string to float and then converting it to string and compare will do the trick
echo (string)((float)$test1)==(string)$test1; //FALSE
$test2="5.66";
echo (float)$test2==$test2; //TRUE
//Testing the numeric string using `is_float` wont give the expected result
echo is_float($test2); //FALSE
echo (string)((float)$test2)==(string)$test2; //TRUE

Not able to understand the boolean logic [duplicate]

I'm really confused as to why this operation works. Can someone explain it?
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
$test2 = "3581169b064f71be1630b321d3ca318f";
if ($test1 == 0)
echo "Test 1 is Equal!?";
if ($test2 == 0)
echo "Test 2 is Equal!?";
// Returns: Test 1 is Equal!?
For clarification, I am trying to compare the string "0" to the $test variables. I already know to fix the code I can just enclose (as I should have) the 0 in ""s
I'm wondering if this is a PHP bug, a server bug, or somehow a valid operation. According to http://us3.php.net/types.comparisons this should not have worked.
Edit: Scratch that, apparently it does mention that Loose comparisons between string and 0 is true. But I still don't know why.
Edit 2: I've revised my question, why does the $test2 value of "3581169b064f71be1630b321d3ca318f" not work?
From the PHP manual:
String conversion to numbers
When a string is evaluated in a
numeric context, the resulting value
and type are determined as follows.
The string will be evaluated as a
float if it contains any of the
characters '.', 'e', or 'E'.
Otherwise, it will be evaluated as an
integer.
The value is given by the initial
portion of the string. If the string
starts with valid numeric data, this
will be the value used. Otherwise, the
value will be 0 (zero). Valid numeric
data is an optional sign, followed by
one or more digits (optionally
containing a decimal point), followed
by an optional exponent. The exponent
is an 'e' or 'E' followed by one or
more digits.
Type conversion using the == operator
The == operator is a loosely-typed comparison. It will convert both to a common type and compare them. The way strings are converted to integers is explained here.
Note that the page you linked to doesn't contradict this. Check the second table, where it says that comparing the integer 0 to a string "php" using == shall be true.
What happens is that the string is converted to integer, and non-numeric strings (strings that do not contain or begin with a number) convert to 0.
Numeric vs non-numeric strings
A string that consists of a number, or begins with a number, is considered a numeric string. If the string has other characters after that number, these are ignored.
If a string starts with a character that cannot be interpreted as part of a number, then it is a non-numeric string and will convert to 0. This doesn't mean that a numeric string has to start with a digit (0-9) - for example "-1" is a numeric string because the minus sign is part of a number in that case.
So for example, your string "d85d1d81b25614a3504a3d5601a9cb2e" does not start with a number, so it would convert to 0. But your second string "3581169b064f71be1630b321d3ca318f" would be converted to integer 3581169. So that's why your second test does not work the same way.
What you should do
You probably want:
if ($test1 === "0")
Notice the use of triple equals instead of a double equals. This ensures that what you are comparing is a string that contains the digit zero only, and prevents any type conversion.
After some investigation, it turns out aidan from the PHP manual mentioned that any strings that do not start with a number will be converted to 0 when casted as an integer.
This means that:
("php" == 0) === true
("1php" == 0) === false
Very annoying and not well documented. It was at the bottom of the comments on the type comparison page.
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
this string starts with a "d", which is not valid number, the var will resolve to 0 and your test#1 will pass.
$test2 = "3581169b064f71be1630b321d3ca318f";
this string starts with 3581169 which is a valid number, so the var will resolve to that value which is not equal to 0.
So your test#2 will not pass.
I've been using some conversions and comparisons to test if a numeric string is a number:
$test1="19de6a91d2ca9d91721d82f1bd8102b6";
echo (float)$test1==$test1; //TRUE
echo is_float($test1); //FALSE
//Converting the string to float and then converting it to string and compare will do the trick
echo (string)((float)$test1)==(string)$test1; //FALSE
$test2="5.66";
echo (float)$test2==$test2; //TRUE
//Testing the numeric string using `is_float` wont give the expected result
echo is_float($test2); //FALSE
echo (string)((float)$test2)==(string)$test2; //TRUE

PHP casting an expression [duplicate]

I'm really confused as to why this operation works. Can someone explain it?
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
$test2 = "3581169b064f71be1630b321d3ca318f";
if ($test1 == 0)
echo "Test 1 is Equal!?";
if ($test2 == 0)
echo "Test 2 is Equal!?";
// Returns: Test 1 is Equal!?
For clarification, I am trying to compare the string "0" to the $test variables. I already know to fix the code I can just enclose (as I should have) the 0 in ""s
I'm wondering if this is a PHP bug, a server bug, or somehow a valid operation. According to http://us3.php.net/types.comparisons this should not have worked.
Edit: Scratch that, apparently it does mention that Loose comparisons between string and 0 is true. But I still don't know why.
Edit 2: I've revised my question, why does the $test2 value of "3581169b064f71be1630b321d3ca318f" not work?
From the PHP manual:
String conversion to numbers
When a string is evaluated in a
numeric context, the resulting value
and type are determined as follows.
The string will be evaluated as a
float if it contains any of the
characters '.', 'e', or 'E'.
Otherwise, it will be evaluated as an
integer.
The value is given by the initial
portion of the string. If the string
starts with valid numeric data, this
will be the value used. Otherwise, the
value will be 0 (zero). Valid numeric
data is an optional sign, followed by
one or more digits (optionally
containing a decimal point), followed
by an optional exponent. The exponent
is an 'e' or 'E' followed by one or
more digits.
Type conversion using the == operator
The == operator is a loosely-typed comparison. It will convert both to a common type and compare them. The way strings are converted to integers is explained here.
Note that the page you linked to doesn't contradict this. Check the second table, where it says that comparing the integer 0 to a string "php" using == shall be true.
What happens is that the string is converted to integer, and non-numeric strings (strings that do not contain or begin with a number) convert to 0.
Numeric vs non-numeric strings
A string that consists of a number, or begins with a number, is considered a numeric string. If the string has other characters after that number, these are ignored.
If a string starts with a character that cannot be interpreted as part of a number, then it is a non-numeric string and will convert to 0. This doesn't mean that a numeric string has to start with a digit (0-9) - for example "-1" is a numeric string because the minus sign is part of a number in that case.
So for example, your string "d85d1d81b25614a3504a3d5601a9cb2e" does not start with a number, so it would convert to 0. But your second string "3581169b064f71be1630b321d3ca318f" would be converted to integer 3581169. So that's why your second test does not work the same way.
What you should do
You probably want:
if ($test1 === "0")
Notice the use of triple equals instead of a double equals. This ensures that what you are comparing is a string that contains the digit zero only, and prevents any type conversion.
After some investigation, it turns out aidan from the PHP manual mentioned that any strings that do not start with a number will be converted to 0 when casted as an integer.
This means that:
("php" == 0) === true
("1php" == 0) === false
Very annoying and not well documented. It was at the bottom of the comments on the type comparison page.
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
this string starts with a "d", which is not valid number, the var will resolve to 0 and your test#1 will pass.
$test2 = "3581169b064f71be1630b321d3ca318f";
this string starts with 3581169 which is a valid number, so the var will resolve to that value which is not equal to 0.
So your test#2 will not pass.
I've been using some conversions and comparisons to test if a numeric string is a number:
$test1="19de6a91d2ca9d91721d82f1bd8102b6";
echo (float)$test1==$test1; //TRUE
echo is_float($test1); //FALSE
//Converting the string to float and then converting it to string and compare will do the trick
echo (string)((float)$test1)==(string)$test1; //FALSE
$test2="5.66";
echo (float)$test2==$test2; //TRUE
//Testing the numeric string using `is_float` wont give the expected result
echo is_float($test2); //FALSE
echo (string)((float)$test2)==(string)$test2; //TRUE

PHP comparison '==' problem

Why is the output 'in'?
<?php
if (1=='1, 3')
{
echo "in";
}
?>
The == operator does type conversion on the two values to try to get them to be the same type. In your example it will convert the second value from a string into an integer, which will be equal to 1. This is then obviously equal to the value you're matching.
If your first value had been a string - ie '1' in quotes, rather than an integer, then the match would have failed because both sides are strings, so it would have done a string comparison, and they're different strings.
If you need an exact match operator that doesn't do type conversion, PHP also offers a tripple-equal operator, ===, which may be what you're looking for instead.
Hope that helps.
Because PHP is doing type conversion, it's turning a string into an integer, and it's methods of doing so work such that it counts all numbers up until a non-numeric value. In your case that's the substring ('1') (because , is the first non-numeric character). If you string started with anything but a number, you'd get 0.
You are comparing a string and an integer. The string must be converted to an integer first, and PHP converts numeric strings to integers. Since the start of that string is '1', it compares the number one, with the number one, these are equal.
What functionality did you intend?
If you're trying to check if 1 is equal to 1 or 3, then I would definitely do it this way:
if (1 == 1 || 1 == 3)
Please refer to the PHP documentation:
http://php.net/manual/en/language.operators.comparison.php
The output should be:
in
From PHP's documentation:
When converting from a string to an
integer, PHP analyzes the string one
character at a time until it finds a
non-digit character. (The number may,
optionally, start with a + or - sign.)
The resulting number is parsed as a
decimal number (base-10). A failure to
parse a valid decimal number returns
the value 0.
I'm guessing you want to know whether a variable is in a range of values.
You can use in_array:
if (in_array(1, array(1, 3, 5, 6)))
echo "in";
if(in_array(1, array(1,3)) {
echo "in";
}

Comparing String to Integer gives strange results

I'm really confused as to why this operation works. Can someone explain it?
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
$test2 = "3581169b064f71be1630b321d3ca318f";
if ($test1 == 0)
echo "Test 1 is Equal!?";
if ($test2 == 0)
echo "Test 2 is Equal!?";
// Returns: Test 1 is Equal!?
For clarification, I am trying to compare the string "0" to the $test variables. I already know to fix the code I can just enclose (as I should have) the 0 in ""s
I'm wondering if this is a PHP bug, a server bug, or somehow a valid operation. According to http://us3.php.net/types.comparisons this should not have worked.
Edit: Scratch that, apparently it does mention that Loose comparisons between string and 0 is true. But I still don't know why.
Edit 2: I've revised my question, why does the $test2 value of "3581169b064f71be1630b321d3ca318f" not work?
From the PHP manual:
String conversion to numbers
When a string is evaluated in a
numeric context, the resulting value
and type are determined as follows.
The string will be evaluated as a
float if it contains any of the
characters '.', 'e', or 'E'.
Otherwise, it will be evaluated as an
integer.
The value is given by the initial
portion of the string. If the string
starts with valid numeric data, this
will be the value used. Otherwise, the
value will be 0 (zero). Valid numeric
data is an optional sign, followed by
one or more digits (optionally
containing a decimal point), followed
by an optional exponent. The exponent
is an 'e' or 'E' followed by one or
more digits.
Type conversion using the == operator
The == operator is a loosely-typed comparison. It will convert both to a common type and compare them. The way strings are converted to integers is explained here.
Note that the page you linked to doesn't contradict this. Check the second table, where it says that comparing the integer 0 to a string "php" using == shall be true.
What happens is that the string is converted to integer, and non-numeric strings (strings that do not contain or begin with a number) convert to 0.
Numeric vs non-numeric strings
A string that consists of a number, or begins with a number, is considered a numeric string. If the string has other characters after that number, these are ignored.
If a string starts with a character that cannot be interpreted as part of a number, then it is a non-numeric string and will convert to 0. This doesn't mean that a numeric string has to start with a digit (0-9) - for example "-1" is a numeric string because the minus sign is part of a number in that case.
So for example, your string "d85d1d81b25614a3504a3d5601a9cb2e" does not start with a number, so it would convert to 0. But your second string "3581169b064f71be1630b321d3ca318f" would be converted to integer 3581169. So that's why your second test does not work the same way.
What you should do
You probably want:
if ($test1 === "0")
Notice the use of triple equals instead of a double equals. This ensures that what you are comparing is a string that contains the digit zero only, and prevents any type conversion.
After some investigation, it turns out aidan from the PHP manual mentioned that any strings that do not start with a number will be converted to 0 when casted as an integer.
This means that:
("php" == 0) === true
("1php" == 0) === false
Very annoying and not well documented. It was at the bottom of the comments on the type comparison page.
$test1 = "d85d1d81b25614a3504a3d5601a9cb2e";
this string starts with a "d", which is not valid number, the var will resolve to 0 and your test#1 will pass.
$test2 = "3581169b064f71be1630b321d3ca318f";
this string starts with 3581169 which is a valid number, so the var will resolve to that value which is not equal to 0.
So your test#2 will not pass.
I've been using some conversions and comparisons to test if a numeric string is a number:
$test1="19de6a91d2ca9d91721d82f1bd8102b6";
echo (float)$test1==$test1; //TRUE
echo is_float($test1); //FALSE
//Converting the string to float and then converting it to string and compare will do the trick
echo (string)((float)$test1)==(string)$test1; //FALSE
$test2="5.66";
echo (float)$test2==$test2; //TRUE
//Testing the numeric string using `is_float` wont give the expected result
echo is_float($test2); //FALSE
echo (string)((float)$test2)==(string)$test2; //TRUE

Categories