Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:107835 Return-Path: Delivered-To: mailing list internals@lists.php.net Received: (qmail 90207 invoked from network); 19 Nov 2019 20:05:28 -0000 Received: from unknown (HELO php-smtp3.php.net) (208.43.231.12) by pb1.pair.com with SMTP; 19 Nov 2019 20:05:28 -0000 Received: from php-smtp3.php.net (localhost [127.0.0.1]) by php-smtp3.php.net (Postfix) with ESMTP id B16D72C0463 for ; Tue, 19 Nov 2019 09:58:25 -0800 (PST) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on php-smtp3.php.net X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,RCVD_IN_DNSWL_NONE,SPF_HELO_NONE autolearn=no autolearn_force=no version=3.4.2 X-Spam-ASN: AS3215 2.6.0.0/16 X-Spam-Virus: Error (Cannot connect to unix socket '/var/run/clamav/clamd.ctl': connect: Connection refused) Received: from mail-yw1-xc2e.google.com (mail-yw1-xc2e.google.com [IPv6:2607:f8b0:4864:20::c2e]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by php-smtp3.php.net (Postfix) with ESMTPS for ; Tue, 19 Nov 2019 09:58:25 -0800 (PST) Received: by mail-yw1-xc2e.google.com with SMTP id n82so7611445ywc.7 for ; Tue, 19 Nov 2019 09:58:25 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=newclarity-net.20150623.gappssmtp.com; s=20150623; h=mime-version:subject:from:in-reply-to:date:cc :content-transfer-encoding:message-id:references:to; bh=ZXqYR9GriPHAv6++kODAeojEaCXDPOkkv31TA3/i6Po=; b=QuOs2rS4UuoNwZTsYH86hgEqistnf3ynvZcdxulpKKRXXAmvT4PSZQKm8+ihNgEMzh fPeRZ/EfVA4kYp0oRFq38IKFum/m6ZQDQkSvH46OQNhFCQNi4fyFWo5LlDnfnx7A+igx fOZ/nH7uOCwArVs52iewSbDlhfqLz/y39QSDPCJiBPUpg1bTZPpzk30SUH3Eu+c4o+WT mlcMi9diNpuBtf3g6xn1cUuKsJVo5l9yWOY/OhrGX6H7tyiD3rkPZLYlhRDCORkgXpy6 kzlj9X5ulbkrajTOJ6xb1ovhSVvOfzdRTFXknsSt/7OaNKLXx1wiLRobd8UWt5TaEtYW KnPg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:subject:from:in-reply-to:date:cc :content-transfer-encoding:message-id:references:to; bh=ZXqYR9GriPHAv6++kODAeojEaCXDPOkkv31TA3/i6Po=; b=lmJszLCjdUJ/LltcbrUOthrHAsbchviiuQ9VX8Ex+vcGUl5l7UN+EYPJNI7d5xgzDi S54ZvFNVZ2H2vYawZY+dGgMyC3y4ON3AowdAYZc2mV3D04ER2skXNJZi3rFG8iSCZvDa zFMkHCTDGLUyFd1cUhuBeYEL+P41b5EutzSrvO2b1PzUNeLctL5E478QM9/Mb6P5bAUo TkhH/utHHKvk+pSMQtx4ubccThzvLpphISx/VJ7ZMRLBSuAm/lhL6ZwGGzob+yVOHUHl chKiJZp+2l8fcvUWfzL6B5jd5i9hsk9PYUCr1xU+aAaj2KCvteDKZT/v//oK6N3dAaAM 0r/g== X-Gm-Message-State: APjAAAVFxihwaPeNCs27CmHKZMhY10z+HJPgDzS/02pnubry2cwrjcXr eYfd5GKoWAVM8myDqndysYj2YbKtJUwgIQ== X-Google-Smtp-Source: APXvYqxlUc4QiQxxSQ8zCme1TFKWG7kY48aK2EeqdNKuXJuEG2BMRIs/MkzKc8jKucnlzW5peorfDg== X-Received: by 2002:a81:c249:: with SMTP id t9mr26428274ywg.9.1574186304122; Tue, 19 Nov 2019 09:58:24 -0800 (PST) Received: from ?IPv6:2601:c0:c680:5cc0:154c:f1a3:b13d:a112? ([2601:c0:c680:5cc0:154c:f1a3:b13d:a112]) by smtp.gmail.com with ESMTPSA id x201sm12135984ywx.34.2019.11.19.09.58.22 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Tue, 19 Nov 2019 09:58:23 -0800 (PST) Content-Type: text/plain; charset=utf-8 Mime-Version: 1.0 (Mac OS X Mail 12.4 \(3445.104.11\)) In-Reply-To: Date: Tue, 19 Nov 2019 12:58:22 -0500 Cc: Rowan Tommins Content-Transfer-Encoding: quoted-printable Message-ID: <83307615-4A87-4ACA-B450-3405DD9221D7@newclarity.net> References: <461958fe-182e-59bf-9fdb-b110fd09e2b2@aimeos.com> <08de5448-3c5a-ad32-555e-b8f9579c1337@aimeos.com> <7b527bbb-47e3-9b24-8766-c15e6334c78a@gmail.com> <1BF6C8EC-6DF1-4481-94B2-3A6E7D1312BE@newclarity.net> <2814FAA1-3BEC-47CF-A95E-AE61A33B7308@newclarity.net> To: PHP Internals X-Mailer: Apple Mail (2.3445.104.11) X-Envelope-From: Subject: Re: [PHP-DEV] Concept: "arrayable" pseudo type and \Arrayable interface From: mike@newclarity.net (Mike Schinkel) > On Nov 19, 2019, at 10:54 AM, Rowan Tommins = wrote: > Neither. We should discuss the advantages of the feature, the = potential > costs, and whether other features would be even better. In concept, I agree. =20 But AFAIK no other "better" features were proposed. Do you have an = alternate to propose for __toArray()? I am all ears. > I think that's where this conversation has broken down a bit, which = may be > my fault: I wasn't intending to argue against all the possibilities of = the > feature, only the specific arguments you were raising. We disagree = over > whether (array)$foo would be used more consistently than meaningful = method > names, so maybe we should leave that there, and look at some other = pros and > cons of the feature. I appreciate you elaborating.=20 We can certainly disagree; in both cases it is just our opinion for what = might happen if a new feature is introduced, and neither of us can know = for certain what the potential future holds. That said, which I think you acknowledged, it is a bit of bikeshedding = on both our parts to belabor this one point any longer. > What makes __toString() worthy of a special case in my mind is that = there > are fairly common scenarios where variables are _implicitly_ cast to > string: in double-quoted strings, echo, etc. Having the language be = able to > automatically call a particular method in those situations is = therefore > more valuable. The same can be said for __toBool(), and could be said for any other = data type assuming that the appropriate __toType() were available. Said another way, if __toString() was not in PHP then no implicit = casting would be possible and thus nobody would do it.=20 So there really is no difference; if we had __toArray() and __toBool(), = people could start using them where they would be implicitly cast to = those values. > I think I'd actually be more receptive to a proposal to > allow _all_ casts to be overloaded, rather than adding array as a = second > special case, because *implicitly* casting to array doesn't seem like = it > would be any more common than other types. The feels like "perfect being the enemy of the good" again. If there is anything I have picked up by studying the nature of = enhancements to PHP it is that they are added incrementally at best. = Consider type hinting; we have basic type hinting today but we are just = now getting union types. It would have been ideal to get all typing = needs addressed at once, but if that had been the bar we probably would = still be doing without. Also consider that implementation of _all_ casts would be a heavier lift = than implementing just one today, and then hopefully implementing others = later. And consider that the nature of PHP with its voting means that larger = changes are exponentially harder to get accepted. So for me, rather than argue against a feature because we don't take all = 10 steps at once, I would celebrate moving 1 step at a time in the = positive direction, because we would at least be 1 step ahead of where = we are today. > Yes, I would see that as a better example. I think operator = overloading in > general makes sense when the object itself can be thought of as a > special-case of the primitive it's emulating operators for. So in this > case, the IsSuccessful class would be "a special kind of boolean"; and = the > hypothetical List or Collection classes I mentioned a couple of days = ago > would be "a special kind of array". We even have that in PHP for = built-in > types: GMP objects can now be used with mathematical operators like = $foo * > $bar, and those operations do what you'd expect them to do on an = integer or > float. Exactly! I agree that for general purpose classes the general array = cast is less ideal. But there would really be value in having "cast" magic methods to wrap = built-in data types and then add related methods to them. > Operator overloading can also be used just as a cute way of spelling > something - probably most famously, C++ uses the << and >> operators = for > writing to and reading from streams, even though they're actually = overloads > of the bit-shift operator. Interestingly, I am against general operator overloading, because Ruby = and Rails. Seriously, when operators can be overloaded you can end up with code = that is almost impossible to decipher. But I do not think the same is = true for casting as I tried to illustrate by example. > Overloading of cast operators is no different - the clearest use cases = for > __toString() are where the whole class basically represents a piece of > text, and the more controversial are where (string)$foo is actually a = cute > spelling of one method on a complex class. I fully agree with that. =20 > That's not necessarily a reason to not add a feature - any feature can = be > abused - but it potentially makes it harder for users to understand = each > other's code, and that's a cost we should at least consider. I would like to err on the side of power combined with documentation and = education rather than prohibition.=20 > This is an interesting example. On the one hand, there is only one = array > ever going to be produced by that class; but on the other hand, the > ultimate use of it is explicitly passing to a function that expects a > different type. Assuming the same behaviour as __toString, the code = shown > would give an error under strict_types=3D1, and need changing to > wp_kses((array)$allowed_html) You assume that my proposed __asArray() was not also implemented.=20 However =E2=80=94 per the proposal =E2=80=94 when __asArray() returns = true PHP would treat the object as an array in any context where an = array is expected but still allow methods to be called. > A different interpretation would be that this is the Builder Pattern, = and > the target type happens to be an array rather than an object. So you = might > decide that the consistency you really needed is that all builders = should > have a build() method, and the last line of the example would become: >=20 > $clean_html =3D wp_kses($_POST[ 'content' ] ?? null, > $allowed_html_builder->build()); Totally.=20 But the primary use-case for __toArray() I have identified is to support = patterns that exist in other peoples code =E2=80=94 such as WordPress = core =E2=80=94 where you cannot easily rearchitect the code to be what a = developer thinks they really need; you have to go with what is not what = you want to be. > That doesn't mean the version you wrote is *wrong*, but should make us > consider why one version deserves special treatment by the language = and the > other one doesn't. What other version, and what special treatment is needed? I think I am sensing a pattern in your objections: For you, providing = benefits in one area is to be avoided unless all areas can receive = similar benefits? And when providing all areas with similar benefits = would mean infinite features, you would prefer that no use cases get = improved at all, even if the areas proposed to be improved represent the = ~80 percentile of use-cases? Tell me if I am grasping your objections correctly? -Mike