php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Request #46128 Magic function __cast($to)
Submitted: 2008-09-19 15:52 UTC Modified: 2016-07-13 18:15 UTC
Votes:86
Avg. Score:4.9 ± 0.4
Reproduced:61 of 62 (98.4%)
Same Version:23 (37.7%)
Same OS:33 (54.1%)
From: 131 dot php at cloudyks dot org Assigned:
Status: Open Package: *General Issues
PHP Version: 5.2.6 OS: Linux
Private report: No CVE-ID: None
View Developer Edit
Welcome! If you don't have a Git account, you can't do anything here.
If you reported this bug, you can edit this bug over here.
(description)
Block user comment
Status: Assign to:
Package:
Bug Type:
Summary:
From: 131 dot php at cloudyks dot org
New email:
PHP Version: OS:

 

 [2008-09-19 15:52 UTC] 131 dot php at cloudyks dot org
Description:
------------
The same way __toString is implemented, i suggest new magics functions
__toBool, __toInt, __toArray, or maybe, as suggested on php.general, a generic magic function __cast($type){}

An example of implementation could be
class error extends exeption {
 __toBool(){return false; }
}




Reproduce code:
---------------
<?
//by C. Guthrie
class MyClass {
  function __cast($type)
  {
   switch ($type)
   {
     case 'string':
       return 'Foo';
     case 'array':
       return array('Foo');
     case 'DomDocument':
       // etc.
   }
  }
}
$my = new MyClass();


$xml = (DomDocument)$foo;

It would return the result of __cast called with $type == 'DomDocument'.



Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2008-10-05 08:49 UTC] mark at hell dot ne dot jp
Did a test implementation only supporting a few types (int, float, bool, string).

This works as expected.

Test code:
----------
class test {
	public function __cast($type) {
		switch($type) {
			case 'string': return 'a string';
			case 'bool': return true;
			case 'float': return 123.456;
			case 'int': return 978;
			default:
				var_dump($type);
				return null;
		}
	}
}

$t = new test();

var_dump((string)$t);
var_dump((int)$t);
var_dump((float)$t);
var_dump((bool)$t);

Result:
string(8) "a string"
int(978)
float(123.456)
bool(true)

Here's the patch file for this simple implementation against PHP 5.3.0alpha2.

http://ookoo.org/svn/snip/php-5.3.0alpha2_class_cast_func.patch
 [2008-10-05 16:33 UTC] 131 dot php at cloudyks dot org
This is awesome
 [2008-10-06 04:15 UTC] mark at hell dot ne dot jp
Backported to PHP 5.2.6 :

http://ookoo.org/svn/snip/php-5.2.6_class_cast_func.patch
 [2008-10-27 17:08 UTC] info at netmosfera dot it
AWESOME!
php developers, please, we need it!!
http://bugs.php.net/bug.php?id=46404
 [2008-11-23 09:01 UTC] mark at hell dot ne dot jp
Please test the following extension :

http://ookoo.org/svn/snip/phpcastable/

This extension adds a "Castable" interface. Any class implementing this interface have to implement a __cast() function. This function will be called when the object needs to be casted to a type.

This extension is EXPERIMENTAL and needs more testing/review before being used in any production system.
 [2009-02-06 00:11 UTC] rayro at gmx dot de
This is such a nice Implementation and very useful, but i prefer to add the methods __toBool, __toInt and __toArray rather than __cast, stay tuned with PHP's other magic methods..

I dont agree fully with that post in feature request #38508 from helly. If that'll be the way, why did the decision for magic methods?
Isnt that all complex although? ^^
We know, but in my eyes (and many others), i think that these magically stuff is one of the top key features for php. And none of these features will become critism i think. If not needed, just dont use them!

The additional goody __toInvoke() introduced in 5_3 is a such nice addition for developing "quick gets" based on nested object sets:
<?php
$magazine(3)->getArticles();
// old way
$magazine->getArticle($magazine->useMagazine(3));
?>
This helper is a "backdoor" like way to enable PHP to fully write nested Objects like in Javascript. And my opinion for that: I LIKE THIS :)

I think this is a very very discussable topic to the changes for 5_3 or 6_0 beside the wanted support for traditional type hinting and utf8!

thanks
 [2009-03-28 12:41 UTC] andrea at 3site dot it
I wonder why you guys do not implement in core the PECL php_operator which would make code style and life much easier.

I cannot imagine a Number class which needs (int)$obj for every single operation.
Please do not get me wrong, __cast is a good idea, but it covers only explicit cases while every other decent language (C#, Java, Python) allows developer to implement implic cast behavior as well.

This, in PHP 5.3, would be excellent (but probaly an illusion thou).
Regards
 [2011-01-20 22:54 UTC] neoegm at hotmail dot com
This would be very useful in order to be able to define a specific evaluation method for an object as a boolean, to, for example, simplify if-switches, so you can just do:

if ($obj)
{
	//...
}

Here an example of a class which toggles its own value each time it's evaluated as a boolean:

class ToggleObj
{
	var $val = FALSE;

	function __toBool()
	{
		$ret = $this->val;
		$this->val = !$ret;
		return $ret;
	}
}

$obj = new ToggleObj;

if ($obj)
{
	//Does not enter
}

if ($obj)
{
	//Now it does
}


Or going further, to make even table rows highlighted:

foreach ($rows as $row)
{
?>
	<tr class="<?=$obj?"":"highlighted"?>">
		<td><?=$row?></td>
	</tr>
<?php
}

Thanks.

NeoEGM
http://www.neoegm.com/
 [2012-09-04 14:18 UTC] qfox at ya dot ru
WHEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEEN?!!
There was 3 years to patch sources!
 [2012-09-05 21:01 UTC] maciej dot sz at gmail dot com
I think we all need this badly. It just suits the direction in which the 5.4 is going.

Regarding same functionality I think it is worth nothing that the conversion to boolean should be implicit. Otherwise such code could not work:

<?php
function check($response) {
  if ( ! $response ) die('error');
}

$resp = new Response();
check($resp->isSuccessful());
check($resp); // this would fail without the cast if the conversion was explicit
?>
 [2012-11-09 16:00 UTC] shabazzk at gmail dot com
My suggestion is to replace `__cast($to)` with `__toObject($object)` (or even 
`__toSelf($object)`). That way, we have a magic method for each type to cast to, 
and we avoid the messy switch/if statements.
 [2013-05-03 19:10 UTC] mkutschker-php at yahoo dot com
While __toXxx() may more in line with the existing __toString() IMHO __cast() is more in line with the other magic functions and gettype(). If I could choose I'd take __cast() and deprectate __toString().
 [2013-05-04 15:02 UTC] shabazzk at gmail dot com
I think we're preaching to the choir at this point. I don't think its a high 
priority to anyone who is actually developing PHP. If we want this feature, then 
we should take it upon ourselves to implement and we should all support it 
getting 
in to a release version.

I'm sure once this is in there then that is when the masses will wonder how they 
ever did without it.
 [2016-07-13 18:15 UTC] cmb@php.net
-Package: Feature/Change Request +Package: *General Issues
 [2016-07-13 18:15 UTC] cmb@php.net
> If we want this feature, then we should take it upon ourselves
> to implement and we should all support it getting in to a
> release version.

Well said, see <https://wiki.php.net/rfc/howto>.
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Nov 21 12:01:29 2024 UTC