Is there any difference between int and integer in PHP?
Which is the newer or more recommended use?
$a = (int)"3 euros";
echo $a; // $a==3
$a = (integer)"3 euros";
echo $a; // $a==3
The difference arises when we use type hinting from php 7.0+
this is valid
function getId(): int
{
return $id;
}
this is not
function getId(): integer
{
return $id;
}
the second one will expect you to return an object of a 'class integer', which will cause a strange sentence:
Uncaught TypeError: Return value of getId() must be an instance of integer, integer returned in ...
No.
They are the same, they both cast the value to an integer, one is just terser by four characters.
Source.
Quoting the manual:
Converting to integer
To explicitly convert a value to integer, use either the (int) or
(integer) casts. ...
This is not quite true, there is actually a difference between int and integer.
Here a simple example:
//print_r('PHP version: '.phpversion().'<br />');
//PHP version: 5.5.23
$i = '1';
function testme(int $j){
print_r ($j);
}
testme(intval($i));
This little portion of code will print an "E_RECOVERABLE_ERROR"
since testme function is expecting 'int' and get 'integer' instead.
Related
I have function which will receive parameter ?string
public function func(?string $x): string
{
$x = trim(strtolower($x));
$x = preg_replace('/\s+/', ' ', $x);
$x = str_replace(' ', '-', $x);
return $x;
}
running ./vendor/bin/phpstan analyse give those errors:
Parameter #1 $str of function strtolower expects string, string|null given.
Parameter #3 $subject of function preg_replace expects array|string, string|null given.
Parameter #3 $subject of function str_replace expects array|string, string|null given.
strtolower needs string and preg_replace&str_replace need array|string what is the best way to solve this without changing param from ?string $x to string $x?
in otherwords how to change var type from string|null to string ?
While PHP can convert null to an empty string with casting, you really have to ask yourself why this function should even accept a null value in the first place.
If null means you have some default value for $x, then that seems perfectly logical, and you can use null coalescing to make $x the default string value if $x is null.
$x = $x ?? 'default';
However, the above could be more effectively resolved by defining 'default' in the signature:
function func(string $x = 'default')
But based on your code, there really isn't any reason for null to be passed to this function. In my opinion, that's a code smell and should not be allowed. This function only works with strings, so don't allow nulls to begin with. The null value should then be handled before it reaches this function, by the consumer.
I believe you may be able to typecast your value of $x,
example:
function foo(?string $x) : string {
$a = (string) $x;
return $a;
}
This should yield,
var_dump(foo("test"));
string(4) "test"
And,
var_dump(foo(null));
string(0) ""
Hope this is what you were looking for.
With PHP 7 I just found out that if I have a function like this:
function automatic_int_conversion(int $value) {
echo gettype($value) . ' ' . $value;
}
and I call it with a float parameter like this one:
automatic_int_conversion(2.0); # prints out: integer 2
the float(2.0) value is automatically converted to an int, while if I call the function with the float(NAN) this way:
automatic_int_conversion(NAN); # TypeError
I get a type error although the documentation says:
As of PHP 7.0.0, instead of being undefined and platform-dependent, NaN and Infinity will always be zero when cast to integer.
IMHO this is pretty confusing and not consistent, because either every float is automatically converted or none.
Am I missing anything?
There is a difference between type casting (explicit) and type coercion (implicit). The parameter value is not being cast to an int, it is being coerced. You can cast any value to int, e.g.:
echo (int) "a"; // prints 0
But passing "a" to your type declared function throws an error, just as passing NAN does:
automatic_int_conversion("a"); // TypeError
Coercion only works the same as casting on a very limited set of values.
You might want to enable strict types to disable the coercions for function parameters, then it will work 'as expected':
declare(strict_types=1);
class wat
{
public $a = 3.14;
public $x = 9;
public $y = 2;
}
$a = new wat();
var_dump(1000 + $a);
var_dump($a + 1000);
The output is:
int(1001)
int(1001)
Well, adding the wat* object to an integer is obviously not the right thing to do, since PHP complains about it with "Object of class wat could not be converted to int", but still, what does it do?
(I also have a practical reason for asking this, I want to refactor a function to get rid of the "PHP Notice", while still keeping behaviour completely unchanged.)
*: http://img.youtube.com/vi/kXEgk1Hdze0/1.jpg
Addition (+) implicitly casts both operands to float if either one of them is float, otherwise both operands are cast to int (See paragraph #2.)
It seems that, at least for now, an object cast to int results in the value 1, hence the result 1000 + 1 = 1001 or 1 + 1000 = 1001, however, per the documentation, the behavior is undefined and should not be relied upon.
If you've turned on E_NOTICE error reporting, a notice should also be produced, saying that object could not be converted to int.
You're right that you shouldn't cast an Object to an Integer and you can't!
Than's why PHP assigns the integer 1 to the variable and should give you a notice which looks like this:
Notice: Object of class foo could not be converted to int in /path/to/file.php on line 1
$foo is now 1
int(1)
to be sure I get the code which actually do the cast:
from Zend/zend_operators.c:
case IS_OBJECT:
{
int retval = 1;
/* some other code */
ZVAL_LONG(op, retval); // < This sets the 1 you see.
return;
}
so it is not like i said before a internal cast ((int)(boolean)$object)
by doing this they preserve semantics of 0,"",NULL,false = false and !0,"...",Object = true
I was reading PHP manual and I came across type juggling
I was confused, because I've never came across such thing.
$foo = 5 + "10 Little Piggies"; // $foo is integer (15)
When I used this code it returns me 15, it adds up 10 + 5 and when I use is_int() it returns me true ie. 1 where I was expecting an error, it later referenced me to String conversion to numbers where I read If the string starts with valid numeric data, this will be the value used. Otherwise, the value will be 0 (zero)
$foo = 1 + "bob3"; /* $foo is int though this doesn't add up 3+1
but as stated this adds 1+0 */
now what should I do if I want to treat 10 Little Piggies OR bob3 as a string and not as an int. Using settype() doesn't work either. I want an error that I cannot add 5 to a string.
If you want an error, you need to trigger an error:
$string = "bob3";
if (is_string($string))
{
trigger_error('Does not work on a string.');
}
$foo = 1 + $string;
Or if you like to have some interface:
class IntegerAddition
{
private $a, $b;
public function __construct($a, $b) {
if (!is_int($a)) throw new InvalidArgumentException('$a needs to be integer');
if (!is_int($b)) throw new InvalidArgumentException('$b needs to be integer');
$this->a = $a; $this->b = $b;
}
public function calculate() {
return $this->a + $this->b;
}
}
$add = new IntegerAddition(1, 'bob3');
echo $add->calculate();
This is by design as a result of PHP's dynamically typed nature and of course lack of an explicit type declaration requirement. Variable types are determined based on context.
Based on your example, when you do:
$a = 10;
$b = "10 Pigs";
$c = $a + $b // $c == (int) 20;
Calling is_int($c) will of course always evaluate to a boolean true because PHP has decided to convert the result of the statement to an integer.
If you're looking for an error by the interpreter, you won't get it since this is, like I mentioned, something built into the language. You might have to write a lot of ugly conditional code to test your data types.
Or, if you want to do that for testing arguments passed to your functions - that's the only scenario which I can think of where you might want to do this - you can trust the client invoking your function to know what they are doing. Otherwise, the return value can simply be documented to be undefined.
I know coming from other platforms and languages, that might be hard to accept, but believe it or not a lot of great libraries written in PHP follow that same approach.
Hi when trying to cast from a string to int using int() I get the following error:
Call to undefined function int()
Why would this be?
intval() works just fine but I cannot use int() for some reason.
There is no int function; you must use proper typecasting syntax for this:
$b = (int) $a;
Or:
settype($a, 'int');
function int($string) {
return (int) $string;
}
Have you tried
$intVar = (int)$var;
If PHP is telling you that int() isn't a function, then it probably isn't.