Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:129935 X-Original-To: internals@lists.php.net Delivered-To: internals@lists.php.net Received: from php-smtp4.php.net (php-smtp4.php.net [45.112.84.5]) by lists.php.net (Postfix) with ESMTPS id 762641A00BC for ; Mon, 26 Jan 2026 18:41:09 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=php.net; s=mail; t=1769452874; bh=/a9G57V0zRwtMHbBi3OSoQe31th2hcQql5GVsCoh08s=; h=Date:Subject:To:References:From:In-Reply-To:From; b=V3rMfZ6fPcFeAYLSLc9X8t/HTSAGdL8KHbP26EDw5Zq0O/AbbPkUKZuy9TJGgN9il 9+P3hqXNR4T3TbWaC1BwYXQKGWFRrMcZm94skfQR3OxG/94EjRLIk2aJP+wLSCN9Iv Vf6hbIz+Sa9gnHxxu/p4hzRVZerjx6GSJov62eELOojH+BL12nmjBuEim5XsHhT014 ZT8afDFWkrO8WyomXLNo1CzUgKpF0Hc+w8PaxNxlSmU2JMJFrPTxvUOeFP3/PfZiUL 3aToNF4xxVeLtODb3wg3kAxDfXeySE5lkRkP4aouQjhiM39yfLoZf+F5dIoVWp0P0G 3llwrYWbda8wA== Received: from php-smtp4.php.net (localhost [127.0.0.1]) by php-smtp4.php.net (Postfix) with ESMTP id 1A763180087 for ; Mon, 26 Jan 2026 18:41:13 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 4.0.1 (2024-03-25) on php-smtp4.php.net X-Spam-Level: X-Spam-Status: No, score=-0.9 required=5.0 tests=BAYES_20,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,DMARC_MISSING,HTML_MESSAGE, RCVD_IN_DNSWL_LOW,SPF_HELO_PASS,SPF_PASS autolearn=no autolearn_force=no version=4.0.1 X-Spam-Virus: No X-Envelope-From: Received: from fout-b8-smtp.messagingengine.com (fout-b8-smtp.messagingengine.com [202.12.124.151]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by php-smtp4.php.net (Postfix) with ESMTPS for ; Mon, 26 Jan 2026 18:41:12 +0000 (UTC) Received: from phl-compute-10.internal (phl-compute-10.internal [10.202.2.50]) by mailfout.stl.internal (Postfix) with ESMTP id 416361D00018 for ; Mon, 26 Jan 2026 13:41:06 -0500 (EST) Received: from phl-frontend-03 ([10.202.2.162]) by phl-compute-10.internal (MEProxy); Mon, 26 Jan 2026 13:41:06 -0500 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=rwec.co.uk; h=cc :content-type:content-type:date:date:from:from:in-reply-to :in-reply-to:message-id:mime-version:references:reply-to:subject :subject:to:to; s=fm2; t=1769452866; x=1769539266; bh=XR5LNTW2Xo fofeo8fMNvDhtMV8Z6o9z/8kEO7kv2bXo=; b=Jc023gV6a42zHRMOq/JJ2Rde0G MhgfRj10jkh1y6WA9gagULdzrz9/IRRgdg4W8+MZTVVX0WDB77JkD7hfreloud+A uTZWuz4bt2VkcNOEHhxMkmOTtmxI83a02MnWAUChnd7XCEn9FJCCbac2J2z88FAG FhBpCTOWTobJUZ6fhXUblw7l42raoI6gkdSN0kABNL5sVBG5EKHHsPoeXqahnj5U sd8hvN5VYHiXXWZByjZQAz11BzB8x0tCcDRUYqHPpmjxDTKY+jys652l44dLuy7Z zoQB6GeNcqF1SVGE5IPL3FwQeKKPefy1YjVrWHR5ItKP0cb4x7pzE3QmpE9w== DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d= messagingengine.com; h=cc:content-type:content-type:date:date :feedback-id:feedback-id:from:from:in-reply-to:in-reply-to :message-id:mime-version:references:reply-to:subject:subject:to :to:x-me-proxy:x-me-sender:x-me-sender:x-sasl-enc; s=fm2; t= 1769452866; x=1769539266; bh=XR5LNTW2Xofofeo8fMNvDhtMV8Z6o9z/8kE O7kv2bXo=; b=dcIa2J3cFvV/q9JBhm1Ig/TrWe+SwoTYOd0kxnEh3NtBAN2mglV jjDTw4f0MqLvzl25oXVL5h5XNGFfkkaja9bux12o5593RVtyo5ZRZ0Jm9faaIlPS /PlchU5An1yodfiNA0WYIRuSpFT7Vz4sSxCJOcA/6JDf+iCYkkAa867Xiw6Zr9pL LgYuy9JyMffhBpjGIj4nurIxoVIFqGjKb3g2iyPaHcbgeAExBha59dYOXa3q081b maX3CgvI/Rf/gvSNO5YCebzKCsws604QSjvdljCEDbO1yTPILqAMCga69YRDE9uT 4I5q6IoBMxRVg9vIIPmd1r0B3LhA2MwFHdQ== X-ME-Sender: X-ME-Received: X-ME-Proxy-Cause: gggruggvucftvghtrhhoucdtuddrgeefgedrtddtgdduheekgedvucetufdoteggodetrf dotffvucfrrhhofhhilhgvmecuhfgrshhtofgrihhlpdfurfetoffkrfgpnffqhgenuceu rghilhhouhhtmecufedttdenucenucfjughrpegtkfffgggfuffvfhfhjgesrgdtreertd dvjeenucfhrhhomhepfdftohifrghnucfvohhmmhhinhhsucglkffoufhorfgnfdcuoehi mhhsohhprdhphhhpsehrfigvtgdrtghordhukheqnecuggftrfgrthhtvghrnhepheetle eiiefgueduieeuieffvdevheduueefkeejuefgffeftdeitdegtedtleetnecuvehluhhs thgvrhfuihiivgeptdenucfrrghrrghmpehmrghilhhfrhhomhepihhmshhophdrphhhph esrhifvggtrdgtohdruhhkpdhnsggprhgtphhtthhopedupdhmohguvgepshhmthhpohhu thdprhgtphhtthhopehinhhtvghrnhgrlhhssehlihhsthhsrdhphhhprdhnvght X-ME-Proxy: Feedback-ID: id5114917:Fastmail Received: by mail.messagingengine.com (Postfix) with ESMTPA for ; Mon, 26 Jan 2026 13:41:05 -0500 (EST) Content-Type: multipart/alternative; boundary="------------ZBT0axIv4pahDALN80wdjGEj" Message-ID: <85c420f7-38ba-46f6-b434-addb733d023d@rwec.co.uk> Date: Mon, 26 Jan 2026 18:41:04 +0000 Precedence: list list-help: list-unsubscribe: list-post: List-Id: x-ms-reactions: disallow MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: Re: [PHP-DEV] [RFC] Deprecate Fuzzy Type Casts and Allow Stringable in Strict Mode To: internals@lists.php.net References: <31563ed1-ac44-47ef-9fca-3ebbfc567ba5@sandfox.me> <8A9F3BDD-1C65-4E6F-BD65-C43F017D52E2@rwec.co.uk> Content-Language: en-GB In-Reply-To: From: imsop.php@rwec.co.uk ("Rowan Tommins [IMSoP]") This is a multi-part message in MIME format. --------------ZBT0axIv4pahDALN80wdjGEj Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit On 26/01/2026 08:46, Alexandre Daubois wrote: > Le ven. 23 janv. 2026 à 18:46, Rowan Tommins [IMSoP] > a écrit : >> I don't think we should repurpose widely-used syntax for a different use case. If we want new functionality, with new semantics, we should add new syntax for that. > The rules/semantics proposed in this RFC are not new. Hi Alexandre, In my mind, cast / type conversion behaviour can be described in two parts: The first part is the rules of which input values count as "valid". In the case of string to integer casts: can it include a leading '+'? leading space? trailing space? leading zeroes? trailing zero decimal part? trailing non-zero decimal part? other trailing characters? PHP has a bunch of different versions of these rules used in different contexts, and it would certainly be nice to make them all more consistent. The second part is the behaviour of what happens for a value which is *not* valid. In the case of parameter types and return types, this is to throw a TypeError. But that's not the only reasonable option - you might just a boolean (true=valid, false=invalid); or you might want to substitute a default value. In the case of the "(int)" syntax, I would argue that the established behaviour is that an invalid value *returns a default value* - for an integer, zero. In other words, I don't think (int)'hello' is a "fuzzy cast", it is an operator with clear and useful behaviour: reject 'hello' as input for integer, and substitute default zero. The "(int)" syntax has had that behaviour in PHP for over 20 years, and a huge amount of code has been written explicitly making use of that fact. For instance, I see this pattern a lot: $foo = (int)$_GET['foo']; if ( $foo !== 0 ) { ... } Changing the behaviour of (int) so that it throws a TypeError for invalid cases would be a hugely disruptive change, and would replace one useful feature with a different useful feature, rather than having good syntax for both. Regards, -- Rowan Tommins [IMSoP] --------------ZBT0axIv4pahDALN80wdjGEj Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: 8bit
On 26/01/2026 08:46, Alexandre Daubois wrote:
Le ven. 23 janv. 2026 à 18:46, Rowan Tommins [IMSoP]
<imsop.php@rwec.co.uk> a écrit :
I don't think we should repurpose widely-used syntax for a different use case. If we want new functionality, with new semantics, we should add new syntax for that.
The rules/semantics proposed in this RFC are not new. 


Hi Alexandre,

In my mind, cast / type conversion behaviour can be described in two parts:


The first part is the rules of which input values count as "valid". 

In the case of string to integer casts: can it include a leading '+'? leading space? trailing space? leading zeroes? trailing zero decimal part? trailing non-zero decimal part? other trailing characters?

PHP has a bunch of different versions of these rules used in different contexts, and it would certainly be nice to make them all more consistent.


The second part is the behaviour of what happens for a value which is *not* valid.

In the case of parameter types and return types, this is to throw a TypeError. But that's not the only reasonable option - you might just a boolean (true=valid, false=invalid); or you might want to substitute a default value.

In the case of the "(int)" syntax, I would argue that the established behaviour is that an invalid value *returns a default value* - for an integer, zero. 

In other words, I don't think (int)'hello' is a "fuzzy cast", it is an operator with clear and useful behaviour: reject 'hello' as input for integer, and substitute default zero.


The "(int)" syntax has had that behaviour in PHP for over 20 years, and a huge amount of code has been written explicitly making use of that fact. For instance, I see this pattern a lot:

$foo = (int)$_GET['foo'];
if ( $foo !== 0 ) { ... }

Changing the behaviour of (int) so that it throws a TypeError for invalid cases would be a hugely disruptive change, and would replace one useful feature with a different useful feature, rather than having good syntax for both.


Regards,

-- 
Rowan Tommins
[IMSoP]
--------------ZBT0axIv4pahDALN80wdjGEj--