Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:109640 Return-Path: Delivered-To: mailing list internals@lists.php.net Received: (qmail 51749 invoked from network); 14 Apr 2020 18:54:00 -0000 Received: from unknown (HELO php-smtp4.php.net) (45.112.84.5) by pb1.pair.com with SMTP; 14 Apr 2020 18:54:00 -0000 Received: from php-smtp4.php.net (localhost [127.0.0.1]) by php-smtp4.php.net (Postfix) with ESMTP id 76E0A1804C2 for ; Tue, 14 Apr 2020 10:23:41 -0700 (PDT) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on php-smtp4.php.net X-Spam-Level: X-Spam-Status: No, score=-2.1 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,FREEMAIL_FROM, RCVD_IN_DNSWL_NONE,RCVD_IN_MSPIKE_H2,SPF_HELO_NONE,SPF_PASS autolearn=no autolearn_force=no version=3.4.2 X-Spam-ASN: AS15169 209.85.128.0/17 X-Spam-Virus: No X-Envelope-From: Received: from mail-yb1-f173.google.com (mail-yb1-f173.google.com [209.85.219.173]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by php-smtp4.php.net (Postfix) with ESMTPS for ; Tue, 14 Apr 2020 10:23:40 -0700 (PDT) Received: by mail-yb1-f173.google.com with SMTP id i2so7617816ybk.2 for ; Tue, 14 Apr 2020 10:23:40 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=mime-version:references:in-reply-to:from:date:message-id:subject:to :cc; bh=gGqR9t8BheKCnuDluAZfW4eUyi+wdVKymHCKYp/rYG8=; b=jUkNPvXSkog4ujJymCalPU1m0e6RbAxP7Y5xxHM/TFSFjQ7jJRGlbULPdzjEhIY7C4 LLciqH/jnsgGtbPCzHod9fWkEkdymekv5hNLWE7ozlskWyR0nlr4mcBEqU26w+uQxg9k StbI3KDlH2VC2gYNYggBxN9YPyHamKRiZP93WjuydqUc+ylbV9pknZnGmZfjHh2kNMCD W0H6wrfJrAULhOA1l9LPmD/wK+7bwUEN7AHGW84ahF2tcUzJnpNoOjHolsKQqVEU8wHn S1mF6R+TT11hMo10izlWP0YZJxGtbtT9XHvsAMCwIVDePnD65jk9TrOC3NPF2oLivzIy IJSA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:references:in-reply-to:from:date :message-id:subject:to:cc; bh=gGqR9t8BheKCnuDluAZfW4eUyi+wdVKymHCKYp/rYG8=; b=P5RZyvtQC1cyNrOJVW30K/n4vmQSvoWCRoQJ4iGg/qlTSXHATqAXzFXhUXLsW16IWQ XZoQ21Gy+5w5uASLJ+x3p2ijR9lX1VpOh34hiMVNus3C+1OgXjaumbIKdZX43Ij6KZmz WtHNLrnWIsgW0IBcxptz1JsOycem1nwg5/PKrVb0PCRvwsaiNoPlFhP/Q8qGsyMvXjMZ Wxw/wGwfgJ43i3W61v8fx0RtG3POwcwmla4+V8ZWk0cjqG+h+yvRRWAiYloycJ6cuIUo a2G2n071p7sODpJrH9fgP2+nIvA6+jGwTHgbDYVR6aWmfM0lYyR6llug/iOzWkCkh/fR ZZOg== X-Gm-Message-State: AGi0PuaqBx26AVRf8kMFRbeQWUiFQ9dKlbhg0FyGzSUTpaxKd1HkDaUX eKXyeb2YfsIvxVDSJ9qsybTV/z78wM+iaIZTkCM= X-Google-Smtp-Source: APiQypLIuEAUqU+kBowosiCYywl3PtwRPjS4NWTenWiMY5jMs/px+Cwdbt8tqBWttBTTduTQU9J9q0rBAh3ZTsUniNs= X-Received: by 2002:a25:5f07:: with SMTP id t7mr1615616ybb.411.1586885019237; Tue, 14 Apr 2020 10:23:39 -0700 (PDT) MIME-Version: 1.0 References: <5e94f84b.1c69fb81.8f1da.317bSMTPIN_ADDED_MISSING@mx.google.com> In-Reply-To: <5e94f84b.1c69fb81.8f1da.317bSMTPIN_ADDED_MISSING@mx.google.com> Date: Tue, 14 Apr 2020 19:23:27 +0200 Message-ID: To: Andrea Faulds Cc: PHP internals Content-Type: text/plain; charset="UTF-8" Subject: Re: [PHP-DEV] Re: [DISCUSSION] Match expression From: tovilo.ilija@gmail.com (Ilija Tovilo) Hi Andrea I realize there's a lot of noise in the mailing list right now, I'll keep this my only e-mail for today. > I share others' concern that it is inconsistent with PHP's > existing statements Can you elaborate on what exactly the concerns are? Note that even if we added block expressions to the language there are still certain sanity checks we'd likely need to make, so the differentiation between statement/expression would still not go away. For example: ``` match ($y) { 1 => { echo 'Foo'; echo 'Bar'; // This is fine }, } $x = match ($y) { 1 => { echo 'Foo'; echo 'Bar'; // Error, block must return a value. }, }; ``` At the moment there are very limited use cases for the block expression. The only ones I can think of are the match expression, arrow functions and maybe normal functions. And as that would introduce two ways to return a value from a function it's questionable whether we should even allow that or not. ``` $arrowFn = fn() => { echo 'Foo'; 'Bar' }; // Questionable. You're saving a few characters function getFoo() { echo 'Foo'; $this->foo } ``` > It is a shame you don't suggest taking this opportunity to add > pattern matching. My main concern here is just complexity. There's so much to consider. We need to think well about each pattern, how it should work, what it should look like, how it should be implemented, etc. Furthermore pattern matching usually isn't restricted to the match expression. There's often pattern matching for `if`, `while`, `foreach`, function params, normal assignment, etc. So I don't think it should be mixed with this RFC. IMO if we implement pattern matching we should make it available for all of these cases. ``` let [string $x, 10] = ['foo', 20]; // Error: Unmatched pattern if (let Foo { bar: $bar } = $foo) {} while (let 1..<10 = $x) {} ``` > Using a keyword prefix (e.g. `let`) in future means we end > up with two kinds of arm (one with === behaviour, one with > pattern-matching behaviour), but wouldn't it be simpler to > have just one? I personally don't think so. Consider this case: ``` $x = 10; $y = 20; // This variable is unused match ($x) { $y => { // Always true echo $y; // Outputs 10 }, } ``` `$y` is an identifier pattern and it always matches and assigns the given value to the variable. This is rather confusing. A keyword like `let` would make it more obvious that you're using a pattern. I'd also suspect that it's more common to pass expressions to the lhs of a match statement than patterns so it makes sense that this is the default. Also, imagine you want to equate multiple dynamic values with each other: ``` $x = ...; $y = ...; $z = ...; match ($x) { $y => ..., $z => ..., } // If we only have pattern matching match (true) { true if $x === $y => ..., true if $x === $z => ..., } ``` Without allowing dynamic lhs expressions this becomes pretty awkward. > Relatedly, it is a shame not to have guards I don't think guards are awfully useful without pattern matching. What's the benefit over this? ``` match ($x) { 1 => { if ($foo === BAR) { ... } else { ... } }, } // vs match ($x) { 1 if $foo === 'Bar' => { ... }, 1 => { ... }, } ``` That just makes it harder to generate a jump table. It does reduce nesting a bit but the same could be said for if statements in loops where we don't have guards. > It is unfortunate if we have to add another reserved word My previous draft was mainly criticized because of the usage of the `switch` keyword. Ilija