Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:122727 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 qa.php.net (Postfix) with ESMTPS id F38C01A009C for ; Fri, 22 Mar 2024 13:06:24 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=php.net; s=mail; t=1711112806; bh=JAj8mFR9ypVNmFdqZEvdALp8A8uTJrE+lqDhBPgC+Rk=; h=Date:Subject:To:References:From:In-Reply-To:From; b=QlzleVm8YnAEBedaGPrRe7+MaaA5HV2AwC8IheWxORSO04DCYQjLG124wjhFUYcDV X0Mt+os9h8ld4Jy1OLW4716NGj1KLCuUVE9Vtny9Oq9dQKTU+MJxWLvUAOMxIu1XPM aAN6Y6v+O0jL3VQ0ec3m7miiGbuK8d0pc0MmB5ky0/f5CuqhiJbT4eBysGdYQeZdEM K7YJejdtP9U2JUmlLv2a6XGGZVDx+rDq3158rblHZ7WTJShR5JC/Ussv9U5qagHu+4 UWoHqJCu0KYUpNMjS3xWxReZaxNfqfbz7iaLl0r9aGF2DqESR+1eLSLto7BJ+r7M/x zh7TULbMdcvhA== Received: from php-smtp4.php.net (localhost [127.0.0.1]) by php-smtp4.php.net (Postfix) with ESMTP id 8A1CB180592 for ; Fri, 22 Mar 2024 13:06:45 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 4.0.0 (2022-12-13) on php-smtp4.php.net X-Spam-Level: ** X-Spam-Status: No, score=2.1 required=5.0 tests=BAYES_50,BODY_8BITS, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,DMARC_PASS, HTML_MESSAGE,RCVD_IN_DNSWL_NONE,RCVD_IN_MSPIKE_H2,SPF_HELO_NONE, SPF_PASS,T_SCC_BODY_TEXT_LINE autolearn=no autolearn_force=no version=4.0.0 X-Spam-Virus: No X-Envelope-From: Received: from mail-wm1-f41.google.com (mail-wm1-f41.google.com [209.85.128.41]) (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 ; Fri, 22 Mar 2024 13:06:45 +0000 (UTC) Received: by mail-wm1-f41.google.com with SMTP id 5b1f17b1804b1-41468f6d584so15599475e9.0 for ; Fri, 22 Mar 2024 06:06:23 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=seld.be; s=google; t=1711112782; x=1711717582; darn=lists.php.net; h=in-reply-to:from:references:to:content-language:subject:user-agent :mime-version:date:message-id:from:to:cc:subject:date:message-id :reply-to; bh=Xk76whJitc01OeNktURExkCeK2JBiFohpMi3fgHz+tI=; b=XSah6nb4wD4fk37Mt+aAEgQ2M827Ce+INVfL8vfVtJLfJulmUnMp7X7lYeIz9eju1W utjsVeYROdqUK81kuv6z+w31kg54Yvo46+2NdLeQqLwNd3KURUhGFVWGfUNABqQS5CT8 mEpeqf/oP+bqxCZUkC6eWLRqAONXCIQ/ODchIBTd8BPlZGmZDgCfb5vv902gvF58tHp2 ZVd4k98MXs+1jpYus9Q/d2cs2wQsQzpWrr5w7OuFlAl/6n/e5GQGFijetgZ+0v8e2Udi X5nVgbRc9B/fmoCN6PVyOgeiM2k9ovwKRg+Mpq+aDC6dgN8lLbsxIKgM5mcF2+aTC67N y6zA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1711112782; x=1711717582; h=in-reply-to:from:references:to:content-language:subject:user-agent :mime-version:date:message-id:x-gm-message-state:from:to:cc:subject :date:message-id:reply-to; bh=Xk76whJitc01OeNktURExkCeK2JBiFohpMi3fgHz+tI=; b=By67/HsX7K9WyPi5cf2x/VskD/ZQZog4kaHkDAkCYKYcmrgCGhgp8V6fDYX850a9xo pmZKCeYqGOSQS4KzRfk/P0OwfNioNbTWZTl65sdnaaO3W+XSvt44KE5IYY2O4GoJtowH zWP3I2o++q+69uXsf2+Kttvna6IfFhgH8j5mRUEMbkB5wAgDGIecG4ax/BZHEVd11TUV q5WyjyeJ0xDjBqjKIyv8kq+Kx/GdQdGoFZ4Hg8Lbos4KoA/RRpGqDRO0QsiWUgVRXw+b lUcNx0AAN8nA98BmvPmSvPF8UCpYnT7LhgL4BCVBPHnqPWZ00tcvYP12rlgmBqhFoyPp 6ePw== X-Forwarded-Encrypted: i=1; AJvYcCWgees0gQ3WsFeVB6Cz6WNNABrho9zFDa00aeEQurU6Pwo21/TyaLPz7QksBBvgBgCajlZvV5PTUihysHmTzpAEPo62Kxzd6Q== X-Gm-Message-State: AOJu0YyHslSTJWOoNtJHFq7+J/ghCcciV8XNoRdOcuW/wLxg6TDq3AP3 3mWRXovOb2AzLzIiZbgYc/kfYQPsWxB8Owor/+Grl7njIt2pWnOQqb97E46/af8nwCkHZTfKUaG E X-Google-Smtp-Source: AGHT+IGFvv+8Y37Q1owJpFxIKP4sWdT56qqAf8nsbnIOPBJo2XuG2PIVgzDPSRQBrrC2JVYmIDKoZQ== X-Received: by 2002:a05:600c:1392:b0:414:b66:7079 with SMTP id u18-20020a05600c139200b004140b667079mr1333076wmf.36.1711112781616; Fri, 22 Mar 2024 06:06:21 -0700 (PDT) Received: from ?IPV6:2a02:168:4b6e:0:355c:9b25:d:8295? ([2a02:168:4b6e:0:355c:9b25:d:8295]) by smtp.gmail.com with ESMTPSA id p17-20020a05600c469100b004132ae838absm3007732wmo.43.2024.03.22.06.06.21 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Fri, 22 Mar 2024 06:06:21 -0700 (PDT) Content-Type: multipart/alternative; boundary="------------ET2UXd6sZ97ZoEqTkQghzHW2" Message-ID: Date: Fri, 22 Mar 2024 14:06:20 +0100 Precedence: bulk list-help: list-post: List-Id: internals.lists.php.net MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: Re: [PHP-DEV] Proposal: AS assertions Content-Language: fr To: "Rowan Tommins [IMSoP]" , internals@lists.php.net References: <3F78A125-1946-42E2-A4F5-A2B282BE2107@rwec.co.uk> <2d7ec203-6e80-445c-94f4-d29ef58743b1@rwec.co.uk> <7d53f2e4-46f3-46f1-89b0-6e1d3b0b2e32@app.fastmail.com> In-Reply-To: <7d53f2e4-46f3-46f1-89b0-6e1d3b0b2e32@app.fastmail.com> From: j.boggiano@seld.be (Jordi Boggiano) This is a multi-part message in MIME format. --------------ET2UXd6sZ97ZoEqTkQghzHW2 Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit On 2024-03-22 10:46, Rowan Tommins [IMSoP] wrote: > On Fri, 22 Mar 2024, at 08:17, Jordi Boggiano wrote: >> We perhaps could make sure that as does not throw if used with `??`, >> or that `??` catches the type error and returns the right-hand >> expression instead: >> >> So to do a nullable typecast you would do: >> >>     $a as int|float ?? null >> > > While this limits the impact to only expressions combining as with ?? > it still has the same fundamental problem: you can't meaningfully use > it with a nullable type. > > > As a concrete example, imagine you have an optional $description > parameter, and want to ensure any non-null values are converted to > string, but keep null unchanged. > > At first sight, it looks like you could write this: > > $descString = $description as string|null ?? (string)$description; > > But this won't work - the ?? swallows the null and turns it into an > empty string, which isn't what you wanted. You need some syntax that > catches the TypeError, but preserves the null: > > $descString = $description as string|null else (string)$description; > // or > $descString = $description as string|null catch (string)$description; > // or > $descString = $description as string|null default (string)$description; > > > I actually think there are quite a lot of scenarios where that idiom > would be useful: > > $optionalExpiryDateTime = $expiry as ?DateTimeInterface else new > DateTimeImmutable($expiry); > $optionalUnixTimestamp = $time as ?int else strotime((string)$time); > $optionalUnicodeName = $name as ?UnicodeString else new UnicodeString( > $name ); > etc Yeah I think this looks great actually, minus the confusing bits about |null which is in reality yes probably rarely useful in a "as" cast. as that throws + default to catch it👍🏻 Best, Jordi -- Jordi Boggiano @seldaek -https://seld.be --------------ET2UXd6sZ97ZoEqTkQghzHW2 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: 8bit
On 2024-03-22 10:46, Rowan Tommins [IMSoP] wrote:
On Fri, 22 Mar 2024, at 08:17, Jordi Boggiano wrote:
We perhaps could make sure that as does not throw if used with `??`, or that `??` catches the type error and returns the right-hand expression instead:

So to do a nullable typecast you would do:

    $a as int|float ?? null


While this limits the impact to only expressions combining as with ?? it still has the same fundamental problem: you can't meaningfully use it with a nullable type.


As a concrete example, imagine you have an optional $description parameter, and want to ensure any non-null values are converted to string, but keep null unchanged.

At first sight, it looks like you could write this:

$descString = $description as string|null ?? (string)$description;

But this won't work - the ?? swallows the null and turns it into an empty string, which isn't what you wanted. You need some syntax that catches the TypeError, but preserves the null:

$descString = $description as string|null else (string)$description;
// or
$descString = $description as string|null catch (string)$description;
// or
$descString = $description as string|null default (string)$description;


I actually think there are quite a lot of scenarios where that idiom would be useful:

$optionalExpiryDateTime = $expiry as ?DateTimeInterface else new DateTimeImmutable($expiry);
$optionalUnixTimestamp = $time as ?int else strotime((string)$time);
$optionalUnicodeName = $name as ?UnicodeString else new UnicodeString( $name );
etc

Yeah I think this looks great actually, minus the confusing bits about |null which is in reality yes probably rarely useful in a "as" cast.

as that throws + default to catch it👍🏻

Best,
Jordi

-- 
Jordi Boggiano
@seldaek - https://seld.be
--------------ET2UXd6sZ97ZoEqTkQghzHW2--