Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:125236 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 09E8C1A00BD for ; Sun, 25 Aug 2024 20:30:02 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=php.net; s=mail; t=1724617914; bh=wa2pE2Xjev9TZ7qXGoOPJqvtLoI1SI8O6hZltFY9DYc=; h=Subject:From:In-Reply-To:Date:Cc:References:To:From; b=bCFJtVRY6d5i9A6LEq8mt2pHP9tJ61C8PcA5KmBXOsOP7uepqs9eT1Nf4SHoGMJQn wmlmFb4ECwNxtEM8nt8wCriKtxatuzFuo15kCx9HNbj1iLwGxuF4dy1HebgQkfLLYY MUOMf7Lx7MEBo3A2bKgslL0IThP8ZFmYp2UU28DhEQ2RUBg/1MYSda4VH3PpTILvg6 h7fSY1XjdTaUteqyAC/gzf0DRGK/nwln9KRciGnNCV+qBiMU/6GcxV/ms34iDnaTGN meQ5t/bngw0H/AQWMdgYHhDWzHP4WJLj5NLZTWYBOJhmtMG+nWCVDA1scHJsV8BUgu faeh+u04YKjHQ== Received: from php-smtp4.php.net (localhost [127.0.0.1]) by php-smtp4.php.net (Postfix) with ESMTP id 2B55F180086 for ; Sun, 25 Aug 2024 20:31:52 +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=0.6 required=5.0 tests=BAYES_50,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,DMARC_MISSING,SPF_HELO_NONE, SPF_PASS autolearn=no autolearn_force=no version=4.0.0 X-Spam-Virus: No X-Envelope-From: Received: from nebula.zort.net (nebula.zort.net [96.241.205.3]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by php-smtp4.php.net (Postfix) with ESMTPS for ; Sun, 25 Aug 2024 20:31:48 +0000 (UTC) Received: from smtpclient.apple (pulsar.zort.net [96.241.205.6]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by nebula.zort.net (Postfix) with ESMTPSA id 98CBB20278F5A; Sun, 25 Aug 2024 16:29:55 -0400 (EDT) DKIM-Filter: OpenDKIM Filter v2.11.0 nebula.zort.net 98CBB20278F5A DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=zort.net; s=zort; t=1724617795; bh=CH3xz6xpk56XevlrlXxD4RK8YYTOPO0aKsMT/MyHK5o=; h=Subject:From:In-Reply-To:Date:Cc:References:To:From; b=PK5F9NgGALZcdQQRUZxc96aFqjmzTSqXVJC+6D1QYmMYHCbAux+tzhQl6wgyrAOUQ OOwwH9XOCQKrMsM198v0PCKpovaQOfExluFRDQ0Vifh8OyKkV9nEihbevtlVk28+Rz eYwdSN+GnuKb3DzIQiP6hcXUrGl4+jrJRQLuf3/w= Content-Type: text/plain; charset=us-ascii Precedence: bulk list-help: list-post: List-Id: internals.lists.php.net x-ms-reactions: disallow Mime-Version: 1.0 (Mac OS X Mail 16.0 \(3776.700.51\)) Subject: Re: [PHP-DEV] [RFC] Default expression In-Reply-To: Date: Sun, 25 Aug 2024 16:29:45 -0400 Cc: internals@lists.php.net Content-Transfer-Encoding: quoted-printable Message-ID: <9F07D1D1-E539-4F23-94F2-8957C2AE7A5E@zort.net> References: <0c8ed5d6-5507-4c41-8d7f-05d14ba8aa4c@scriptfusion.com> <0cfd3a28-3cb0-4478-85fb-cf086d8e5c66@app.fastmail.com> To: "Rowan Tommins [IMSoP]" X-Mailer: Apple Mail (2.3776.700.51) From: jbafford@zort.net (John Bafford) On Aug 25, 2024, at 14:46, Rowan Tommins [IMSoP] = wrote: >=20 > On 25/08/2024 18:44, John Bafford wrote: >=20 >> Although I'm not sold on the idea of using default as part of an=20 >> expression, I would argue that a default function parameter value is=20= >> fair game to be read and manipulated by callers. If the default value=20= >> was intended to be private, it shouldn't be in the function = declaration. >=20 > There's an easy argument against this interpretation: child classes = can freely change the default value for a parameter, as long as they do = not make it mandatory. https://3v4l.org/SEsRm > That matches my intuition: that the public API, as a contract, states = that the parameter is optional; the specification of what happens when = it is not provided is an implementation detail. > For comparison, consider constructor property promotion; the caller = shouldn't know or care whether a class is defined as: > public function __construct(private int $bar) {} > or: > private int $my_bar; > public function __construct(int $bar) { $this->my_bar =3D $bar; } > The syntax sits in the function signature because it's convenient, not = because it's part of the API. This is only by current convention. It used to be that parameter names = were not part of the API contract, but now with named parameters, they = are. There's no reason default values couldn't (or shouldn't) become = part of the API contract in the same way. (Note that in some other languages, default parameter values are not = only part of the API contract, but they're emitted into the clients when = compiled, so an API can change/add/remove its default values and the = client continues to function as it used to with the value as defined at = compile time. This doesn't currently matter for PHP, where you have the = full source to anything you run, but could become important later if PHP = gained ahead-of-time compiled binary modules.) >> One important case where reading the default value could be important = is >> in interoperability with different library versions. For example, a=20= >> library might change a default parameter value between versions. If=20= >> you're using the library, and want to support both versions, you = might=20 >> both not want to set the value, and yet also care what the default = value >> is from the standpoint of knowing what to expect out of the function. >=20 > This seems contradictory to me. If you use the default, you're telling = the library that you don't care about that parameter, and trust it to = provide a default. > If you want to know what the library did with its arguments, = reflecting the signature will never be enough anyway. For example, it's = quite common to write code like this: > function foo(?SomethingInterface $blah =3D null) { > if ( $blah =3D=3D=3D null ) { > $blah =3D self::_setup_default_blah(); > } > // ... > } > A caller can't tell by looking at the signature that a new version of = the library has changed what _setup_default_blah() returns. If the = library doesn't provide an API to get $blah out later, then it's a = private detail that the caller has no business inspecting. Well, but that's the private default example I described. In that case = you're not intended to be able to reason about what the default is, = because it's a private implementation detail of the function, as opposed = to being expressed in the parameter list. Although, if it weren't = intended to be an implementation detail, the only thing stopping you = from writing in the parameter list like this: function foo(SomethingInterface $blah =3D = self::_setup_default_blah()) {...} is because PHP doesn't currently allow default values to be computed at = runtime. (Maybe it should.) -John