unofficial mirror of emacs-devel@gnu.org 
 help / color / mirror / code / Atom feed
* The poor state of documentation of pcase like things.
@ 2015-12-16 20:26 Alan Mackenzie
  2015-12-16 20:53 ` Kaushal Modi
                   ` (3 more replies)
  0 siblings, 4 replies; 375+ messages in thread
From: Alan Mackenzie @ 2015-12-16 20:26 UTC (permalink / raw)
  To: emacs-devel

Hello, Emacs.

Months after recognising that the documentation of pcase like things is
in need of vast improvement, we haven't advanced significantly.

We appear to have the following functions/macros: pcase, pcase-let,
pcase-let*, pcase-codegen, pcase-defmacro, pcase-dolist,
pcase-exhaustive, and pcase-lambda.

NONE OF THESE, with the exception of pcase itself, IS EVEN MENTIONED IN
THE ELISP MANUAL.

NONE OF THESE, with the exception of pcase itself, HAS A MEANINGFUL DOC
STRING.

Some of these doc strings are patronising indeed.  They all seem to say,
implicitly, "the author's time is far too valuable to waste in writing
meaningful documentation".

Particularly egregious is the doc string for pcase-exhaustive: "The
exhaustive version of `pcase' (which see).".  Uhh????  Needless to say,
the doc string of pcase makes no mention of "exhaustive".

Let us analyse the documentation of the one macro which is documented to
any meaningful extent, pcase itself:

The article in the Elisp manual for pcase starts well, documenting the
basic form and outlining the basic semantics, but then starts rambling
on like a tutorial, rather than filling in the semantic details.  Here
is a partial list of what is missing from that manual page:

(i) A @dfn{U-PATTERN}.
(ii) A @dfn{Q-PATTERN}.
These two things are described only in terms of their structure, not
what they are conceptually.  What do "U" and "Q" stand for?  What is the
semantic significance of a Q-PATTERN?
(iii) A statement that ` is not ` and , is not ,.
(iv) A rigorous specification of what ` and , (and ,@?) mean in pcase
patterns.
(v) A rigorous specification of when variables get bound, and what they
get bound to.
(vi) A rigorous specification of when a value matches a pattern.

Now, let's have a look a pcase's doc string.  It doesn't say what pcase
does: "perform ML-style pattern matching" is meaningless to anybody who
doesn't know ML-style pattern matching.  What it should say is that the
value is used to select (at most) one of the CASES, and the forms in
that CASE are evaluated - or something like that.

It would appear that Lisp programmers are expected to absorb the
semantics (and sometimes even the syntax) of pcase-* by osmosis:
studying and imitating examples.  This is a Bad Thing.

Most (?all) of the rest of Emacs Lisp is effectively and rigorously
documented.  For example, both the Elisp manual entry and the doc string
for cond are effective.

There are people on this list who are using pcase like things, and so
clearly understand their syntax and semantics.  Could these people
PLEASE document these things, and do so before the release of Emacs
25.1.  Preferably well before.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-16 20:26 The poor state of documentation of pcase like things Alan Mackenzie
@ 2015-12-16 20:53 ` Kaushal Modi
  2015-12-17 16:34   ` John Wiegley
  2015-12-18  0:42   ` John Wiegley
  2015-12-16 21:01 ` Drew Adams
                   ` (2 subsequent siblings)
  3 siblings, 2 replies; 375+ messages in thread
From: Kaushal Modi @ 2015-12-16 20:53 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: Emacs developers

+1

I would welcome a short tutorial on how (and why) to use pcase.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2015-12-16 20:26 The poor state of documentation of pcase like things Alan Mackenzie
  2015-12-16 20:53 ` Kaushal Modi
@ 2015-12-16 21:01 ` Drew Adams
  2015-12-17 13:59 ` Phillip Lord
  2015-12-19 15:26 ` Michael Heerdegen
  3 siblings, 0 replies; 375+ messages in thread
From: Drew Adams @ 2015-12-16 21:01 UTC (permalink / raw)
  To: Alan Mackenzie, emacs-devel

Drive-by implementation?  Too clever by half?

(We don' need no stinkin' doc.  The code is the doc.
Anyone who needs doc is a wimp.  Etc.)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-16 20:26 The poor state of documentation of pcase like things Alan Mackenzie
  2015-12-16 20:53 ` Kaushal Modi
  2015-12-16 21:01 ` Drew Adams
@ 2015-12-17 13:59 ` Phillip Lord
  2015-12-17 17:06   ` Alan Mackenzie
  2015-12-19 15:26 ` Michael Heerdegen
  3 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-17 13:59 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel

Alan Mackenzie <acm@muc.de> writes:
> Some of these doc strings are patronising indeed.  They all seem to say,
> implicitly, "the author's time is far too valuable to waste in writing
> meaningful documentation".

I think it's probably better to make your points (which are reasonable)
without making such aspersions. The author in question has been
extremely generous with their time.


>
> Particularly egregious is the doc string for pcase-exhaustive: "The
> exhaustive version of `pcase' (which see).".  Uhh????  Needless to say,
> the doc string of pcase makes no mention of "exhaustive".
>
> Let us analyse the documentation of the one macro which is documented to
> any meaningful extent, pcase itself:
>
> The article in the Elisp manual for pcase starts well, documenting the
> basic form and outlining the basic semantics, but then starts rambling
> on like a tutorial, rather than filling in the semantic details.  Here
> is a partial list of what is missing from that manual page:
>
> (i) A @dfn{U-PATTERN}.
> (ii) A @dfn{Q-PATTERN}.
> These two things are described only in terms of their structure, not
> what they are conceptually.  What do "U" and "Q" stand for?  What is the
> semantic significance of a Q-PATTERN?


These defined in terms, but unfortunately, the definition is a bit
recursive -- so a Q-PATTERN is defined in terms of other Q-PATTERNs (or
an atom).


> It would appear that Lisp programmers are expected to absorb the
> semantics (and sometimes even the syntax) of pcase-* by osmosis:
> studying and imitating examples.  This is a Bad Thing.


I am not 100% convinced that this is a bad thing. The actual semantics
of pcase do mess your head up a bit. The first part, the tutorial
section, is for me one of the clearest sections. I think it's something
that we should have more off, personally.

> Most (?all) of the rest of Emacs Lisp is effectively and rigorously
> documented.  For example, both the Elisp manual entry and the doc string
> for cond are effective.
>
> There are people on this list who are using pcase like things, and so
> clearly understand their syntax and semantics.  Could these people
> PLEASE document these things, and do so before the release of Emacs
> 25.1.  Preferably well before.

It is indeed worth doing these things.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-16 20:53 ` Kaushal Modi
@ 2015-12-17 16:34   ` John Wiegley
  2015-12-17 19:22     ` Kaushal Modi
                       ` (3 more replies)
  2015-12-18  0:42   ` John Wiegley
  1 sibling, 4 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-17 16:34 UTC (permalink / raw)
  To: Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

>>>>> Kaushal Modi <kaushal.modi@gmail.com> writes:

> I would welcome a short tutorial on how (and why) to use pcase.

There are several examples shown here:

    http://www.emacswiki.org/emacs/PatternMatching

pcase makes a lot more sense if you're used to pattern matching in functional
languages, where you describe a pattern (not unlike destructuring-bind) whose
"shape" is intended to match the set of shapes you want to successful match
against.

Since pattern matching like this isn't something I had ever encountered
outside of FP, I agree that a tutorial is in order. I'm willing to volunteer
for this.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 13:59 ` Phillip Lord
@ 2015-12-17 17:06   ` Alan Mackenzie
  0 siblings, 0 replies; 375+ messages in thread
From: Alan Mackenzie @ 2015-12-17 17:06 UTC (permalink / raw)
  To: Phillip Lord; +Cc: emacs-devel

Hello, Phillip.

On Thu, Dec 17, 2015 at 01:59:56PM +0000, Phillip Lord wrote:
> Alan Mackenzie <acm@muc.de> writes:
> > Some of these doc strings are patronising indeed.  They all seem to say,
> > implicitly, "the author's time is far too valuable to waste in writing
> > meaningful documentation".

> I think it's probably better to make your points (which are reasonable)
> without making such aspersions. The author in question has been
> extremely generous with their time.

I'm aware of this, and I'm not making any such asperesions.  I'm merely
trying to point out how these doc strings will be perceived by users,
should they still be in their current state at the 25.1 release.

[ .... ]

> Phil

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 16:34   ` John Wiegley
@ 2015-12-17 19:22     ` Kaushal Modi
  2015-12-17 21:16     ` Phillip Lord
                       ` (2 subsequent siblings)
  3 siblings, 0 replies; 375+ messages in thread
From: Kaushal Modi @ 2015-12-17 19:22 UTC (permalink / raw)
  To: Kaushal Modi, Alan Mackenzie, Emacs developers

> There are several examples shown here:
>
>     http://www.emacswiki.org/emacs/PatternMatching
>

Thanks John. I have no experience with functional programming and so I
did not understand the "shape" explanation.
But now that I got some clue as to what to look for online, I will do
some digging. I will start with the emacswiki page you pointed.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 16:34   ` John Wiegley
  2015-12-17 19:22     ` Kaushal Modi
@ 2015-12-17 21:16     ` Phillip Lord
  2015-12-17 21:56       ` Drew Adams
  2015-12-18  7:15       ` Eli Zaretskii
  2015-12-17 21:26     ` Alan Mackenzie
  2015-12-19 15:31     ` Michael Heerdegen
  3 siblings, 2 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-17 21:16 UTC (permalink / raw)
  To: Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

John Wiegley <jwiegley@gmail.com> writes:

>>>>>> Kaushal Modi <kaushal.modi@gmail.com> writes:
>
>> I would welcome a short tutorial on how (and why) to use pcase.
>
> There are several examples shown here:
>
>     http://www.emacswiki.org/emacs/PatternMatching
>
> pcase makes a lot more sense if you're used to pattern matching in functional
> languages, where you describe a pattern (not unlike destructuring-bind) whose
> "shape" is intended to match the set of shapes you want to successful match
> against.
>
> Since pattern matching like this isn't something I had ever encountered
> outside of FP, I agree that a tutorial is in order. I'm willing to volunteer
> for this.

I'll have a go at the docstrings.

I only found out about pcase recently. It's a very useful tool, and it
deserves more use. Could I suggest it be promoted in the manual a
little. Currently, it's a subnode of "conditionals", but pattern match
is really a form of control flow in its own right.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 16:34   ` John Wiegley
  2015-12-17 19:22     ` Kaushal Modi
  2015-12-17 21:16     ` Phillip Lord
@ 2015-12-17 21:26     ` Alan Mackenzie
  2015-12-17 23:34       ` John Wiegley
  2015-12-18  7:16       ` Eli Zaretskii
  2015-12-19 15:31     ` Michael Heerdegen
  3 siblings, 2 replies; 375+ messages in thread
From: Alan Mackenzie @ 2015-12-17 21:26 UTC (permalink / raw)
  To: Kaushal Modi, Emacs developers

Hello, John.

On Thu, Dec 17, 2015 at 08:34:27AM -0800, John Wiegley wrote:
> >>>>> Kaushal Modi <kaushal.modi@gmail.com> writes:

> > I would welcome a short tutorial on how (and why) to use pcase.

> There are several examples shown here:

>     http://www.emacswiki.org/emacs/PatternMatching

> pcase makes a lot more sense if you're used to pattern matching in functional
> languages, where you describe a pattern (not unlike destructuring-bind) whose
> "shape" is intended to match the set of shapes you want to successful match
> against.

> Since pattern matching like this isn't something I had ever encountered
> outside of FP, I agree that a tutorial is in order. I'm willing to volunteer
> for this.

An external tutorial is all well and good, and very useful.  But it is
drifting off topic ever so slightly.

That topic is the state of the the documentation about pcase etc.,
_inside_ Emacs, in its doc strings and the Elisp manual.  Can we take it
that that documentation will be fixed before the release of 25.1?

> -- 
> John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
> http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2015-12-17 21:16     ` Phillip Lord
@ 2015-12-17 21:56       ` Drew Adams
  2015-12-17 22:22         ` Phillip Lord
  2015-12-18  7:15       ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Drew Adams @ 2015-12-17 21:56 UTC (permalink / raw)
  To: phillip.lord, Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

> pattern match is really a form of control flow in its own right.

OT, but no, pattern matching per se has nothing to do with control flow.

You can *combine* pattern matching with control flow (as `pcase' does,
testing the results of pattern-match binding to control the flow).  But
pattern matching itself does not imply any effect on control flow.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 21:56       ` Drew Adams
@ 2015-12-17 22:22         ` Phillip Lord
  0 siblings, 0 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-17 22:22 UTC (permalink / raw)
  To: Drew Adams; +Cc: Alan Mackenzie, Emacs developers, Kaushal Modi

Drew Adams <drew.adams@oracle.com> writes:

>> pattern match is really a form of control flow in its own right.
>
> OT, but no, pattern matching per se has nothing to do with control flow.
>
> You can *combine* pattern matching with control flow (as `pcase' does,
> testing the results of pattern-match binding to control the flow).  But
> pattern matching itself does not imply any effect on control flow.

You are right. Currently, only pcase is documented though, hence my
(badly worded) statement.

Possibly the solution is to introduce a generic "pattern matching" node,
and then have much shorter descriptions for pcase in control flow, and
the other functions elsewhere.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 21:26     ` Alan Mackenzie
@ 2015-12-17 23:34       ` John Wiegley
  2015-12-18  7:16       ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-17 23:34 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: Emacs developers, Kaushal Modi

>>>>> Alan Mackenzie <acm@muc.de> writes:

> An external tutorial is all well and good, and very useful. But it is
> drifting off topic ever so slightly.

I was hoping the tutorial would become part of the Elisp manual.

And I agree that we should lift "Pattern Matching" to a higher-level topic.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-16 20:53 ` Kaushal Modi
  2015-12-17 16:34   ` John Wiegley
@ 2015-12-18  0:42   ` John Wiegley
  2015-12-18  4:07     ` Richard Stallman
                       ` (3 more replies)
  1 sibling, 4 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-18  0:42 UTC (permalink / raw)
  To: Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

[-- Attachment #1: Type: text/plain, Size: 10003 bytes --]

>>>>> Kaushal Modi <kaushal.modi@gmail.com> writes:

> I would welcome a short tutorial on how (and why) to use pcase.

The following is a brief pcase tutorial. I welcome any edits and comments.
Also, I wonder if anyone would be willing to hammer this into a form better
suited to the Emacs Lisp manual. I'm not familiar enough with the "language"
of that document at the moment to emulate it, though I could do some reading
next week if no one else is interested in word-smithing.

John

                         Pattern Matching with pcase

All data fits into some kind of pattern. The most explicit pattern is a
description of the data itself. Let's consider the following value as a
running example:

    '(1 2 (4 . 5) "Hello")

# Exact matches

Explicitly stated, this is a list of four elements, where the first two
elements are the integers 1 and 2, the third is a cons consisting of a car of
4 and a cdr of 5, and the fourth is the string "Hello". This states an
explicit pattern that we can match against using an equality test:

    (equal value '(1 2 (4 . 5) "Hello"))

# Pattern matches

Where patterns become useful is when we want to generalize a bit. Let's say we
want to do a similar equality test, but we don't care what the final string's
contents are, only that it's a string. Even though it's simply state, this
becomes quite difficult using an equality test:

    (and (equal (subseq value 0 3) '(1 2 (4 .5)))
         (stringp (nth 3 value)))

What we would prefer is a more direct language for encoding our description of
the *family of values we'd like to match against*. The way we said in English
was: the first three elements exactly so, and the last element, any string.
This is how we'd phrase that using `pcase':

    (pcase value
      (`(1 2 (4 . 5) ,(pred stringp))
        (message "It matched!")))

Think of `pcase' as a form of `cond', where instead of evaluating each test
for non-nil, it compares a series of *patterns* against the value under
consideration (often called the "scrutinee" in the literature). There can be
many patterns, and the first one wins, as with cond.

# Capturing matches

But `pcase' can go one step further: Not only can we compare a candidate value
against a family of possible values described by their pattern, we can also
"capture" sub-values from that pattern for later use. Continuing from the last
example, let's say we want to print the string that match, even though we
didn't care about the contents of the string for the sake of the match:

    (pcase value
      (`(1 2 (4 . 5) ,(and (pred stringp) foo))
        (message "It matched, and the string was %s" foo)))

Whenever a naked symbol like `foo' occurs as a UPattern (see next section),
the part of the value being matched at that position is bound to a local
variable of the same name.

# QPatterns and UPatterns

To master `pcase', there are two types of patterns you must know: UPatterns
and QPatterns. UPatterns are the "logical" aspect of pattern matching, where
we describe the kind of data we'd like to match against, and other special
actions to take when it matches; and QPatterns are the "literal" aspect,
stating the exact form of a particular match.

QPatterns are by far the easiest to think about. To match against any atom,
string, or list of the same, the corresponding QPattern is that exact value.
So the QPattern "foo" matches the string "foo", 1 matches the atom 1, etc.

`pcase' matches against a list of UPatterns, so to use a QPattern, we must
backquote it:

    (pcase value
      (`1 (message "Matched a 1"))
      (`2 (message "Matched a 2"))
      (`"Hello" (message "Matched the string Hello")))

The only special QPattern is the anti-quoting pattern, `,foo`, which allows
you to use UPatterns within QPatterns! The analogy to macro expansion is
direct, so you can think of them similarly.  For example:

    (pcase value
      (`(1 2 ,(or `3 `4))
       (message "Matched either the list (1 2 3) or (1 2 4)")))

# More on UPatterns

There are many special UPatterns, and their variety makes this the hardest
aspect to master. Let's consider them one by one.

## Underscore `_'

To match against anything whatsoever, no matter its type or value, use
underscore. Thus to match against a list containing anything at all at its
head, we'd use:

    (pcase value
      (`(_ 1 2)
       (message "Matched a list of anything followed by (2 3)")))

## Self-quoting

If an atom is self-quoting, we don't need to use backquotes to match against
it. This means that the QPattern `1 is identical to the UPattern 1:

    (pcase value
      (1 (message "Matched a 1"))
      (2 (message "Matched a 2"))
      ("Hello" (message "Matched the string Hello")))

## Symbol

When performing a match, if a symbol occurs within a UPattern, it binds
whatever was found at that position to a local symbol of the same name. Some
examples will help to make this clearer:

    (pcase value
      (`(1 2 ,foo 3)
       (message "Matched 1, 2, something now bound to foo, and 3"))
      (foo
       (message "Match anything at all, and bind it to foo!"))
      (`(,the-car . ,the-cdr))
       (message "Match any cons cell, binding the car and cdr locally"))

The reason for doing this is two-fold: Either to refer to a previous match
later in the pattern (where it is compared using `eq'), or to make use of a
matched value within the related code block:

    (pcase value
      (`(1 2 ,foo ,foo 3)
       (message "Matched (1 2 %s %s 3)" foo)))

## `(or UPAT ...)` and `(and UPAT ...)

We can express boolean logic within a pattern match using the `or` and `and`
Patterns:

    (pcase value
      (`(1 2 ,(or 3 4)
         ,(and (pred stringp)
               (pred (string> "aaa"))
               (pred (lambda (x) (> (length x) 10)))))
       (message "Matched 1, 2, 3 or 4, and a long string "
                "that is lexically greater than 'aaa'")))

## `pred' predicates

Arbitrary predicates can be applied to matched elements, where the predicate
will be passed the object that matched. As in the previous example, lambdas
can be used to form arbitrarily complex predicates, with their own logic.

## guard expressions

At any point within a match, you may assert that something is true by
inserting a guard. This might consult some other variable to confirm the
validity of a pattern at a given time, or it might reference a local symbol
that was earlier bound by the match itself, as described above:

    (pcase value
      (`(1 2 ,foo ,(guard (and (not (numberp foo)) (/= foo 10)))
       (message "Matched 1, 2, anything, and then anything again, "
                "but only if the first anything wasn't the number 10"))))

Note that in this example, the guard occurs at a match position, so even
though the guard doesn't refer to what is being matched, if it passes, then
whatever occurs at that position (the fourth element of the list), would be an
unnamed successful matched. This is rather bad form, so we can be more
explicit about the logic here:

    (pcase value
      (`(1 2 ,(and foo (guard (and (not (numberp foo)) (/= foo 10)))) _)
       (message "Matched 1, 2, anything, and then anything again, "
                "but only if the first anything wasn't the number 10"))))


This means the same, but associates the guard with the value it tests, and
makes it clear that we don't care what the fourth element is, only that it
exists.

## Pattern let bindings

Within a pattern we can match sub-patterns, using a special form of let that
has a meaning specific to `pcase':

    (pcase value
      (`(1 2 ,(and foo (let 3 foo)))
       (message "A weird way of matching (1 2 3)")))

This example is a bit contrived, but it allows us to build up complex guard
patterns that might match against values captured elsewhere in the surrounding
code:

    (pcase value1
      (`(1 2 ,foo)
       (pcase value2
         (`(1 2 ,(and (let (or 3 4) foo) bar))
          (message "A nested pcase depends on the results of the first")))))

Here the third value of `value2' -- which must be a list of exactly three
elements, starting with 1 and 2 -- is being bound to the local variable `bar',
but only if foo was a 3 or 4. There are many other ways this logic could be
expressed, but this gives you a test of how flexibly you can introduce
arbitrary pattern matching of other values within any UPattern.

# `pcase-let' and `pcase-let*'

That's all there is to know about `pcase'! The other two utilities you might
like to use are `pcase-let` and `pcase-let*`, which do similar things to their
UPattern counter-part `let', but as regular Lisp forms:

    (pcase-let ((`(1 2 ,foo) value1)
                (`(3 4 ,bar) value2))
      (message "value1 is a list of (1 2 %s); value2 ends with %s"
               foo bar))

Note that `pcase-let' does not fail, and always executes the correspond forms
unless there is a type error. That is, `value1' above is not required to fit
the form of the match exactly. Rather, every binding that can paired is bound
to its corresponding element, but every binding that cannot is bound to nil:

    (pcase-let ((`(1 2 ,foo) '(10)))
      (message "foo = %s" foo))   => prints "foo = nil"

    (pcase-let ((`(1 2 ,foo) 10))
      (message "foo = %s" foo))   => Lisp error, 10 is not a list

    (pcase-let ((`(1 2 ,foo) '(3 4 10)))
      (message "foo = %s" foo))   => prints "foo = 10"

Thus, `pcase-let' could be thought of as a more expressive form of
`destructuring-bind'.

The `pcase-let*' variant, like `let*', allows you to reference bound local
symbols from prior matches.

    (pcase-let* ((`(1 2 ,foo) '(1 2 3))
                 (`(3 4 ,bar) (list 3 4 foo)))
      (message "foo = %s, bar = %s" foo bar))  => foo = 3, bar = 3

However, if you name a symbol with same name in a later UPattern, it is not
used as an `eq' test, but rather shadows that symbol:

    (pcase-let* ((`(1 2 ,foo) '(1 2 3))
                 (`(3 4 ,foo) '(3 4 5)))
      (message "1 2 %s" foo))

This prints out "1 2 5", rather current match.

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 629 bytes --]

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  0:42   ` John Wiegley
@ 2015-12-18  4:07     ` Richard Stallman
  2015-12-18 10:39       ` Phillip Lord
  2015-12-18  8:55     ` Eli Zaretskii
                       ` (2 subsequent siblings)
  3 siblings, 1 reply; 375+ messages in thread
From: Richard Stallman @ 2015-12-18  4:07 UTC (permalink / raw)
  To: John Wiegley; +Cc: acm, emacs-devel, kaushal.modi

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  > There are many special UPatterns, and their variety makes this the hardest
  > aspect to master. Let's consider them one by one.

  > ## Underscore `_'

  > To match against anything whatsoever, no matter its type or value, use
  > underscore. Thus to match against a list containing anything at all at its
  > head, we'd use:

  >     (pcase value
  >       (`(_ 1 2)
  >        (message "Matched a list of anything followed by (2 3)")))

I don't follow this part.  (_ 1 2) seems to be a QPattern.
Is that right?  So how is it that an element can be a UPattern?

It would help if some of the examples used symbols inside a QPattern,
without comma, so we can see what that does.

-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 21:16     ` Phillip Lord
  2015-12-17 21:56       ` Drew Adams
@ 2015-12-18  7:15       ` Eli Zaretskii
  2015-12-18  9:12         ` Rasmus
                           ` (3 more replies)
  1 sibling, 4 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18  7:15 UTC (permalink / raw)
  To: Phillip Lord; +Cc: acm, emacs-devel, kaushal.modi

> From: phillip.lord@russet.org.uk (Phillip Lord)
> Date: Thu, 17 Dec 2015 21:16:56 +0000
> Cc: Alan Mackenzie <acm@muc.de>, Emacs developers <emacs-devel@gnu.org>
> 
> Could I suggest [pcase] be promoted in the manual a
> little. Currently, it's a subnode of "conditionals", but pattern
> match is really a form of control flow in its own right.

If that's your itch, feel free to scratch it.

IMO, that's largely a waste of your time and energy: the manual is
rarely if ever read in its entirety, or even in large portions.  Most
of its uses is to quickly find the subject whose description you need,
hopefully by using the Info-index command ("i TOPIC RET"), and read
that and perhaps some of the cross-references there.  With this use
case, the level on which a description is found is irrelevant.

Btw, the importance is in the eyes of the beholder.  You look at that
through the glasses of someone who hacks Emacs core.  Try to take the
POV of a casual Lisper who just wants to put some advanced
customizations in her ~/.emacs, for example.  IOW, advanced features
and subjects are frequently very important to power users, but much
less so to "mere mortals".  The manual is supposed to serve both types
of audience.

Bottom line: what we do need is make the description clear and
complete.  Where it appears is orders of magnitude less important.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 21:26     ` Alan Mackenzie
  2015-12-17 23:34       ` John Wiegley
@ 2015-12-18  7:16       ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18  7:16 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel, kaushal.modi

> Date: Thu, 17 Dec 2015 21:26:33 +0000
> From: Alan Mackenzie <acm@muc.de>
> 
> Can we take it that that documentation will be fixed before the
> release of 25.1?

It goes without saying.  I wish more people got involved in this
activity, instead of hacking on master, though.  It would help
releasing Emacs 25.1 earlier.

TIA



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  0:42   ` John Wiegley
  2015-12-18  4:07     ` Richard Stallman
@ 2015-12-18  8:55     ` Eli Zaretskii
  2015-12-19 15:18       ` Michael Heerdegen
  2015-12-19 15:55       ` Michael Heerdegen
  2015-12-19 15:44     ` Michael Heerdegen
  2015-12-24  5:49     ` Richard Stallman
  3 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18  8:55 UTC (permalink / raw)
  To: John Wiegley; +Cc: acm, emacs-devel, kaushal.modi

> From: John Wiegley <jwiegley@gmail.com>
> Date: Thu, 17 Dec 2015 16:42:13 -0800
> Cc: Alan Mackenzie <acm@muc.de>, Emacs developers <emacs-devel@gnu.org>
> 
> >>>>> Kaushal Modi <kaushal.modi@gmail.com> writes:
> 
> > I would welcome a short tutorial on how (and why) to use pcase.
> 
> The following is a brief pcase tutorial. I welcome any edits and comments.

Thanks, please find below a few questions of a naïve reader.

> Also, I wonder if anyone would be willing to hammer this into a form better
> suited to the Emacs Lisp manual.

I could try, but only if I understand this enough to write about it,
and if the description you posted is complete (is it?).  It's hard to
convert tutorials into a manual section otherwise.

> # QPatterns and UPatterns
> 
> To master `pcase', there are two types of patterns you must know: UPatterns
> and QPatterns. UPatterns are the "logical" aspect of pattern matching, where
> we describe the kind of data we'd like to match against, and other special
> actions to take when it matches; and QPatterns are the "literal" aspect,
> stating the exact form of a particular match.

What do "Q" and "U" stand for?  "Quoted" and "Unquoted", something
else?  When introducing terminology that is not English words, you
need to help the reader form a mental model by connecting terms to
words.

> The only special QPattern is the anti-quoting pattern, `,foo`

But the example doesn't use `,foo`, it uses just ,foo.  I guess `..`
here is some markdown-style "quoting", unrelated to the Lisp
backticks?

>     (pcase value
>       (`(1 2 ,(or `3 `4))
>        (message "Matched either the list (1 2 3) or (1 2 4)")))

Do 3 and 4 really have to be quoted here?  Why?

> When performing a match, if a symbol occurs within a UPattern, it binds
> whatever was found at that position to a local symbol of the same name.

"Local symbol" here meaning what? an un-interned symbol or a local
variable by that name?

>     (pcase value
>       (`(1 2 ,foo 3)
>        (message "Matched 1, 2, something now bound to foo, and 3"))
>       (foo
>        (message "Match anything at all, and bind it to foo!"))
>       (`(,the-car . ,the-cdr))
>        (message "Match any cons cell, binding the car and cdr locally"))

So to bind something to 'foo' you just use "foo", but to bind
something to 'the-car' and 'the-cdr' you need to use ",the-car" and
",the-cdr"?  Why the inconsistency?

> The reason for doing this is two-fold: Either to refer to a previous match
> later in the pattern (where it is compared using `eq'), or to make use of a
> matched value within the related code block:
> 
>     (pcase value
>       (`(1 2 ,foo ,foo 3)
>        (message "Matched (1 2 %s %s 3)" foo)))

??? Is "foo" here bound to 2 different values?  And how come the
format has 2 %s, but only one variable, foo, to provide values?

> We can express boolean logic within a pattern match using the `or` and `and`
> Patterns:
> 
>     (pcase value
>       (`(1 2 ,(or 3 4)
>          ,(and (pred stringp)
>                (pred (string> "aaa"))
>                (pred (lambda (x) (> (length x) 10)))))
>        (message "Matched 1, 2, 3 or 4, and a long string "
>                 "that is lexically greater than 'aaa'")))

Why did you use 'lambda' for the 3rd predicate, but not for the 2nd?
Is it just a way to show off use of 'lambda', or is there some
significant difference between these 2 use cases that requires a
'lambda' in the latter case?  More generally, when is 'lambda'
required in a predicate like these ones?

>     (pcase value
>       (`(1 2 ,foo ,(guard (and (not (numberp foo)) (/= foo 10)))
>        (message "Matched 1, 2, anything, and then anything again, "
>                 "but only if the first anything wasn't the number 10"))))

How is using 'guard' here different from using a predicate?

> Note that in this example, the guard occurs at a match position, so even
> though the guard doesn't refer to what is being matched, if it passes, then
> whatever occurs at that position (the fourth element of the list), would be an
> unnamed successful matched.

What is the significance of an "unnamed successful matched"?

> This is rather bad form, so we can be more
> explicit about the logic here:
> 
>     (pcase value
>       (`(1 2 ,(and foo (guard (and (not (numberp foo)) (/= foo 10)))) _)
>        (message "Matched 1, 2, anything, and then anything again, "
>                 "but only if the first anything wasn't the number 10"))))
> 
> 
> This means the same, but associates the guard with the value it tests, and
> makes it clear that we don't care what the fourth element is, only that it
> exists.

Again, how is this different from using a 'pred'?

> 
> ## Pattern let bindings
> 
> Within a pattern we can match sub-patterns, using a special form of let that
> has a meaning specific to `pcase':
> 
>     (pcase value
>       (`(1 2 ,(and foo (let 3 foo)))
>        (message "A weird way of matching (1 2 3)")))
> 
> This example is a bit contrived, but it allows us to build up complex guard
> patterns that might match against values captured elsewhere in the surrounding
> code:
> 
>     (pcase value1
>       (`(1 2 ,foo)
>        (pcase value2
>          (`(1 2 ,(and (let (or 3 4) foo) bar))
>           (message "A nested pcase depends on the results of the first")))))
> 
> Here the third value of `value2' -- which must be a list of exactly three
> elements, starting with 1 and 2 -- is being bound to the local variable `bar',
> but only if foo was a 3 or 4.

Why do you need the 'let' here?  Binding bar to the 3rd element can be
expressed without a 'let', I think.  And why is 'and' needed here?

> That's all there is to know about `pcase'! The other two utilities you might
> like to use are `pcase-let` and `pcase-let*`, which do similar things to their
> UPattern counter-part `let', but as regular Lisp forms:
> 
>     (pcase-let ((`(1 2 ,foo) value1)
>                 (`(3 4 ,bar) value2))
>       (message "value1 is a list of (1 2 %s); value2 ends with %s"
>                foo bar))

Isn't it true that pcase-let is just a short-hand for a pcase that
assigns values according to patterns, and has nil as the default
value?  If that's true, I think it explains better what pcase-let
does, especially when backed up by an example of a pcase and the
equivalent pcase-let.

Looking at the ELisp manual's node "Pattern matching case statement",
it sounds like everything you've described is already covered there,
so perhaps what we need is more examples?

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  7:15       ` Eli Zaretskii
@ 2015-12-18  9:12         ` Rasmus
  2015-12-18  9:21           ` Eli Zaretskii
  2015-12-18 10:30         ` Phillip Lord
                           ` (2 subsequent siblings)
  3 siblings, 1 reply; 375+ messages in thread
From: Rasmus @ 2015-12-18  9:12 UTC (permalink / raw)
  To: emacs-devel


Eli Zaretskii <eliz@gnu.org> writes:

>> Could I suggest [pcase] be promoted in the manual a
>> little. Currently, it's a subnode of "conditionals", but pattern
>> match is really a form of control flow in its own right.
>
> If that's your itch, feel free to scratch it.
>
> IMO, that's largely a waste of your time and energy: the manual is
> rarely if ever read in its entirety, or even in large portions.  Most
> of its uses is to quickly find the subject whose description you need,
> hopefully by using the Info-index command ("i TOPIC RET"), and read
> that and perhaps some of the cross-references there.  With this use
> case, the level on which a description is found is irrelevant.

But by lifting it, it would appear more prominently in the TOC.  This
might cause interest on its own (I’m thinking about the pdf/tex version
here).

Rasmus


-- 
I hear there's rumors on the, uh, Internets. . .




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  9:12         ` Rasmus
@ 2015-12-18  9:21           ` Eli Zaretskii
  2015-12-18  9:57             ` Rasmus
                               ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18  9:21 UTC (permalink / raw)
  To: Rasmus; +Cc: emacs-devel

> From: Rasmus <rasmus@gmx.us>
> Date: Fri, 18 Dec 2015 10:12:00 +0100
> 
> > IMO, that's largely a waste of your time and energy: the manual is
> > rarely if ever read in its entirety, or even in large portions.  Most
> > of its uses is to quickly find the subject whose description you need,
> > hopefully by using the Info-index command ("i TOPIC RET"), and read
> > that and perhaps some of the cross-references there.  With this use
> > case, the level on which a description is found is irrelevant.
> 
> But by lifting it, it would appear more prominently in the TOC.

Only in the printed book, maybe.  The TOC of the Info manual is flat:
all the nodes appear on the same level.  Are printed or PDF manuals
being used a lot these days, in preference to the Info manual?

Besides, did you ever see anyone read the TOC of a large manual?  I
didn't.  I guess someone might do that, but I cannot imagine this
being a frequent use case.

Once again, I won't object to such a change, I just think there are
lots and lots of much more important things that can and should be
done in Emacs development, even in the documentation area.  I'd love
to see the available scarce resource we have applied in those more
important areas, if possible.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  9:21           ` Eli Zaretskii
@ 2015-12-18  9:57             ` Rasmus
  2015-12-18 10:13             ` David Kastrup
  2015-12-18 12:23             ` Marcin Borkowski
  2 siblings, 0 replies; 375+ messages in thread
From: Rasmus @ 2015-12-18  9:57 UTC (permalink / raw)
  To: eliz; +Cc: emacs-devel

Hi,

Eli Zaretskii <eliz@gnu.org> writes:

>> But by lifting it, it would appear more prominently in the TOC.
>
> Only in the printed book, maybe.  The TOC of the Info manual is flat:
> all the nodes appear on the same level.  Are printed or PDF manuals
> being used a lot these days, in preference to the Info manual?

I very much like the pdf manuals.  They are the prettiest.  I also use the
Info and html versions, depending on mode.

> Besides, did you ever see anyone read the TOC of a large manual?  I
> didn't.  I guess someone might do that, but I cannot imagine this
> being a frequent use case.

I do.  I cannot speak for other people.

> Once again, I won't object to such a change, I just think there are
> lots and lots of much more important things that can and should be
> done in Emacs development, even in the documentation area.  I'd love
> to see the available scarce resource we have applied in those more
> important areas, if possible.

I believe you.

Rasmus

-- 
Hvor meget poesi tror De kommer ud af et glas isvand?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  9:21           ` Eli Zaretskii
  2015-12-18  9:57             ` Rasmus
@ 2015-12-18 10:13             ` David Kastrup
  2015-12-18 10:47               ` Eli Zaretskii
  2015-12-18 12:23             ` Marcin Borkowski
  2 siblings, 1 reply; 375+ messages in thread
From: David Kastrup @ 2015-12-18 10:13 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Rasmus, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

>> From: Rasmus <rasmus@gmx.us>
>> Date: Fri, 18 Dec 2015 10:12:00 +0100
>> 
>> > IMO, that's largely a waste of your time and energy: the manual is
>> > rarely if ever read in its entirety, or even in large portions.  Most
>> > of its uses is to quickly find the subject whose description you need,
>> > hopefully by using the Info-index command ("i TOPIC RET"), and read
>> > that and perhaps some of the cross-references there.  With this use
>> > case, the level on which a description is found is irrelevant.
>> 
>> But by lifting it, it would appear more prominently in the TOC.
>
> Only in the printed book, maybe.  The TOC of the Info manual is flat:
> all the nodes appear on the same level.

Are we talking about the same Info manual here?  That of Emacs?  That
with the


     — The Detailed Node Listing —
     ———————————

    Here are some other nodes which are really subnodes of the ones
    already listed, mentioned here so you can get to them in one step:

section?

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  7:15       ` Eli Zaretskii
  2015-12-18  9:12         ` Rasmus
@ 2015-12-18 10:30         ` Phillip Lord
  2015-12-18 12:21         ` Marcin Borkowski
  2015-12-22  5:20         ` John Wiegley
  3 siblings, 0 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-18 10:30 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: acm, kaushal.modi, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

>> From: phillip.lord@russet.org.uk (Phillip Lord)
>> Date: Thu, 17 Dec 2015 21:16:56 +0000
>> Cc: Alan Mackenzie <acm@muc.de>, Emacs developers <emacs-devel@gnu.org>
>> 
>> Could I suggest [pcase] be promoted in the manual a
>> little. Currently, it's a subnode of "conditionals", but pattern
>> match is really a form of control flow in its own right.
>
> If that's your itch, feel free to scratch it.

I was suggesting it for John as he was going to write a tutorial.

> IMO, that's largely a waste of your time and energy: the manual is
> rarely if ever read in its entirety, or even in large portions.  Most
> of its uses is to quickly find the subject whose description you need,
> hopefully by using the Info-index command ("i TOPIC RET"), and read
> that and perhaps some of the cross-references there.  With this use
> case, the level on which a description is found is irrelevant.

It's true. But you have to know to search for something in the first
place. Also, I might well have searched for "destructuring" -- which now
hits the seq.el documentation (implemented with pcase, but not linking
to it).


Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  4:07     ` Richard Stallman
@ 2015-12-18 10:39       ` Phillip Lord
  2015-12-19 15:14         ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-18 10:39 UTC (permalink / raw)
  To: Richard Stallman; +Cc: kaushal.modi, John Wiegley, emacs-devel, acm

Richard Stallman <rms@gnu.org> writes:

> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
> [[[ whether defending the US Constitution against all enemies,     ]]]
> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
>
>   > There are many special UPatterns, and their variety makes this the hardest
>   > aspect to master. Let's consider them one by one.
>
>   > ## Underscore `_'
>
>   > To match against anything whatsoever, no matter its type or value, use
>   > underscore. Thus to match against a list containing anything at all at its
>   > head, we'd use:
>
>   >     (pcase value
>   >       (`(_ 1 2)
>   >        (message "Matched a list of anything followed by (2 3)")))
>
> I don't follow this part.  (_ 1 2) seems to be a QPattern.
> Is that right?  So how is it that an element can be a UPattern?


I think the example is wrong. This....

(pcase '(3 1 2)
   (`(_ 1 2)
   (message "Matched a list of anything followed by (2 3)")))

prints nothing.

while this...

(pcase '(3 1 2)
   (`(,_ 1 2)
   (message "Matched a list of anything followed by (2 3)")))

prints the message (which should be "followed by (2 3)").

I am a bit surprised to find that _ needs , in these examples, and I
think that it's a bug.

I would anyway change it to:

(pcase '(3 1 2)
   (`(,_ 1 2)
      "Matched a list of anything followed by (1 2)"))

As I think it makes the point that `pcase' returns something, as opposed
to working by side effect. I think the example in the manual needs the
same change.

> It would help if some of the examples used symbols inside a QPattern,
> without comma, so we can see what that does.


A symbol IS a QPattern

(pcase '(a b c)
  (`(a b ,x) x))

returns "c".

Phil




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 10:13             ` David Kastrup
@ 2015-12-18 10:47               ` Eli Zaretskii
  2015-12-18 16:44                 ` Phillip Lord
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18 10:47 UTC (permalink / raw)
  To: David Kastrup; +Cc: rasmus, emacs-devel

> From: David Kastrup <dak@gnu.org>
> Cc: Rasmus <rasmus@gmx.us>,  emacs-devel@gnu.org
> Date: Fri, 18 Dec 2015 11:13:18 +0100
> 
> >> But by lifting it, it would appear more prominently in the TOC.
> >
> > Only in the printed book, maybe.  The TOC of the Info manual is flat:
> > all the nodes appear on the same level.
> 
> Are we talking about the same Info manual here?  That of Emacs?  That
> with the
> 
> 
>      — The Detailed Node Listing —
>      ———————————
> 
>     Here are some other nodes which are really subnodes of the ones
>     already listed, mentioned here so you can get to them in one step:
> 
> section?

Yes, and it's flat.

Or maybe we are not using the same English language, and your meaning
of "flat" is different from mine.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  7:15       ` Eli Zaretskii
  2015-12-18  9:12         ` Rasmus
  2015-12-18 10:30         ` Phillip Lord
@ 2015-12-18 12:21         ` Marcin Borkowski
  2015-12-22  5:20         ` John Wiegley
  3 siblings, 0 replies; 375+ messages in thread
From: Marcin Borkowski @ 2015-12-18 12:21 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: kaushal.modi, acm, emacs-devel, Phillip Lord



On 2015-12-18, at 08:15, Eli Zaretskii <eliz@gnu.org> wrote:

>> From: phillip.lord@russet.org.uk (Phillip Lord)
>> Date: Thu, 17 Dec 2015 21:16:56 +0000
>> Cc: Alan Mackenzie <acm@muc.de>, Emacs developers <emacs-devel@gnu.org>
>> 
>> Could I suggest [pcase] be promoted in the manual a
>> little. Currently, it's a subnode of "conditionals", but pattern
>> match is really a form of control flow in its own right.
>
> If that's your itch, feel free to scratch it.
>
> IMO, that's largely a waste of your time and energy: the manual is
> rarely if ever read in its entirety, or even in large portions.  Most

Well, I did read most of it some time ago (15 years?).  Then, I mainly
relied on NEWS, `C-s' and `i' in the manual.

I'd love to read the whole manual again some day - I like it - but it's
soo time-consuming...

> of its uses is to quickly find the subject whose description you need,
> hopefully by using the Info-index command ("i TOPIC RET"), and read
> that and perhaps some of the cross-references there.  With this use
> case, the level on which a description is found is irrelevant.
>
> Btw, the importance is in the eyes of the beholder.  You look at that
> through the glasses of someone who hacks Emacs core.  Try to take the
> POV of a casual Lisper who just wants to put some advanced
> customizations in her ~/.emacs, for example.  IOW, advanced features
> and subjects are frequently very important to power users, but much
> less so to "mere mortals".  The manual is supposed to serve both types
> of audience.
>
> Bottom line: what we do need is make the description clear and
> complete.  Where it appears is orders of magnitude less important.

Agreed.

-- 
Marcin Borkowski
http://octd.wmi.amu.edu.pl/en/Marcin_Borkowski
Faculty of Mathematics and Computer Science
Adam Mickiewicz University



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  9:21           ` Eli Zaretskii
  2015-12-18  9:57             ` Rasmus
  2015-12-18 10:13             ` David Kastrup
@ 2015-12-18 12:23             ` Marcin Borkowski
  2 siblings, 0 replies; 375+ messages in thread
From: Marcin Borkowski @ 2015-12-18 12:23 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Rasmus, emacs-devel



On 2015-12-18, at 10:21, Eli Zaretskii <eliz@gnu.org> wrote:

>> From: Rasmus <rasmus@gmx.us>
>> Date: Fri, 18 Dec 2015 10:12:00 +0100
>> 
>> But by lifting it, it would appear more prominently in the TOC.
>
> Only in the printed book, maybe.  The TOC of the Info manual is flat:
> all the nodes appear on the same level.  Are printed or PDF manuals
> being used a lot these days, in preference to the Info manual?

Yes - a pdf (or html) on an ebook reader.


-- 
Marcin Borkowski
http://octd.wmi.amu.edu.pl/en/Marcin_Borkowski
Faculty of Mathematics and Computer Science
Adam Mickiewicz University



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 10:47               ` Eli Zaretskii
@ 2015-12-18 16:44                 ` Phillip Lord
  2015-12-18 17:17                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-18 16:44 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: David Kastrup, rasmus, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:
>> 
>>      — The Detailed Node Listing —
>>      ———————————
>> 
>>     Here are some other nodes which are really subnodes of the ones
>>     already listed, mentioned here so you can get to them in one step:
>> 
>> section?
>
> Yes, and it's flat.
>
> Or maybe we are not using the same English language, and your meaning
> of "flat" is different from mine.

In the sense that "Conditionals" appears in the detailed node listing,
but that "Pattern Matching" does not.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 16:44                 ` Phillip Lord
@ 2015-12-18 17:17                   ` Eli Zaretskii
  2015-12-18 17:24                     ` David Kastrup
  2015-12-19 11:23                     ` Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18 17:17 UTC (permalink / raw)
  To: Phillip Lord; +Cc: dak, rasmus, emacs-devel

> From: phillip.lord@russet.org.uk (Phillip Lord)
> Cc: David Kastrup <dak@gnu.org>,  <rasmus@gmx.us>,  <emacs-devel@gnu.org>
> Date: Fri, 18 Dec 2015 16:44:56 +0000
> 
> Eli Zaretskii <eliz@gnu.org> writes:
> >> 
> >>      — The Detailed Node Listing —
> >>      ———————————
> >> 
> >>     Here are some other nodes which are really subnodes of the ones
> >>     already listed, mentioned here so you can get to them in one step:
> >> 
> >> section?
> >
> > Yes, and it's flat.
> >
> > Or maybe we are not using the same English language, and your meaning
> > of "flat" is different from mine.
> 
> In the sense that "Conditionals" appears in the detailed node listing,
> but that "Pattern Matching" does not.

That's simply a bug in the manual.  If no one beats me to it, I will
fix it soon.  (Usually, the menu in the Top node gets fixed when all
the documentation issues are done, so technically it's too soon to ask
for that menu to be in perfect order.)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 17:17                   ` Eli Zaretskii
@ 2015-12-18 17:24                     ` David Kastrup
  2015-12-18 18:47                       ` Eli Zaretskii
  2015-12-19 11:23                     ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: David Kastrup @ 2015-12-18 17:24 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel, rasmus, Phillip Lord

Eli Zaretskii <eliz@gnu.org> writes:

>> From: phillip.lord@russet.org.uk (Phillip Lord)
>> Cc: David Kastrup <dak@gnu.org>,  <rasmus@gmx.us>,  <emacs-devel@gnu.org>
>> Date: Fri, 18 Dec 2015 16:44:56 +0000
>> 
>> Eli Zaretskii <eliz@gnu.org> writes:
>> >> 
>> >>      — The Detailed Node Listing —
>> >>      ———————————
>> >> 
>> >>     Here are some other nodes which are really subnodes of the ones
>> >>     already listed, mentioned here so you can get to them in one step:
>> >> 
>> >> section?
>> >
>> > Yes, and it's flat.
>> >
>> > Or maybe we are not using the same English language, and your meaning
>> > of "flat" is different from mine.
>> 
>> In the sense that "Conditionals" appears in the detailed node listing,
>> but that "Pattern Matching" does not.
>
> That's simply a bug in the manual.  If no one beats me to it, I will
> fix it soon.

As much fun as proving me wrong must be, that seems excessive.  I'm
likely not alone in the belief that the "Detailed Node Listing" is an
intentional addition rather than the outcome of a bug.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 17:24                     ` David Kastrup
@ 2015-12-18 18:47                       ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-18 18:47 UTC (permalink / raw)
  To: David Kastrup; +Cc: emacs-devel, rasmus, phillip.lord

> From: David Kastrup <dak@gnu.org>
> Cc: phillip.lord@russet.org.uk (Phillip Lord),  rasmus@gmx.us,  emacs-devel@gnu.org
> Date: Fri, 18 Dec 2015 18:24:40 +0100
> 
> > That's simply a bug in the manual.  If no one beats me to it, I will
> > fix it soon.
> 
> As much fun as proving me wrong must be, that seems excessive.  I'm
> likely not alone in the belief that the "Detailed Node Listing" is an
> intentional addition rather than the outcome of a bug.

Way over my head.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 17:17                   ` Eli Zaretskii
  2015-12-18 17:24                     ` David Kastrup
@ 2015-12-19 11:23                     ` Eli Zaretskii
  2015-12-19 11:39                       ` David Kastrup
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 11:23 UTC (permalink / raw)
  To: phillip.lord; +Cc: dak, rasmus, emacs-devel

> Date: Fri, 18 Dec 2015 19:17:32 +0200
> From: Eli Zaretskii <eliz@gnu.org>
> Cc: dak@gnu.org, rasmus@gmx.us, emacs-devel@gnu.org
> 
> > From: phillip.lord@russet.org.uk (Phillip Lord)
> > Cc: David Kastrup <dak@gnu.org>,  <rasmus@gmx.us>,  <emacs-devel@gnu.org>
> > Date: Fri, 18 Dec 2015 16:44:56 +0000
> > 
> > Eli Zaretskii <eliz@gnu.org> writes:
> > >> 
> > >>      — The Detailed Node Listing —
> > >>      ———————————
> > >> 
> > >>     Here are some other nodes which are really subnodes of the ones
> > >>     already listed, mentioned here so you can get to them in one step:
> > >> 
> > >> section?
> > >
> > > Yes, and it's flat.
> > >
> > > Or maybe we are not using the same English language, and your meaning
> > > of "flat" is different from mine.
> > 
> > In the sense that "Conditionals" appears in the detailed node listing,
> > but that "Pattern Matching" does not.
> 
> That's simply a bug in the manual.  If no one beats me to it, I will
> fix it soon.

Done.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 11:23                     ` Eli Zaretskii
@ 2015-12-19 11:39                       ` David Kastrup
  2015-12-19 12:15                         ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: David Kastrup @ 2015-12-19 11:39 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel, rasmus, phillip.lord

Eli Zaretskii <eliz@gnu.org> writes:

>> Date: Fri, 18 Dec 2015 19:17:32 +0200
>> From: Eli Zaretskii <eliz@gnu.org>
>> Cc: dak@gnu.org, rasmus@gmx.us, emacs-devel@gnu.org
>> 
>> > From: phillip.lord@russet.org.uk (Phillip Lord)
>> > Cc: David Kastrup <dak@gnu.org>,  <rasmus@gmx.us>,  <emacs-devel@gnu.org>
>> > Date: Fri, 18 Dec 2015 16:44:56 +0000
>> > 
>> > Eli Zaretskii <eliz@gnu.org> writes:
>> > >> 
>> > >>      — The Detailed Node Listing —
>> > >>      ———————————
>> > >> 
>> > >>     Here are some other nodes which are really subnodes of the ones
>> > >>     already listed, mentioned here so you can get to them in one step:
>> > >> 
>> > >> section?
>> > >
>> > > Yes, and it's flat.
>> > >
>> > > Or maybe we are not using the same English language, and your meaning
>> > > of "flat" is different from mine.
>> > 
>> > In the sense that "Conditionals" appears in the detailed node listing,
>> > but that "Pattern Matching" does not.
>> 
>> That's simply a bug in the manual.  If no one beats me to it, I will
>> fix it soon.
>
> Done.

The Detailed Node listing now reads

    Control Structures

    * Sequencing::              Evaluation in textual order.
    * Conditionals::            @code{if}, @code{cond}, @code{when}, @code{unless}.
    * Combining Conditions::    @code{and}, @code{or}, @code{not}.
    * Iteration::               @code{while} loops.
    * Generators::              Generic sequences and coroutines.
    * Nonlocal Exits::          Jumping out of a sequence.

    Conditionals

    * Pattern matching case statement::  How to use @code{pcase}.

    Nonlocal Exits

    * Catch and Throw::         Nonlocal exits for the program's own purposes.
    * Examples of Catch::       Showing how such nonlocal exits can be written.
    * Errors::                  How errors are signaled and handled.
    * Cleanups::                Arranging to run a cleanup form if an

Note that "Conditionals" now appears twice: as a proper node name and as
a newly added section containing only "pcase" and nothing else.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 11:39                       ` David Kastrup
@ 2015-12-19 12:15                         ` Eli Zaretskii
  2015-12-19 20:35                           ` Phillip Lord
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 12:15 UTC (permalink / raw)
  To: David Kastrup; +Cc: emacs-devel, rasmus, phillip.lord

> From: David Kastrup <dak@gnu.org>
> Cc: phillip.lord@russet.org.uk,  rasmus@gmx.us,  emacs-devel@gnu.org
> Date: Sat, 19 Dec 2015 12:39:22 +0100
> 
> The Detailed Node listing now reads
> 
>     Control Structures
> 
>     * Sequencing::              Evaluation in textual order.
>     * Conditionals::            @code{if}, @code{cond}, @code{when}, @code{unless}.
>     * Combining Conditions::    @code{and}, @code{or}, @code{not}.
>     * Iteration::               @code{while} loops.
>     * Generators::              Generic sequences and coroutines.
>     * Nonlocal Exits::          Jumping out of a sequence.
> 
>     Conditionals
> 
>     * Pattern matching case statement::  How to use @code{pcase}.
> 
>     Nonlocal Exits
> 
>     * Catch and Throw::         Nonlocal exits for the program's own purposes.
>     * Examples of Catch::       Showing how such nonlocal exits can be written.
>     * Errors::                  How errors are signaled and handled.
>     * Cleanups::                Arranging to run a cleanup form if an
> 
> Note that "Conditionals" now appears twice: as a proper node name and as
> a newly added section containing only "pcase" and nothing else.

Yes, and that is a problem because...?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18 10:39       ` Phillip Lord
@ 2015-12-19 15:14         ` Michael Heerdegen
  2015-12-19 19:23           ` Phillip Lord
  2015-12-19 19:24           ` Phillip Lord
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 15:14 UTC (permalink / raw)
  To: emacs-devel

phillip.lord@russet.org.uk (Phillip Lord) writes:

> (pcase '(3 1 2)
>    (`(_ 1 2)
>    (message "Matched a list of anything followed by (2 3)")))
>
> prints nothing.
>
> while this...
>
> (pcase '(3 1 2)
>    (`(,_ 1 2)
>    (message "Matched a list of anything followed by (2 3)")))
>
> prints the message (which should be "followed by (2 3)").
>
> I am a bit surprised to find that _ needs , in these examples, and I
> think that it's a bug.

I think it's intentional, and it fits the documentation.

We think of elements in a backquoted list to be all quoted unless
explicitly unquoted.  It makes no sense that '_ matches any expression.
It matches only the symbol _, and that can be useful, too.


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  8:55     ` Eli Zaretskii
@ 2015-12-19 15:18       ` Michael Heerdegen
  2015-12-22  5:22         ` John Wiegley
  2015-12-19 15:55       ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 15:18 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: kaushal.modi, John Wiegley, emacs-devel, acm

Eli Zaretskii <eliz@gnu.org> writes:

> >     (pcase value
> >       (`(1 2 ,(or `3 `4))
> >        (message "Matched either the list (1 2 3) or (1 2 4)")))
>
> Do 3 and 4 really have to be quoted here?  Why?

Of course not!  The form after the `unquote' is a "normal" pcase
pattern.  Numbers count as atoms matching themselves. 


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-16 20:26 The poor state of documentation of pcase like things Alan Mackenzie
                   ` (2 preceding siblings ...)
  2015-12-17 13:59 ` Phillip Lord
@ 2015-12-19 15:26 ` Michael Heerdegen
  2015-12-19 16:04   ` Michael Heerdegen
                     ` (2 more replies)
  3 siblings, 3 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 15:26 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel

Alan Mackenzie <acm@muc.de> writes:

> Hello, Emacs.

Hello.  (no, I'm not Emacs)

> Months after recognising that the documentation of pcase like things
> is in need of vast improvement, we haven't advanced significantly.

I wished you had not raised this issue so shortly before Christmas.

> We appear to have the following functions/macros: pcase, pcase-let,
> pcase-let*, pcase-codegen, pcase-defmacro, pcase-dolist,
> pcase-exhaustive, and pcase-lambda.
>
> NONE OF THESE, with the exception of pcase itself, IS EVEN MENTIONED IN
> THE ELISP MANUAL.
>
> NONE OF THESE, with the exception of pcase itself, HAS A MEANINGFUL DOC
> STRING.
>
> Some of these doc strings are patronising indeed.  They all seem to say,
> implicitly, "the author's time is far too valuable to waste in writing
> meaningful documentation".

As far as I understand how Stefan used to work, most of the semantics of
most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
we are not yet sure how useful we are, or if they may later be better be
replaced by other forms that are more general, etc.

IMHO it's good to leave the documentation of the derivatives as is for
now.

>  What do "U" and "Q" stand for?

> There are people on this list who are using pcase like things, and so
> clearly understand their syntax and semantics.  Could these people
> PLEASE document these things, and do so before the release of Emacs
> 25.1.  Preferably well before.

To be honest, I tweaked some of the pcase related documentation, and was
quite happy with it.  I think the pcase docstring is quite good.  A
tutorial is missing though, clearly.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-17 16:34   ` John Wiegley
                       ` (2 preceding siblings ...)
  2015-12-17 21:26     ` Alan Mackenzie
@ 2015-12-19 15:31     ` Michael Heerdegen
  2015-12-22  5:25       ` John Wiegley
  3 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 15:31 UTC (permalink / raw)
  To: Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

[-- Attachment #1: Type: text/plain, Size: 377 bytes --]

John Wiegley <jwiegley@gmail.com> writes:

> Since pattern matching like this isn't something I had ever encountered
> outside of FP, I agree that a tutorial is in order. I'm willing to
> volunteer
> for this.

I had already posted a tutorial here some time ago.  Sorry, my fault, I
did not yet find the time to further improve it and work in the
comments.

Here it is again:


[-- Attachment #2: pcase-guide.el --]
[-- Type: application/emacs-lisp, Size: 12100 bytes --]

[-- Attachment #3: Type: text/plain, Size: 219 bytes --]


I'm very much willing to help with a different tutorial, prove-read your
stuff and improved docs etc. but don't have so much time before
Christmas.

Do we have the time to do this after Christmas?


Regards,

Michael.

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  0:42   ` John Wiegley
  2015-12-18  4:07     ` Richard Stallman
  2015-12-18  8:55     ` Eli Zaretskii
@ 2015-12-19 15:44     ` Michael Heerdegen
  2015-12-19 17:02       ` Eli Zaretskii
  2015-12-19 20:31       ` Phillip Lord
  2015-12-24  5:49     ` Richard Stallman
  3 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 15:44 UTC (permalink / raw)
  To: Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

John Wiegley <jwiegley@gmail.com> writes:

> # QPatterns and UPatterns
>
> To master `pcase', there are two types of patterns you must know: UPatterns
> and QPatterns. UPatterns are the "logical" aspect of pattern matching, where
> we describe the kind of data we'd like to match against, and other special
> actions to take when it matches; and QPatterns are the "literal" aspect,
> stating the exact form of a particular match.

I think we should not emphasize QPatterns and UPatterns too much,
because today, ``' is just a pcase macro.  When not using ``' is pcase,
we speak of just PATTERNs.

> QPatterns are by far the easiest to think about. To match against any atom,
> string, or list of the same, the corresponding QPattern is that exact value.
> So the QPattern "foo" matches the string "foo", 1 matches the atom 1,
> etc.

Note that atoms are compared with `equal', so "foo" matches any string
"foo", for example.

> `pcase' matches against a list of UPatterns, so to use a QPattern, we must
> backquote it:
>
>     (pcase value
>       (`1 (message "Matched a 1"))
>       (`2 (message "Matched a 2"))
>       (`"Hello" (message "Matched the string Hello")))

We used to write it like that in the old times.  Today, we better quote
stuff at toplevel with quote: `''.

>     (pcase value
>       (`(_ 1 2)
>        (message "Matched a list of anything followed by (2 3)")))

The example is wrong, as already had been mentioned.


Just had a very quick look.


To sum up, I don't think that basing the tutorial on the difference of
qpatterns and upatterns is a good idea.  Destructuring is only one
specific aspect of pcase.  And there are even different means of
destructuring now, namely seq and map.

If there are still examples like

>     (pcase value
>       (`1 (message "Matched a 1"))
>       (`2 (message "Matched a 2"))
>       (`"Hello" (message "Matched the string Hello")))

in the info manual, they should be changed to not use backquote.


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  8:55     ` Eli Zaretskii
  2015-12-19 15:18       ` Michael Heerdegen
@ 2015-12-19 15:55       ` Michael Heerdegen
  2015-12-19 17:08         ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 15:55 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: kaushal.modi, John Wiegley, emacs-devel, acm

Eli Zaretskii <eliz@gnu.org> writes:

> But the example doesn't use `,foo`, it uses just ,foo.  I guess `..`
> here is some markdown-style "quoting", unrelated to the Lisp
> backticks?

Yes.

> "Local symbol" here meaning what? an un-interned symbol or a local
> variable by that name?

It binds to the symbol specified.  The type of binding is local.

> >     (pcase value
> >       (`(1 2 ,foo 3)
> >        (message "Matched 1, 2, something now bound to foo, and 3"))
> >       (foo
> >        (message "Match anything at all, and bind it to foo!"))
> >       (`(,the-car . ,the-cdr))
> >        (message "Match any cons cell, binding the car and cdr locally"))
>
> So to bind something to 'foo' you just use "foo", but to bind
> something to 'the-car' and 'the-cdr' you need to use ",the-car" and
> ",the-cdr"?  Why the inconsistency?

The examples only differ because some symbols occur inside backquote and
others don't.


> > The reason for doing this is two-fold: Either to refer to a previous match
> > later in the pattern (where it is compared using `eq'), or to make use of a
> > matched value within the related code block:
> > 
> >     (pcase value
> >       (`(1 2 ,foo ,foo 3)
> >        (message "Matched (1 2 %s %s 3)" foo)))
>
> ??? Is "foo" here bound to 2 different values?  And how come the
> format has 2 %s, but only one variable, foo, to provide values?

The second occurrence is turned into an equivalence test (the pcase
docstring does already say that).  The message call is invalid.


> > We can express boolean logic within a pattern match using the `or` and `and`
> > Patterns:
> > 
> >     (pcase value
> >       (`(1 2 ,(or 3 4)
> >          ,(and (pred stringp)
> >                (pred (string> "aaa"))
> >                (pred (lambda (x) (> (length x) 10)))))
> >        (message "Matched 1, 2, 3 or 4, and a long string "
> >                 "that is lexically greater than 'aaa'")))
>
> Why did you use 'lambda' for the 3rd predicate, but not for the 2nd?
> Is it just a way to show off use of 'lambda', or is there some
> significant difference between these 2 use cases that requires a
> 'lambda' in the latter case?  More generally, when is 'lambda'
> required in a predicate like these ones?

That's explained in the pcase docstring.

> Isn't it true that pcase-let is just a short-hand for a pcase that
> assigns values according to patterns, and has nil as the default
> value?  If that's true, I think it explains better what pcase-let
> does, especially when backed up by an example of a pcase and the
> equivalent pcase-let.

I think there are more differences, AFAICT pcase-let can't "fail", and
it can bind multiple value--pattern pairs.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:26 ` Michael Heerdegen
@ 2015-12-19 16:04   ` Michael Heerdegen
  2015-12-19 19:29     ` Phillip Lord
  2015-12-19 16:47   ` Eli Zaretskii
  2015-12-19 18:30   ` Alan Mackenzie
  2 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 16:04 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> As far as I understand how Stefan used to work, most of the semantics of
> most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
> we are not yet sure how useful we are, or if they may later be better be
> replaced by other forms that are more general, etc.

BTW1, there is also a

 (not PATTERN)

pattern form that already works but is not yet optimized, thus fully
undocumented.


BTW2, I discussed with Stefan the semantics of a `pcase-setq', and how
it could be connected with generalized variables.


BTW3, we were not yet all agreed how the semantics of `pcase-dolist'
should be when the pattern doesn't match (currently, AFAIK, it loops
nonetheless).  Similarly for pcase-let and pcase-lambda.  For some of
these forms, we do not yet know how useful they are.

Just some examples of open questions that shows that some stuff is still
a bit of work in progress.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:26 ` Michael Heerdegen
  2015-12-19 16:04   ` Michael Heerdegen
@ 2015-12-19 16:47   ` Eli Zaretskii
  2015-12-19 17:24     ` Michael Heerdegen
  2015-12-22  5:25     ` John Wiegley
  2015-12-19 18:30   ` Alan Mackenzie
  2 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 16:47 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: acm, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Date: Sat, 19 Dec 2015 16:26:52 +0100
> Cc: emacs-devel@gnu.org
> 
> As far as I understand how Stefan used to work, most of the semantics of
> most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
> we are not yet sure how useful we are, or if they may later be better be
> replaced by other forms that are more general, etc.
> 
> IMHO it's good to leave the documentation of the derivatives as is for
> now.

Grepping for "pcase-let" brings about 90 hits (including pcase-let*),
so leaving that undocumented is no longer an option, IMO.

> To be honest, I tweaked some of the pcase related documentation, and was
> quite happy with it.  I think the pcase docstring is quite good.

Thank you for your efforts.

> A tutorial is missing though, clearly.

Tutorials are always good to have, but they cannot replace good
documentation in the manual.  We should strive to provide manuals that
are self-contained and don't require any tutorial reading for
acquiring a full understanding of an issue and an unimpeded capability
of using it in Lisp programs.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:44     ` Michael Heerdegen
@ 2015-12-19 17:02       ` Eli Zaretskii
  2015-12-19 20:58         ` Michael Heerdegen
  2015-12-22  5:28         ` John Wiegley
  2015-12-19 20:31       ` Phillip Lord
  1 sibling, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 17:02 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: acm, emacs-devel, kaushal.modi

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Date: Sat, 19 Dec 2015 16:44:34 +0100
> Cc: Alan Mackenzie <acm@muc.de>, Emacs developers <emacs-devel@gnu.org>
> 
> John Wiegley <jwiegley@gmail.com> writes:
> 
> I think we should not emphasize QPatterns and UPatterns too much,
> because today, ``' is just a pcase macro.  When not using ``' is pcase,
> we speak of just PATTERNs.

If we want to do that, we need to rewrite both the ELisp manual and
the doc string to never use these.  With the current text of the
manual, you simply cannot ignore them.  (Personally, I think trying to
stop using them is futile, since so many people who actively use
'pcase' use these terms freely in their messages and other text they
write.  But that's me.)

> If there are still examples like
> 
> >     (pcase value
> >       (`1 (message "Matched a 1"))
> >       (`2 (message "Matched a 2"))
> >       (`"Hello" (message "Matched the string Hello")))
> 
> in the info manual, they should be changed to not use backquote.

There are quite a few of these there.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:55       ` Michael Heerdegen
@ 2015-12-19 17:08         ` Eli Zaretskii
  2015-12-19 17:19           ` Eli Zaretskii
  2015-12-19 17:40           ` Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 17:08 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: kaushal.modi, jwiegley, emacs-devel, acm

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: John Wiegley <jwiegley@gmail.com>,  acm@muc.de,  emacs-devel@gnu.org,  kaushal.modi@gmail.com
> Date: Sat, 19 Dec 2015 16:55:12 +0100
> 
> > >     (pcase value
> > >       (`(1 2 ,foo 3)
> > >        (message "Matched 1, 2, something now bound to foo, and 3"))
> > >       (foo
> > >        (message "Match anything at all, and bind it to foo!"))
> > >       (`(,the-car . ,the-cdr))
> > >        (message "Match any cons cell, binding the car and cdr locally"))
> >
> > So to bind something to 'foo' you just use "foo", but to bind
> > something to 'the-car' and 'the-cdr' you need to use ",the-car" and
> > ",the-cdr"?  Why the inconsistency?
> 
> The examples only differ because some symbols occur inside backquote and
> others don't.

",foo" in the first pattern is also inside a backquote, but it is
still different from "foo" in the second pattern and ",the-car" in the
third.  So I'm still not out of the woods regarding the inconsistency.

> > >     (pcase value
> > >       (`(1 2 ,(or 3 4)
> > >          ,(and (pred stringp)
> > >                (pred (string> "aaa"))
> > >                (pred (lambda (x) (> (length x) 10)))))
> > >        (message "Matched 1, 2, 3 or 4, and a long string "
> > >                 "that is lexically greater than 'aaa'")))
> >
> > Why did you use 'lambda' for the 3rd predicate, but not for the 2nd?
> > Is it just a way to show off use of 'lambda', or is there some
> > significant difference between these 2 use cases that requires a
> > 'lambda' in the latter case?  More generally, when is 'lambda'
> > required in a predicate like these ones?
> 
> That's explained in the pcase docstring.

Which part of it?

> > Isn't it true that pcase-let is just a short-hand for a pcase that
> > assigns values according to patterns, and has nil as the default
> > value?  If that's true, I think it explains better what pcase-let
> > does, especially when backed up by an example of a pcase and the
> > equivalent pcase-let.
> 
> I think there are more differences, AFAICT pcase-let can't "fail"

Neither can a pcase that has a default clause, right?

> and it can bind multiple value--pattern pairs.

Did John's tutorial include an example of that?

Or maybe I shouldn't ask about pcase-let, as it's not for the
uninitiated yet? ;-)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 17:08         ` Eli Zaretskii
@ 2015-12-19 17:19           ` Eli Zaretskii
  2015-12-19 21:03             ` Michael Heerdegen
  2015-12-19 17:40           ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 17:19 UTC (permalink / raw)
  To: michael_heerdegen; +Cc: jwiegley, emacs-devel, acm, kaushal.modi

> Date: Sat, 19 Dec 2015 19:08:18 +0200
> From: Eli Zaretskii <eliz@gnu.org>
> Cc: kaushal.modi@gmail.com, jwiegley@gmail.com, emacs-devel@gnu.org, acm@muc.de
> > > >     (pcase value
> > > >       (`(1 2 ,foo 3)
> > > >        (message "Matched 1, 2, something now bound to foo, and 3"))
> > > >       (foo
> > > >        (message "Match anything at all, and bind it to foo!"))
> > > >       (`(,the-car . ,the-cdr))
> > > >        (message "Match any cons cell, binding the car and cdr locally"))
> > >
> > > So to bind something to 'foo' you just use "foo", but to bind
> > > something to 'the-car' and 'the-cdr' you need to use ",the-car" and
> > > ",the-cdr"?  Why the inconsistency?
> > 
> > The examples only differ because some symbols occur inside backquote and
> > others don't.
> 
> ",foo" in the first pattern is also inside a backquote, but it is
> still different from "foo" in the second pattern and ",the-car" in the
> third.  So I'm still not out of the woods regarding the inconsistency.

(Time passes...)  Ah, I see: I was confused by John's different style:
"now bound to foo" vs "bind it to foo".  These actually intend to say
the same thing: "match anything and bind it to foo", but the former
wording made it sound like it was already bound to foo before, i.e. as
if the first pattern _uses_ the existing binding of foo, instead of
binding foo.

Silly me, trying to assign too much importance to the wording.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 16:47   ` Eli Zaretskii
@ 2015-12-19 17:24     ` Michael Heerdegen
  2015-12-22  5:25     ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 17:24 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: acm, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > A tutorial is missing though, clearly.
>
> Tutorials are always good to have, but they cannot replace good
> documentation in the manual.  We should strive to provide manuals that
> are self-contained and don't require any tutorial reading for
> acquiring a full understanding of an issue and an unimpeded capability
> of using it in Lisp programs.

I agree.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 17:08         ` Eli Zaretskii
  2015-12-19 17:19           ` Eli Zaretskii
@ 2015-12-19 17:40           ` Michael Heerdegen
  2015-12-22  5:21             ` John Wiegley
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 17:40 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: kaushal.modi, jwiegley, emacs-devel, acm

Eli Zaretskii <eliz@gnu.org> writes:

> > > Why did you use 'lambda' for the 3rd predicate, but not for the 2nd?
> > > Is it just a way to show off use of 'lambda', or is there some
> > > significant difference between these 2 use cases that requires a
> > > 'lambda' in the latter case?  More generally, when is 'lambda'
> > > required in a predicate like these ones?
> > 
> > That's explained in the pcase docstring.
>
> Which part of it?

  (pred FUN)	matches if FUN applied to the object returns non-nil.

[...]

FUN can take the form
  SYMBOL or (lambda ARGS BODY)  in which case it’s called with one argument.
  (F ARG1 .. ARGn) in which case F gets called with an n+1’th argument
                        which is the value being matched.

So, FUN is generally a symbol or a lambda, as everywhere, nothing
special.  In addition there is a 

  (F ARG1 .. ARGn)

("in which case F gets called with an n+1’th argument which is the value
being matched.")

form that can be used to abbreviate things in some cases.  Probably you
got confused with this additional possible syntax.

> > > Isn't it true that pcase-let is just a short-hand for a pcase that
> > > assigns values according to patterns, and has nil as the default
> > > value?  If that's true, I think it explains better what pcase-let
> > > does, especially when backed up by an example of a pcase and the
> > > equivalent pcase-let.
> > 
> > I think there are more differences, AFAICT pcase-let can't "fail"
>
> Neither can a pcase that has a default clause, right?

Yes - but `pcase-let' never fails AFAIR, no matter how the clauses look
like.

> Did John's tutorial include an example of that?

Haven't looked yet.

> Or maybe I shouldn't ask about pcase-let, as it's not for the
> uninitiated yet? ;-)

I don't expect the semantics of `pcase-let' to change much in the
future, and I think it's quite unquestioned that it's useful and a
good-to-have form per se.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:26 ` Michael Heerdegen
  2015-12-19 16:04   ` Michael Heerdegen
  2015-12-19 16:47   ` Eli Zaretskii
@ 2015-12-19 18:30   ` Alan Mackenzie
  2015-12-19 20:42     ` Michael Heerdegen
  2 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2015-12-19 18:30 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

Hello, Michael.

On Sat, Dec 19, 2015 at 04:26:52PM +0100, Michael Heerdegen wrote:
> Alan Mackenzie <acm@muc.de> writes:

> > Months after recognising that the documentation of pcase like things
> > is in need of vast improvement, we haven't advanced significantly.

> I wished you had not raised this issue so shortly before Christmas.

My level of frustration and annoyance is steadily rising despite the
imminence of Yuletide.  I wish you a happy one, though.

> > We appear to have the following functions/macros: pcase, pcase-let,
> > pcase-let*, pcase-codegen, pcase-defmacro, pcase-dolist,
> > pcase-exhaustive, and pcase-lambda.

> > NONE OF THESE, with the exception of pcase itself, IS EVEN MENTIONED IN
> > THE ELISP MANUAL.

> > NONE OF THESE, with the exception of pcase itself, HAS A MEANINGFUL DOC
> > STRING.

> > Some of these doc strings are patronising indeed.  They all seem to say,
> > implicitly, "the author's time is far too valuable to waste in writing
> > meaningful documentation".

> As far as I understand how Stefan used to work, most of the semantics of
> most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
> we are not yet sure how useful we are, or if they may later be better be
> replaced by other forms that are more general, etc.

Yet the said functions have been committed on the release branch and are
already in widespread use throughout the Emacs sources.  As Eli notes,
there're around 90 uses of pcase-let and pcase-let*.  I count 18
occurrences of pcase-dolist outside of pcase.el.  And so on.

> IMHO it's good to leave the documentation of the derivatives as is for
> now.

They're essentially undocumented.  That makes the code that uses them
essentially unmaintainable, except by those who know, or are prepared to
guess, what these functions do.  I can't agree with you that this is
good.

> >  What do "U" and "Q" stand for?

> > There are people on this list who are using pcase like things, and so
> > clearly understand their syntax and semantics.  Could these people
> > PLEASE document these things, and do so before the release of Emacs
> > 25.1.  Preferably well before.

> To be honest, I tweaked some of the pcase related documentation, and was
> quite happy with it.  I think the pcase docstring is quite good.  A
> tutorial is missing though, clearly.

The pcase docstring is getting better, yes.  It stil doesn't document
explicitly that the normal meanings of ` and , are suspended.  There is
still no explicit statement of what pcase's ` and , mean.

Maybe I'm expecting too much, and ` and , have no intrinsic meanings in
pcase.  But I don't believe that is the case.  

> Michael.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:14         ` Michael Heerdegen
@ 2015-12-19 19:23           ` Phillip Lord
  2015-12-19 21:09             ` Michael Heerdegen
  2015-12-19 19:24           ` Phillip Lord
  1 sibling, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 19:23 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> phillip.lord@russet.org.uk (Phillip Lord) writes:
>
>> (pcase '(3 1 2)
>>    (`(_ 1 2)
>>    (message "Matched a list of anything followed by (2 3)")))
>>
>> prints nothing.
>>
>> while this...
>>
>> (pcase '(3 1 2)
>>    (`(,_ 1 2)
>>    (message "Matched a list of anything followed by (2 3)")))
>>
>> prints the message (which should be "followed by (2 3)").
>>
>> I am a bit surprised to find that _ needs , in these examples, and I
>> think that it's a bug.
>
> I think it's intentional, and it fits the documentation.

Not convinced. The documentation says....

‘(pred numberp)’ is a pattern that simply checks that ‘exp’ is a number,
and ‘_’ is the catch-all pattern that matches anything.

for example, which made me assume that "_" matches anything.


> We think of elements in a backquoted list to be all quoted unless
> explicitly unquoted.  It makes no sense that '_ matches any expression.
> It matches only the symbol _, and that can be useful, too.

To be it seems unintuitive, to be honest. It took me a while to work
this out; John made the same mistake, it seems.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:14         ` Michael Heerdegen
  2015-12-19 19:23           ` Phillip Lord
@ 2015-12-19 19:24           ` Phillip Lord
  1 sibling, 0 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 19:24 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> phillip.lord@russet.org.uk (Phillip Lord) writes:
>
>> (pcase '(3 1 2)
>>    (`(_ 1 2)
>>    (message "Matched a list of anything followed by (2 3)")))
>>
>> prints nothing.
>>
>> while this...
>>
>> (pcase '(3 1 2)
>>    (`(,_ 1 2)
>>    (message "Matched a list of anything followed by (2 3)")))
>>
>> prints the message (which should be "followed by (2 3)").
>>
>> I am a bit surprised to find that _ needs , in these examples, and I
>> think that it's a bug.
>
> I think it's intentional, and it fits the documentation.

Not convinced. The documentation says....

‘(pred numberp)’ is a pattern that simply checks that ‘exp’ is a number,
and ‘_’ is the catch-all pattern that matches anything.

for example, which made me assume that "_" matches anything.


> We think of elements in a backquoted list to be all quoted unless
> explicitly unquoted.  It makes no sense that '_ matches any expression.
> It matches only the symbol _, and that can be useful, too.

To me it seems unintuitive, to be honest. It took me a while to work
this out; John made the same mistake, it seems.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 16:04   ` Michael Heerdegen
@ 2015-12-19 19:29     ` Phillip Lord
  2015-12-19 21:14       ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 19:29 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Alan Mackenzie, emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> Michael Heerdegen <michael_heerdegen@web.de> writes:
>
>> As far as I understand how Stefan used to work, most of the semantics of
>> most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
>> we are not yet sure how useful we are, or if they may later be better be
>> replaced by other forms that are more general, etc.
>
> BTW3, we were not yet all agreed how the semantics of `pcase-dolist'
> should be when the pattern doesn't match (currently, AFAIK, it loops
> nonetheless).  Similarly for pcase-let and pcase-lambda.  For some of
> these forms, we do not yet know how useful they are.

pcase-lambda seems useful to me, seems to only take a single pattern,
like so:

(funcall
 (pcase-lambda (`(,x ,y))
   y)
 '(1 2))

To me, it would be more useful if it supported multiple patterns.

(funcall
 (pcase-lambda
    ((1)
      (message "Is a one"))
    (`(,_)
      (message "is a list")))
 1)

The non-matching situation would then be in the hands of the user. Or it
would be possible to make a "pcase-lambda-exhaustive" macro (probably
with a better name".

I'd also rename "pcase.el" to "p.el" but hey, that's a different story.


    
> Just some examples of open questions that shows that some stuff is still
> a bit of work in progress.


One that's already getting quite a bit of use.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:44     ` Michael Heerdegen
  2015-12-19 17:02       ` Eli Zaretskii
@ 2015-12-19 20:31       ` Phillip Lord
  2015-12-19 21:16         ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 20:31 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Alan Mackenzie, Emacs developers, Kaushal Modi

Michael Heerdegen <michael_heerdegen@web.de> writes:

> Just had a very quick look.
>
>
> To sum up, I don't think that basing the tutorial on the difference of
> qpatterns and upatterns is a good idea.  Destructuring is only one
> specific aspect of pcase.  And there are even different means of
> destructuring now, namely seq and map.


These forms could do with documenting. I've tried to get the seq and
map pcase-macro's working and have failed.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 12:15                         ` Eli Zaretskii
@ 2015-12-19 20:35                           ` Phillip Lord
  2015-12-19 20:58                             ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 20:35 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: David Kastrup, rasmus, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

>> 
>>     Conditionals
>> 
>>     * Pattern matching case statement::  How to use @code{pcase}.
>> 
>>     Nonlocal Exits
>> 
>>     * Catch and Throw::         Nonlocal exits for the program's own purposes.
>>     * Examples of Catch::       Showing how such nonlocal exits can be written.
>>     * Errors::                  How errors are signaled and handled.
>>     * Cleanups::                Arranging to run a cleanup form if an
>> 
>> Note that "Conditionals" now appears twice: as a proper node name and as
>> a newly added section containing only "pcase" and nothing else.
>
> Yes, and that is a problem because...?

I would think that it would make more sense to have "Pattern Matching"
at top-level. pcase is conditional, but neither pcase-let nor
pcase-lambda really is. The "conditional" can have a short section
saying "pcase is like case but with pattern matching", as can the "let"
and "lambda" documentation.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 18:30   ` Alan Mackenzie
@ 2015-12-19 20:42     ` Michael Heerdegen
  2015-12-19 22:25       ` Alan Mackenzie
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 20:42 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel

Alan Mackenzie <acm@muc.de> writes:

> I wish you a happy one, though.

You too!

> > As far as I understand how Stefan used to work, most of the semantics of
> > most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
> > we are not yet sure how useful we are, or if they may later be better be
> > replaced by other forms that are more general, etc.
>
> Yet the said functions have been committed on the release branch

I think Stefan used the term "don't advertise them yet too much" for
such things.

> and are already in widespread use throughout the Emacs sources.  As
> Eli notes, there're around 90 uses of pcase-let and pcase-let*.

Could be they have nearly all been placed there by Stefan ;-)

> They're essentially undocumented.  That makes the code that uses them
> essentially unmaintainable, except by those who know, or are prepared to
> guess, what these functions do.  I can't agree with you that this is
> good.

This can't be the final state, no doubt.  It must be fixed.

But we have to do it very carefully, and maybe not completely now: if
even Stefan was not sure everywhere what could be written in the
documentation and if the code makes much sense, let's not engrave in
stone details we are not sure about whether they are true or intended or
useful.

This does not so much apply to `pcase-let' - I think it's quite clear
what it does, though I didn't use it often myself.

OTOH, I'm not so sure about `pcase-lambda' for example.  How does/should
a `pcase-lambda' behave when applied to something that it's "signature"
doesn't match?  Is it maybe cleaner to move a pcase call just inside the
`lambda'?  Is the semantics of pcase really the best thing one can use
to hook pattern matching into a function, or is there a better one?  In
practice, only a subset of pcase semantics makes sense for
`pcase-lambda' most of the time (mostly, destructuring), you can have
"only one clause" contrary to `pcase' - is the resulting code readable?;
is `pcase-lambda' a good abstraction/idea?  If later we find it's a bad
idea, it's not good if we advertise it too much in the manual, because
we can't remove it so easily then.

> The pcase docstring is getting better, yes.  It stil doesn't document
> explicitly that the normal meanings of ` and , are suspended.

Mmh, but it also doesn't say that the normal meanings of and, or, ' and
let are suspended.  I think it doesn't have to, because a pcase pattern
is not an expression that is evaluated, so symbols with known names
can't have the same semantics as a pattern than as a defined function.

> There is still no explicit statement of what pcase's ` and , mean.

But do we agree that the current docstring completely explains the
semantics, even if the definition is recursive?

> Maybe I'm expecting too much, and ` and , have no intrinsic meanings in
> pcase.  But I don't believe that is the case.

``' is a pcase macro (at least now).  pcase macros are like Lisp macros,
but while Lisp macros expand to Lisp code, pcase macros expand to pcase
patterns.

The backquote macro ``' in Lisp is a utility that is used to build
lists.  pcase's ``' is used to build patterns that match lists.  The
only difference for unquoting (`,'), so to say, is that in the first
case it "inserts" an arbitrary "value" at that position, and in the
second case, "inserts" an arbitrary pcase pattern (that is responsible to
match the element at that place, instead of being a specified constant
that matches only itself via `equal'.)

If you only unquote symbols, like in

   `(1 2 ,x)

you can imagine that x is already bound to the "right" value, then the
thing works much like the standard backquote.  That analogy is not so
useful for things like

   `(1 2 ,(pred stringp))

I guess, though you still can imagine that the pattern matches any
three-element list whose first two elements are 1, 2, and as third
element, anything that fulfills the predicate "stringp" can be
"inserted".

You can verify by yourself that elements in a backquoted list in pcase
"behave" as if they were quoted with a quote (see the 'VAL form) - thus
the name "QPattern" - and that the rules for quoted atoms apply as
expected, and such things.

[ While writing this, I see now that the doc of ``' in the pcase doc is
  a typical mathematical definition: it is absolutely correct, but
  doesn't say "what it's good for" and "how to use it".  To be honest I
  also had much trouble to understand it when I learned `pcase'. ]

BTW, there is no `,@' unquote splicing in pcase's backquote because it
can lead to ambiguity when matching (and would be slow).


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 17:02       ` Eli Zaretskii
@ 2015-12-19 20:58         ` Michael Heerdegen
  2015-12-22  5:28         ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 20:58 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: acm, emacs-devel, kaushal.modi

Eli Zaretskii <eliz@gnu.org> writes:

> If we want to do that, we need to rewrite both the ELisp manual and
> the doc string to never use these.  With the current text of the
> manual, you simply cannot ignore them.  (Personally, I think trying to
> stop using them is futile, since so many people who actively use
> 'pcase' use these terms freely in their messages and other text they
> write.  But that's me.)

The terms are useful when explaining the semantics of ``'.  Using the
terms all the time can be confusing, however, because these terms are
completely unrelated to the semantics of other pcase pattern types.

> > If there are still examples like
> > 
> > >     (pcase value
> > >       (`1 (message "Matched a 1"))
> > >       (`2 (message "Matched a 2"))
> > >       (`"Hello" (message "Matched the string Hello")))
> > 
> > in the info manual, they should be changed to not use backquote.
>
> There are quite a few of these there.

Yip, I think they should be changed, for the same reason we prefer using
a simple quote over using backquote in Lisp when there is no unquoting
involved.  (And it looks unnecessarily weird...)

When pcase had been invented, it was more or less destructuring with
tests.  Now, the thing has developed, and ` does not play such an
central role anymore (though it's still important) because we found out
that it is much more useful for matching non-list values than we had
expected (with "we" I mean Stefan, and that's just my version of the
story).
 

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 20:35                           ` Phillip Lord
@ 2015-12-19 20:58                             ` Eli Zaretskii
  2015-12-19 22:23                               ` Phillip Lord
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-19 20:58 UTC (permalink / raw)
  To: Phillip Lord; +Cc: dak, rasmus, emacs-devel

> From: phillip.lord@russet.org.uk (Phillip Lord)
> Cc: David Kastrup <dak@gnu.org>,  <emacs-devel@gnu.org>,  <rasmus@gmx.us>
> Date: Sat, 19 Dec 2015 20:35:14 +0000
> 
> Eli Zaretskii <eliz@gnu.org> writes:
> 
> >> 
> >>     Conditionals
> >> 
> >>     * Pattern matching case statement::  How to use @code{pcase}.
> >> 
> >>     Nonlocal Exits
> >> 
> >>     * Catch and Throw::         Nonlocal exits for the program's own purposes.
> >>     * Examples of Catch::       Showing how such nonlocal exits can be written.
> >>     * Errors::                  How errors are signaled and handled.
> >>     * Cleanups::                Arranging to run a cleanup form if an
> >> 
> >> Note that "Conditionals" now appears twice: as a proper node name and as
> >> a newly added section containing only "pcase" and nothing else.
> >
> > Yes, and that is a problem because...?
> 
> I would think that it would make more sense to have "Pattern Matching"
> at top-level. pcase is conditional, but neither pcase-let nor
> pcase-lambda really is. The "conditional" can have a short section
> saying "pcase is like case but with pattern matching", as can the "let"
> and "lambda" documentation.

Sorry, I'm not following.  If we think the second instance of
"Conditionals" is not the best text, we can change it at will.  Only
the first one must me identical to the node name.  The second one is
"Conditionals" because it was produced by a program and I left it
unchanged, but it can be changed if we want to.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 17:19           ` Eli Zaretskii
@ 2015-12-19 21:03             ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 21:03 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: jwiegley, emacs-devel, acm, kaushal.modi

Eli Zaretskii <eliz@gnu.org> writes:

> (Time passes...)  Ah, I see: I was confused by John's different style:
> "now bound to foo" vs "bind it to foo".  These actually intend to say
> the same thing: "match anything and bind it to foo", but the former
> wording made it sound like it was already bound to foo before, i.e. as
> if the first pattern _uses_ the existing binding of foo, instead of
> binding foo.

Yes, exactly.

> Silly me, trying to assign too much importance to the wording.

Ok, but the words are there to explain the thing, so...


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 19:23           ` Phillip Lord
@ 2015-12-19 21:09             ` Michael Heerdegen
  2015-12-19 21:57               ` Phillip Lord
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 21:09 UTC (permalink / raw)
  To: Phillip Lord; +Cc: emacs-devel

phillip.lord@russet.org.uk (Phillip Lord) writes:

> >> I am a bit surprised to find that _ needs , in these examples, and I
> >> think that it's a bug.
> >
> > I think it's intentional, and it fits the documentation.
>
> Not convinced. The documentation says....
>
> ‘(pred numberp)’ is a pattern that simply checks that ‘exp’ is a number,
> and ‘_’ is the catch-all pattern that matches anything.
>
> for example, which made me assume that "_" matches anything.

Anything in a backquote is implicitly quoted, and thus should behave
like

    'VAL		matches if the object is ‘equal’ to VAL.

The elements in a backquoted list in a pcase pattern are _not_
interpreted as pcase patterns, unless unquoted.  _ is not special here.

You also can't use

  `(1 2 (pred numberp))

as you would expect.  Why should _ be different?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 19:29     ` Phillip Lord
@ 2015-12-19 21:14       ` Michael Heerdegen
  2015-12-19 22:06         ` Phillip Lord
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 21:14 UTC (permalink / raw)
  To: Phillip Lord; +Cc: Alan Mackenzie, emacs-devel

phillip.lord@russet.org.uk (Phillip Lord) writes:

> I'd also rename "pcase.el" to "p.el" but hey, that's a different
> story.

and `pcase-let' to `plet' etc.  A valid issue IMHO.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 20:31       ` Phillip Lord
@ 2015-12-19 21:16         ` Michael Heerdegen
  2015-12-19 22:11           ` Phillip Lord
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-19 21:16 UTC (permalink / raw)
  To: Phillip Lord; +Cc: Alan Mackenzie, Emacs developers, Kaushal Modi

phillip.lord@russet.org.uk (Phillip Lord) writes:

> These forms could do with documenting. I've tried to get the seq and
> map pcase-macro's working and have failed.

What did you try and what failed?  Did you load seq.el and map.el before
trying?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 21:09             ` Michael Heerdegen
@ 2015-12-19 21:57               ` Phillip Lord
  2015-12-20  5:13                 ` Richard Stallman
  2015-12-20 13:33                 ` Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 21:57 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

>> Not convinced. The documentation says....
>>
>> ‘(pred numberp)’ is a pattern that simply checks that ‘exp’ is a number,
>> and ‘_’ is the catch-all pattern that matches anything.
>>
>> for example, which made me assume that "_" matches anything.
>
> Anything in a backquote is implicitly quoted, and thus should behave
> like
>
>     'VAL		matches if the object is ‘equal’ to VAL.
>
> The elements in a backquoted list in a pcase pattern are _not_
> interpreted as pcase patterns, unless unquoted.  _ is not special here.
>
> You also can't use
>
>   `(1 2 (pred numberp))
>
> as you would expect.  Why should _ be different?


I can certainly see your point, and agree from a point-of-view of
semantics then it makes sense. But from a point-of-view of usability, I
am less convinced.

"_" is different because it has no formal semantics in the rest of lisp.
So, for example, 

(funcall
 (lambda(_)
   _)
 1)

returns 1. Compare this with works

(pcase 1
  (a a))

and this which errors

(pcase 1
  (_ _))

So, "_" can have any semantics we like, and remain consistent.

To me, I would expect this:

(pcase '(1)
  (`(_) 'hello))

to return 'hello and yet it does not. Set against, this, I guess you are
worried that with the semantics I suggest then you cannot do something
like this:

(pcase '(1)
  (`(_) 'hello)
  (`(1) 'goodbye))
  
which now returns 'goodbye, but would return 'hello. This is a valid
concern, I agree, although I think is a more minor usage (since "_" has
no special semantics, how often do you want to match this!). Perhaps, it
could be supported by a syntax like this:

(pcase '(1)
  (`('_) 'hello)
  (`(1) 'goodbye))
=> 'goodbye


Irrespective of whether you agree with this or not, what I would say is
that the current requirement for ,_ is not obvious, and that it is a
pcase "gotcha". I would say that least one concrete example in the
manual of this usage, explicitly mentioning the , is a good idea.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 21:14       ` Michael Heerdegen
@ 2015-12-19 22:06         ` Phillip Lord
  0 siblings, 0 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 22:06 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Alan Mackenzie, emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> phillip.lord@russet.org.uk (Phillip Lord) writes:
>
>> I'd also rename "pcase.el" to "p.el" but hey, that's a different
>> story.
>
> and `pcase-let' to `plet' etc.  A valid issue IMHO.


The standard would be "p-case" and "p-let" I think. A standard (short)
suffix for "exhaustive" (which I interpret to mean "must match or
error") would be nice also. That would make the entry points

p-case
p-let
p-let*
p-dolist
p-lambda

as well as

p-case-ex
p-let-ex

and so on.

Once the semantics of p-lambda is clear, it would probably also make
sense to add "p-defun". And possibly "p-macro". Although this would then
clash with the current "pcase-macro" which would naturally translate to
p-macro also. So, I'd call this "p-defpattern".

Against this, there is a slight concern about proliferation of single
symbol packages (dash, s, f and the like) in the outside world.

Phil




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 21:16         ` Michael Heerdegen
@ 2015-12-19 22:11           ` Phillip Lord
  2015-12-20 12:45             ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 22:11 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Alan Mackenzie, Kaushal Modi, Emacs developers

Michael Heerdegen <michael_heerdegen@web.de> writes:

> phillip.lord@russet.org.uk (Phillip Lord) writes:
>
>> These forms could do with documenting. I've tried to get the seq and
>> map pcase-macro's working and have failed.
>
> What did you try and what failed?  Did you load seq.el and map.el before
> trying?

Just get them working at all. The pcase doc says:

-- (map &rest ARGS)

ARGS can be a list of the form (KEY PAT), in which case KEY in an
unquoted form.

ARGS can also be a list of symbols, which stands for (’SYMBOL
SYMBOL).

So, I tried something like:

(pcase '(:a 1)
  ((map `(:a ,a)) a))

which I thought might eval to 1.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 20:58                             ` Eli Zaretskii
@ 2015-12-19 22:23                               ` Phillip Lord
  2015-12-20  3:38                                 ` Eli Zaretskii
  2015-12-20 14:16                                 ` Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-19 22:23 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: dak, rasmus, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

>> From: phillip.lord@russet.org.uk (Phillip Lord)
>> Cc: David Kastrup <dak@gnu.org>,  <emacs-devel@gnu.org>,  <rasmus@gmx.us>
>> Date: Sat, 19 Dec 2015 20:35:14 +0000
>> 
>> Eli Zaretskii <eliz@gnu.org> writes:
>> 
>> >> 
>> >>     Conditionals
>> >> 
>> >>     * Pattern matching case statement::  How to use @code{pcase}.
>> >> 
>> >>     Nonlocal Exits
>> >> 
>> >>     * Catch and Throw::         Nonlocal exits for the program's own purposes.
>> >>     * Examples of Catch::       Showing how such nonlocal exits can be written.
>> >>     * Errors::                  How errors are signaled and handled.
>> >>     * Cleanups::                Arranging to run a cleanup form if an
>> >> 
>> >> Note that "Conditionals" now appears twice: as a proper node name and as
>> >> a newly added section containing only "pcase" and nothing else.
>> >
>> > Yes, and that is a problem because...?
>> 
>> I would think that it would make more sense to have "Pattern Matching"
>> at top-level. pcase is conditional, but neither pcase-let nor
>> pcase-lambda really is. The "conditional" can have a short section
>> saying "pcase is like case but with pattern matching", as can the "let"
>> and "lambda" documentation.
>
> Sorry, I'm not following.  If we think the second instance of
> "Conditionals" is not the best text, we can change it at will.  Only
> the first one must me identical to the node name.  The second one is
> "Conditionals" because it was produced by a program and I left it
> unchanged, but it can be changed if we want to.


Simple change would be from:

Conditionals

* Pattern matching case statement::  How to use @code{pcase}.


to

Pattern Matching

* Conditional::  How to use @code{pcase}



In the grand scheme I would aim for this....




Control Structures

* Sequencing::              Evaluation in textual order.
* Conditionals::            ‘if’, ‘cond’, ‘when’, ‘unless’.
* Combining Conditions::    ‘and’, ‘or’, ‘not’.
....etc

Pattern Matching

(this would contain a generalised introduction and tutorial, based
around pcase)

* List Clauses::            Destructuring Lists
* Predicates::              Matching with predicate functions
* Booleans::                and and or
* Guards::                  I don't quite understand guards
* Conditionals::            pcase
* Binding::                 pcase-let 
* Lambda::                  pcase-lambda
* New Patterns::            pcase-macro, with description of seq and map support.

Nonlocal Exits

* Catch and Throw::         Nonlocal exits for the program’s own purposes.
* Examples of Catch::       Showing how such nonlocal exits can be written.
* Errors::                  How errors are signaled and handled.
* Cleanups::                Arranging to run a cleanup form if an



Some of these detailed nodes might be too much -- pcase will inevitably
get heavily described in the introduction to pattern matching, while
"predicates, booleans and guards" could be described in one place.

Phil





^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 20:42     ` Michael Heerdegen
@ 2015-12-19 22:25       ` Alan Mackenzie
  2015-12-20 13:11         ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2015-12-19 22:25 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

Hello, Michael.

On Sat, Dec 19, 2015 at 09:42:01PM +0100, Michael Heerdegen wrote:
> Alan Mackenzie <acm@muc.de> writes:

> > I wish you a happy one, though.

> You too!

Thanks!

> > > As far as I understand how Stefan used to work, most of the semantics of
> > > most of the pcase derivatives, like `pcase-let', are not yet 100% fixed,
> > > we are not yet sure how useful we are, or if they may later be better be
> > > replaced by other forms that are more general, etc.

> > Yet the said functions have been committed on the release branch

> I think Stefan used the term "don't advertise them yet too much" for
> such things.

> > and are already in widespread use throughout the Emacs sources.  As
> > Eli notes, there're around 90 uses of pcase-let and pcase-let*.

> Could be they have nearly all been placed there by Stefan ;-)

I think that's probable rather than possible.

> > They're essentially undocumented.  That makes the code that uses them
> > essentially unmaintainable, except by those who know, or are prepared to
> > guess, what these functions do.  I can't agree with you that this is
> > good.

> This can't be the final state, no doubt.  It must be fixed.

Glad you agree.

> But we have to do it very carefully, and maybe not completely now: if
> even Stefan was not sure everywhere what could be written in the
> documentation and if the code makes much sense, let's not engrave in
> stone details we are not sure about whether they are true or intended or
> useful.

I don't really know what pcase-let does.  I haven't a clue what
pcase-lambda, pcase-defmacro, ... do.

> This does not so much apply to `pcase-let' - I think it's quite clear
> what it does, though I didn't use it often myself.

It's not clear to me.  I resent being forced to guess, read the pcase.el
source, or give up on trying to understand significant portions of the
Emacs source code.  So, yes, I think `pcase-let' should be documented.

> OTOH, I'm not so sure about `pcase-lambda' for example.  How does/should
> a `pcase-lambda' behave when applied to something that it's "signature"
> doesn't match?  Is it maybe cleaner to move a pcase call just inside the
> `lambda'?  Is the semantics of pcase really the best thing one can use
> to hook pattern matching into a function, or is there a better one?  In
> practice, only a subset of pcase semantics makes sense for
> `pcase-lambda' most of the time (mostly, destructuring), you can have
> "only one clause" contrary to `pcase' - is the resulting code readable?;
> is `pcase-lambda' a good abstraction/idea?  If later we find it's a bad
> idea, it's not good if we advertise it too much in the manual, because
> we can't remove it so easily then.

> > The pcase docstring is getting better, yes.  It stil doesn't document
> > explicitly that the normal meanings of ` and , are suspended.

> Mmh, but it also doesn't say that the normal meanings of and, or, ' and
> let are suspended.

Good point.  Perhaps it should say that about these symbols, too.  And
perhaps the entries in the Elisp manual for `and', `or', ``', `,', etc.
should warn about the non-uniform meanings within pcase.  The notion of
kicking a wasp's nest springs to mind.

> I think it doesn't have to, because a pcase pattern is not an
> expression that is evaluated, so symbols with known names can't have
> the same semantics as a pattern than as a defined function.

That would be a good argument if only experts read the doc string.
Thoroughly confused people also read doc strings.  I don't think we
should presuppose such sophisticated discernment in the typical reader.

> > There is still no explicit statement of what pcase's ` and , mean.

> But do we agree that the current docstring completely explains the
> semantics, even if the definition is recursive?

I don't agree.  Completely missing is something like "pcase compares the
value with each pattern in turn until one matches, and it then evaluates
the corresponding BODY, returning the result of the last body form
evaluated.  If no pattern matches, nil is returned.".  The somewhat
offensive "perform ML-style pattern matching on that value" is no
substitute for this.

There is no mention of ``' and `,' in the section on patterns.  Or is
\\='VAL really meant to be \\=`VAL?

> > Maybe I'm expecting too much, and ` and , have no intrinsic meanings in
> > pcase.  But I don't believe that is the case.

> ``' is a pcase macro (at least now).  pcase macros are like Lisp macros,
> but while Lisp macros expand to Lisp code, pcase macros expand to pcase
> patterns.

> The backquote macro ``' in Lisp is a utility that is used to build
> lists.  pcase's ``' is used to build patterns that match lists.  The
> only difference for unquoting (`,'), so to say, is that in the first
> case it "inserts" an arbitrary "value" at that position, and in the
> second case, "inserts" an arbitrary pcase pattern (that is responsible to
> match the element at that place, instead of being a specified constant
> that matches only itself via `equal'.)

But what does ``' _do_?  What it normally does is well explained in its
own doc string (which will need modification for pcase).  But what does
``' _do_ within pcase?  Saying "it is used to build patterns ...." is a
cop out.  The difficulty in describing its (and `,''s) semantics seems
to be a weakness in pcase.

> If you only unquote symbols, like in

>    `(1 2 ,x)

> you can imagine that x is already bound to the "right" value, then the
> thing works much like the standard backquote.  That analogy is not so
> useful for things like

>    `(1 2 ,(pred stringp))

> I guess, though you still can imagine that the pattern matches any
> three-element list whose first two elements are 1, 2, and as third
> element, anything that fulfills the predicate "stringp" can be
> "inserted".

> You can verify by yourself that elements in a backquoted list in pcase
> "behave" as if they were quoted with a quote (see the 'VAL form) - thus
> the name "QPattern" - and that the rules for quoted atoms apply as
> expected, and such things.

Are you saying that "QPattern" has no more conceptual meaning than
"patterns which are backquoted"?

> [ While writing this, I see now that the doc of ``' in the pcase doc is
>   a typical mathematical definition: it is absolutely correct, but
>   doesn't say "what it's good for" and "how to use it".  To be honest I
>   also had much trouble to understand it when I learned `pcase'. ]

I think I've got some reasonable partial understanding of ``', but I'm
unhappy that there's no concise description of what it does.

> BTW, there is no `,@' unquote splicing in pcase's backquote because it
> can lead to ambiguity when matching (and would be slow).

OK.

> Regards,

> Michael.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 22:23                               ` Phillip Lord
@ 2015-12-20  3:38                                 ` Eli Zaretskii
  2015-12-20 22:54                                   ` Phillip Lord
  2015-12-20 14:16                                 ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2015-12-20  3:38 UTC (permalink / raw)
  To: Phillip Lord; +Cc: dak, rasmus, emacs-devel

> From: phillip.lord@russet.org.uk (Phillip Lord)
> Cc: <dak@gnu.org>,  <rasmus@gmx.us>,  <emacs-devel@gnu.org>
> Date: Sat, 19 Dec 2015 22:23:54 +0000
> 
> > Sorry, I'm not following.  If we think the second instance of
> > "Conditionals" is not the best text, we can change it at will.  Only
> > the first one must me identical to the node name.  The second one is
> > "Conditionals" because it was produced by a program and I left it
> > unchanged, but it can be changed if we want to.
> 
> Simple change would be from:
> 
> Conditionals
> 
> * Pattern matching case statement::  How to use @code{pcase}.
> 
> 
> to
> 
> Pattern Matching
> 
> * Conditional::  How to use @code{pcase}

The last line can't be done, unless the node names are changed as
well.  Right now the pcase description is in the child node of
"Conditionals" whose name is "Pattern matching case statement".

Also, I think having 2 nodes named "Conditionals" and "Conditional"
will be too confusing.

> Pattern Matching
> 
> (this would contain a generalised introduction and tutorial, based
> around pcase)
> 
> * List Clauses::            Destructuring Lists
> * Predicates::              Matching with predicate functions
> * Booleans::                and and or
> * Guards::                  I don't quite understand guards
> * Conditionals::            pcase
> * Binding::                 pcase-let 
> * Lambda::                  pcase-lambda

These would be too short to justify a separate node, IMO.

> * New Patterns::            pcase-macro, with description of seq and map support.

We avoid using "new" in manuals, because they are that only for one
release.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 21:57               ` Phillip Lord
@ 2015-12-20  5:13                 ` Richard Stallman
  2015-12-20  9:25                   ` Phillip Lord
  2015-12-20 13:45                   ` Michael Heerdegen
  2015-12-20 13:33                 ` Michael Heerdegen
  1 sibling, 2 replies; 375+ messages in thread
From: Richard Stallman @ 2015-12-20  5:13 UTC (permalink / raw)
  To: Phillip Lord; +Cc: michael_heerdegen, emacs-devel

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

Could someone report on what the current meaning of _ is?
How is it actually used in pcase?

-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2015-12-20  5:13                 ` Richard Stallman
@ 2015-12-20  9:25                   ` Phillip Lord
  2015-12-21  5:04                     ` Richard Stallman
  2015-12-20 13:45                   ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-20  9:25 UTC (permalink / raw)
  To: rms@gnu.org, Phillip Lord; +Cc: michael_heerdegen@web.de, emacs-devel@gnu.org



It matches anything (like a variable) but does not actually bind a variable.

It's also being used in other parts of Emacs -- I've used it for generic EIEIO methods

(defmethod blah (a b _))


to mean "I have to have a parameter, but am not going to use it", although it's just a symbol
like any other and binds a variable. IIRC it shuts byte compiler warnings up about unused variables.




________________________________________
From: Richard Stallman [rms@gnu.org]
Sent: 20 December 2015 05:13
To: Phillip Lord
Cc: michael_heerdegen@web.de; emacs-devel@gnu.org
Subject: Re: The poor state of documentation of pcase like things.

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

Could someone report on what the current meaning of _ is?
How is it actually used in pcase?

--
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 22:11           ` Phillip Lord
@ 2015-12-20 12:45             ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-20 12:45 UTC (permalink / raw)
  To: Phillip Lord; +Cc: Alan Mackenzie, nicolas, Kaushal Modi, Emacs developers

phillip.lord@russet.org.uk (Phillip Lord) writes:

> (pcase '(:a 1)

(:a 1) is not a map in the sense of map.el.  You probably want an alist:
((:a . 1)).

>   ((map `(:a ,a)) a))

``' is a different pattern type.  You want to use the `map', and
backquote is not part of its syntax.  So, this is how the example should
look like:

(pcase '((:a . 1))
  ((map (:a a)) a))

But the doc is not correct indeed:


@Nicolas: Can you please correct these sentences of the "map" pcase
pattern documentation:

,----------------------------------------------------------------------
| ARGS can be a list of the form (KEY PAT), in which case KEY in an
| unquoted form.
| 
| ARGS can also be a list of symbols, which stands for (’SYMBOL
| SYMBOL).
`----------------------------------------------------------------------

It should say that ARGS can be a list of elements of the form (KEY PAT)
                                      ^^^^^^^^^^^

(at least that's how I think it is meant.  OTOH,

(pcase '((:a . 1) (:b . 2))
  ((map (:a a :b b)) (list a b)))

gives an error (void variable: b), so I'm not sure)

In the second sentence, our new quoting magic messes the quote character
in the doc shown in the help buffer.


Thanks,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 22:25       ` Alan Mackenzie
@ 2015-12-20 13:11         ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-20 13:11 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel

Alan Mackenzie <acm@muc.de> writes:

> I don't really know what pcase-let does.  I haven't a clue what
> pcase-lambda, pcase-defmacro, ... do.

The doc of `pcase-defmacro' is very terse, but I find the docs of 
`pcase-lambda' and `pcase-let' understandable.  What's wrong with these?

> > Mmh, but it also doesn't say that the normal meanings of and, or, ' and
> > let are suspended.

> > I think it doesn't have to, because a pcase pattern is not an
> > expression that is evaluated, so symbols with known names can't have
> > the same semantics as a pattern than as a defined function.
>
> That would be a good argument if only experts read the doc string.
> Thoroughly confused people also read doc strings.  I don't think we
> should presuppose such sophisticated discernment in the typical
> reader.

Ok, speaking it out is a good idea.  But I would prefer the (improved)
manual section.

> > > There is still no explicit statement of what pcase's ` and , mean.
>
> > But do we agree that the current docstring completely explains the
> > semantics, even if the definition is recursive?
>
> I don't agree.  Completely missing is something like "pcase compares the
> value with each pattern in turn until one matches, and it then evaluates
> the corresponding BODY, returning the result of the last body form
> evaluated.  If no pattern matches, nil is returned.".  The somewhat
> offensive "perform ML-style pattern matching on that value" is no
> substitute for this.

I agree, but that is unrelated to backquote.

> There is no mention of ``' and `,' in the section on patterns.  Or is
> \\='VAL really meant to be \\=`VAL?

No.

Since it's defined with `pcase-defmacro' now, it's listed later in the
section describing all additional pattern types:

,----------------------------------------------------------------------
| -- `QPAT
| 
| Backquote-style pcase patterns.
| QPAT can take the following forms:
|   (QPAT1 . QPAT2)       matches if QPAT1 matches the car and QPAT2 the cdr.
|   [QPAT1 QPAT2..QPATn]  matches a vector of length n and QPAT1..QPATn match
|                            its 0..(n-1)th elements, respectively.
|   ,PAT                  matches if the pcase pattern PAT matches.
|   ATOM                  matches if the object is ‘equal’ to ATOM.
| 			   ATOM can be a symbol, an integer, or a
|                          string.
`----------------------------------------------------------------------

Did you miss it all the time?


> But what does ``' _do_?  What it normally does is well explained in its
> own doc string (which will need modification for pcase).

No, pcase just uses the symbol ``'.  What ``' "means" in pcase doesn't
belong in the docstring of `backquote', those are two completely
unrelated things, there is just some analogy (which led Stefan to use a
backquote for the syntax).

> Are you saying that "QPattern" has no more conceptual meaning than
> "patterns which are backquoted"?

That's were the name comes from.  But the forms a QPAT can have are
different from the "normal" pcase pattern types.  See the -- `QPAT
section I quoted.


Regards,

Michael.


P.S. I'll be on a trip for the next two days in ~ two hours and will not be
able to read this list in that time.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 21:57               ` Phillip Lord
  2015-12-20  5:13                 ` Richard Stallman
@ 2015-12-20 13:33                 ` Michael Heerdegen
  2015-12-20 18:51                   ` Phillip Lord
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-20 13:33 UTC (permalink / raw)
  To: Phillip Lord; +Cc: emacs-devel

phillip.lord@russet.org.uk (Phillip Lord) writes:

> Irrespective of whether you agree with this or not, what I would say is
> that the current requirement for ,_ is not obvious, and that it is a
> pcase "gotcha".

You know, I wanted to make the same suggestion a year ago.  ,_ looks
weird, I see all your arguments, they are all valid.

But how would that fit into the semantics we have?  _ is a pcase
pattern.  You would like it to be also a valid QPAT, matching anything.

This would mess up the semantics to the worse: `_ would
then be a pcase pattern matching anything.  Should '_ also match
anything?  But how to match the symbol _ then?  If not, why should `_ be
different from '_ when there is no unquoting involved?

Or should _ as a QPAT only behave different when used "not at toplevel"?
This would be horribly inconsequent: We would get two different types of
QPATs: toplevel QPATS, and non-toplevel-QPATS.  That would confuse
people even more, a pain to explain and to internalize.


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-20  5:13                 ` Richard Stallman
  2015-12-20  9:25                   ` Phillip Lord
@ 2015-12-20 13:45                   ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-20 13:45 UTC (permalink / raw)
  To: Richard Stallman; +Cc: emacs-devel, Phillip Lord

Richard Stallman <rms@gnu.org> writes:

> Could someone report on what the current meaning of _ is?
> How is it actually used in pcase?

It's one of the pcase pattern types.  It matches anything.  That's all.
See the doc of `pcase'.


Apart from pcase, AFAIK the symbol _ is not special at all, it's just a
symbol.

But the byte compiler suppresses some warnings for symbols whose names
start with a _, in particular, about unused variables.  It is also
allowed to use `_' multiple times in the argument list of a function.

The intended usage is to give function arguments a name starting with _
(including `_' itself) when they are ignored by the function.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 22:23                               ` Phillip Lord
  2015-12-20  3:38                                 ` Eli Zaretskii
@ 2015-12-20 14:16                                 ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-20 14:16 UTC (permalink / raw)
  To: emacs-devel

phillip.lord@russet.org.uk (Phillip Lord) writes:

> * Booleans::                and and or

I would want to avoid the name "Boolean", since we don't speak about
Boolean values.

> * Guards::                  I don't quite understand guards

What's the problem?  (And I think they belong to the same section as
predicates.)

I think the following holds:

  (guard EXPR) == (pred (lambda (_arg) EXPR))


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-20 13:33                 ` Michael Heerdegen
@ 2015-12-20 18:51                   ` Phillip Lord
  2015-12-24 17:46                     ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Phillip Lord @ 2015-12-20 18:51 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> phillip.lord@russet.org.uk (Phillip Lord) writes:
>
>> Irrespective of whether you agree with this or not, what I would say is
>> that the current requirement for ,_ is not obvious, and that it is a
>> pcase "gotcha".
>
> You know, I wanted to make the same suggestion a year ago.  ,_ looks
> weird, I see all your arguments, they are all valid.
>
> But how would that fit into the semantics we have?  _ is a pcase
> pattern.  You would like it to be also a valid QPAT, matching anything.

I don't know. I am thinking of it from a point-of-view of the syntax I
would like as a user, rather than the semantics I would use to achieve
this.

I do worry that the syntax of pcase is too complex. As an example
compare dash.el and pcase:

(-let [(a b _) '(1 2 3)]
  (list a b))

(pcase-let
    ((`(,a ,b ,_) '(1 2 3)))
  (list a b))

I've chosen an extreme example here, but the pcase version has a lot of
punctuation (and worth remembering however familiar the macro expert is
with punctuation not all emacs-lisp programmers are).

Set against this, dash is imperfect in it's handling of "_". Compare:

(-let [(a b _) '(1 2 3)]
  (list a b _))

(pcase-let
    ((`(,a ,b ,_) '(1 2 3)))
  (list a b _))

The former returns "(1 2 3) while the later errors with "No such var".


> This would mess up the semantics to the worse: `_ would
> then be a pcase pattern matching anything.  Should '_ also match
> anything?  But how to match the symbol _ then?  If not, why should `_ be
> different from '_ when there is no unquoting involved?
>
> Or should _ as a QPAT only behave different when used "not at toplevel"?
> This would be horribly inconsequent: We would get two different types of
> QPATs: toplevel QPATS, and non-toplevel-QPATS.  That would confuse
> people even more, a pain to explain and to internalize.

I thought we were not going to mention q-patterns any more!

I think that too much of the implementation semantics is poking through
into the syntax. I suspect no one would notice if "_" matched anything
inside a backquoted list, because it feels natural.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-20  3:38                                 ` Eli Zaretskii
@ 2015-12-20 22:54                                   ` Phillip Lord
  0 siblings, 0 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-20 22:54 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: dak, rasmus, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:
>> 
>> Simple change would be from:
>> 
>> Conditionals
>> 
>> * Pattern matching case statement::  How to use @code{pcase}.
>> 
>> 
>> to
>> 
>> Pattern Matching
>> 
>> * Conditional::  How to use @code{pcase}

>
> The last line can't be done, unless the node names are changed as
> well.  Right now the pcase description is in the child node of
> "Conditionals" whose name is "Pattern matching case statement".
>
> Also, I think having 2 nodes named "Conditionals" and "Conditional"
> will be too confusing.

Agreed. Hostage to fortune, if another pattern matching conditional is
invented.

"Pattern Matching" and "pcase" would work.

>> Pattern Matching
>> 
>> (this would contain a generalised introduction and tutorial, based
>> around pcase)
>> 
>> * List Clauses::            Destructuring Lists
>> * Predicates::              Matching with predicate functions
>> * Booleans::                and and or
>> * Guards::                  I don't quite understand guards
>> * Conditionals::            pcase
>> * Binding::                 pcase-let 
>> * Lambda::                  pcase-lambda
>
> These would be too short to justify a separate node, IMO.

They might be, yes. I'd write it and see. With examples for each, they
might get long enough.

>
>> * New Patterns:: pcase-macro, with description of seq and map support.
>
> We avoid using "new" in manuals, because they are that only for one
> release.

Sorry, poor working "Creating New Patterns" -- or perhaps "extending
pattern matching".

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-20  9:25                   ` Phillip Lord
@ 2015-12-21  5:04                     ` Richard Stallman
  2015-12-21 10:15                       ` Phillip Lord
  2015-12-22  5:18                       ` John Wiegley
  0 siblings, 2 replies; 375+ messages in thread
From: Richard Stallman @ 2015-12-21  5:04 UTC (permalink / raw)
  To: Phillip Lord; +Cc: michael_heerdegen, emacs-devel, phillip.lord

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  > It matches anything (like a variable) but does not actually bind a variable.

Alas, that's the half of the answer that I already knew.
What I don't know is, how do you _write_ the use of _?
That seemed self-contradictory in the text that was posted.

Can someone show me some properly working examples of _ in pcase
and say what they do?

-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-21  5:04                     ` Richard Stallman
@ 2015-12-21 10:15                       ` Phillip Lord
  2015-12-22  5:18                       ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: Phillip Lord @ 2015-12-21 10:15 UTC (permalink / raw)
  To: Richard Stallman; +Cc: michael_heerdegen, emacs-devel

Richard Stallman <rms@gnu.org> writes:

> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
> [[[ whether defending the US Constitution against all enemies,     ]]]
> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
>
>   > It matches anything (like a variable) but does not actually bind a variable.
>
> Alas, that's the half of the answer that I already knew.
> What I don't know is, how do you _write_ the use of _?
> That seemed self-contradictory in the text that was posted.
>
> Can someone show me some properly working examples of _ in pcase
> and say what they do?

Okay. This is the simplest use and it returns 'hello

(pcase 1
  (_ 'hello))

It differs from a normal symbol because this:

(pcase 1
  (a a))

evals to 1, while this

(pcase 1
  (_ _))


errors with "void variable". That is `_' is not bound, unlike a. So `_'
is more than just convention.

Inside a list, though, it needs to be comma'd. So:

(pcase '(1 2 3)
  (`(,a 2 3) 'hello))

(pcase '(1 2 3)
  (`(,_ 2 3) 'hello))


both return `hello' (the former binding `a', the latter not binding
`_').


The question is how should this form behave.

(pcase '(1 2 3)
  (`(_ 2 3) 'hello))


Currently, it returns `nil' because `_' matches the symbol `_' not
anything. Obviously, this is useful if you want to match the symbol
`_'. But I think it's unintuitive.

Even if everyone agrees it is wrong, if it is fixable, I do not know. I
suspect it's probably too late in the day for the emacs-25.

Phil



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-21  5:04                     ` Richard Stallman
  2015-12-21 10:15                       ` Phillip Lord
@ 2015-12-22  5:18                       ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:18 UTC (permalink / raw)
  To: Richard Stallman
  Cc: michael_heerdegen, Phillip Lord, phillip.lord, emacs-devel

>>>>> Richard Stallman <rms@gnu.org> writes:

> Can someone show me some properly working examples of _ in pcase and say
> what they do?

I made an error in the example, Richard, it should have been ,_.  Otherwise,
it matches the explicit symbol named `_'.  I'll correct the example.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  7:15       ` Eli Zaretskii
                           ` (2 preceding siblings ...)
  2015-12-18 12:21         ` Marcin Borkowski
@ 2015-12-22  5:20         ` John Wiegley
  3 siblings, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:20 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: kaushal.modi, acm, emacs-devel, Phillip Lord

>>>>> Eli Zaretskii <eliz@gnu.org> writes:

> Bottom line: what we do need is make the description clear and
> complete.  Where it appears is orders of magnitude less important.

This is quite true. The sort of user who wishes to understand `pcase' will
find the documentation for it, wherever it is the table of contents.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 17:40           ` Michael Heerdegen
@ 2015-12-22  5:21             ` John Wiegley
  0 siblings, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:21 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: kaushal.modi, jwiegley, Eli Zaretskii, emacs-devel, acm

>>>>> Michael Heerdegen <michael_heerdegen@web.de> writes:

>> Neither can a pcase that has a default clause, right?

A default clause for pcase would be:

    (_ (message "Hello, this is the default case"))

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:18       ` Michael Heerdegen
@ 2015-12-22  5:22         ` John Wiegley
  0 siblings, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:22 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: kaushal.modi, John Wiegley, Eli Zaretskii, emacs-devel, acm

>>>>> Michael Heerdegen <michael_heerdegen@web.de> writes:

>> >     (pcase value
>> >       (`(1 2 ,(or `3 `4))
>> 
>> Do 3 and 4 really have to be quoted here?  Why?

> Of course not! The form after the `unquote' is a "normal" pcase pattern.
> Numbers count as atoms matching themselves.

This was an unfortunate attempt to follow the sequence of unveiling features.
I'll avoid this unnecessary complexity.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 16:47   ` Eli Zaretskii
  2015-12-19 17:24     ` Michael Heerdegen
@ 2015-12-22  5:25     ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:25 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, acm, emacs-devel

>>>>> Eli Zaretskii <eliz@gnu.org> writes:

> Tutorials are always good to have, but they cannot replace good
> documentation in the manual. We should strive to provide manuals that are
> self-contained and don't require any tutorial reading for acquiring a full
> understanding of an issue and an unimpeded capability of using it in Lisp
> programs.

Agreed. After I have absorbed all feedback on my proposed tutorial, I'll
recast it into the language of the Elisp manual and include it there.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 15:31     ` Michael Heerdegen
@ 2015-12-22  5:25       ` John Wiegley
  2015-12-22 13:16         ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:25 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Alan Mackenzie, Emacs developers, Kaushal Modi

>>>>> Michael Heerdegen <michael_heerdegen@web.de> writes:

> I'm very much willing to help with a different tutorial, prove-read your
> stuff and improved docs etc. but don't have so much time before Christmas.

> Do we have the time to do this after Christmas?

Yes, I certainly do!  A collaboration on this is most welcome.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-19 17:02       ` Eli Zaretskii
  2015-12-19 20:58         ` Michael Heerdegen
@ 2015-12-22  5:28         ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-22  5:28 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, acm, kaushal.modi, emacs-devel

>>>>> Eli Zaretskii <eliz@gnu.org> writes:

>> I think we should not emphasize QPatterns and UPatterns too much,
>> because today, ``' is just a pcase macro.  When not using ``' is pcase,
>> we speak of just PATTERNs.

> If we want to do that, we need to rewrite both the ELisp manual and the doc
> string to never use these.

I'm at least fine with de-emphasizing them. They convey no information at all
(is it "Quoted" and "Unquoted"? What does that really mean, since they both
have meanings in terms of matching, beyond their quotation level).

So in a word, the two terms are almost worst than nothing. I prefer logical
and explicit matches, where a logical match compares an entity against some
form of query, while an explicit match is the special case of a query by `eq'.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-22  5:25       ` John Wiegley
@ 2015-12-22 13:16         ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-22 13:16 UTC (permalink / raw)
  To: Kaushal Modi; +Cc: Alan Mackenzie, Emacs developers

John Wiegley <jwiegley@gmail.com> writes:

> > Do we have the time to do this after Christmas?
>
> Yes, I certainly do!  A collaboration on this is most welcome.

Great!  Then let's work on this then.


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-18  0:42   ` John Wiegley
                       ` (2 preceding siblings ...)
  2015-12-19 15:44     ` Michael Heerdegen
@ 2015-12-24  5:49     ` Richard Stallman
  2015-12-24  6:15       ` John Wiegley
  3 siblings, 1 reply; 375+ messages in thread
From: Richard Stallman @ 2015-12-24  5:49 UTC (permalink / raw)
  To: John Wiegley; +Cc: acm, emacs-devel, kaushal.modi

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

Is _ as wildcard a UPattern?  In other words, should this

      > (pcase value
      >   (`(_ 1 2)
      >    (message "Matched a list of anything followed by (2 3)")))

really be this?

      > (pcase value
      >   (`(,_ 1 2)
      >    (message "Matched a list of anything followed by (2 3)")))

If so, now the description makes sense.

But I think it might be useful to define _ 
as a QPattern to be equivalent to ,_.
It is true that this would make it an exception among QPatterns,
but one exception might be worth while.

-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-24  5:49     ` Richard Stallman
@ 2015-12-24  6:15       ` John Wiegley
  2015-12-25  5:49         ` Richard Stallman
  0 siblings, 1 reply; 375+ messages in thread
From: John Wiegley @ 2015-12-24  6:15 UTC (permalink / raw)
  To: Richard Stallman; +Cc: acm, emacs-devel, kaushal.modi

>>>>> Richard Stallman <rms@gnu.org> writes:

> Is _ as wildcard a UPattern?  In other words, should this

>> (pcase value
>> (`(_ 1 2)
>> (message "Matched a list of anything followed by (2 3)")))

> really be this?

>> (pcase value
>> (`(,_ 1 2)
>> (message "Matched a list of anything followed by (2 3)")))

> If so, now the description makes sense.

Yes, this is correct.

> But I think it might be useful to define _ 
> as a QPattern to be equivalent to ,_.
> It is true that this would make it an exception among QPatterns,
> but one exception might be worth while.

I don't see much value in doing so; is it just to save a comma?

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-20 18:51                   ` Phillip Lord
@ 2015-12-24 17:46                     ` Michael Heerdegen
  2015-12-24 17:51                       ` John Wiegley
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-24 17:46 UTC (permalink / raw)
  To: Phillip Lord; +Cc: emacs-devel

phillip.lord@russet.org.uk (Phillip Lord) writes:

> I do worry that the syntax of pcase is too complex. As an example
> compare dash.el and pcase:
>
> (-let [(a b _) '(1 2 3)]
>   (list a b))
>
> (pcase-let
>     ((`(,a ,b ,_) '(1 2 3)))
>   (list a b))

-let is only about binding.  pcase, and it's ` macro, is about matching
and binding, including condition testing etc.  Since the latter offers
more features, it is not a surprise that it can be beaten by specialized
tools in special cases wrt the length of the call.

> I've chosen an extreme example here,

I don't think that three additional colons are extreme.

> but the pcase version has a lot of punctuation (and worth remembering
> however familiar the macro expert is with punctuation not all
> emacs-lisp programmers are).

You can just use the `seq' pattern type if you are not familiar with
punctuation.

> > This would mess up the semantics to the worse: `_ would
> > then be a pcase pattern matching anything.  Should '_ also match
> > anything?  But how to match the symbol _ then?  If not, why should `_ be
> > different from '_ when there is no unquoting involved?
> >
> > Or should _ as a QPAT only behave different when used "not at toplevel"?
> > This would be horribly inconsequent: We would get two different types of
> > QPATs: toplevel QPATS, and non-toplevel-QPATS.  That would confuse
> > people even more, a pain to explain and to internalize.
>
> I thought we were not going to mention q-patterns any more!

I never said that.  "qpattern" is a useful term when describing the `
pattern.  What I said was we should avoid the old term "upattern" for
general type pcase patterns.

> I think that too much of the implementation semantics is poking
> through into the syntax.

It's a good thing if the syntax reflects the semantics.  And I don't
think that Stefan had let the semantics be dictated by implementation
details.

> I suspect no one would notice if "_" matched anything inside a
> backquoted list, because it feels natural.

It doesn't feel natural anymore once you have used the thing yourself
and understood the concept.  Yes, pcase does look unusual at the first
look, as does Lisp, but it won't kill you, I promise.  Just give it a
chance.


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-24 17:46                     ` Michael Heerdegen
@ 2015-12-24 17:51                       ` John Wiegley
  2015-12-24 19:10                         ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: John Wiegley @ 2015-12-24 17:51 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel, Phillip Lord

>>>>> Michael Heerdegen <michael_heerdegen@web.de> writes:

>> I thought we were not going to mention q-patterns any more!
> I never said that. "qpattern" is a useful term when describing the `
> pattern. What I said was we should avoid the old term "upattern" for general
> type pcase patterns.

They are both terrible names. Even knowing exactly what they, they don't help
me to think about pcase.

For macros, `foo' gets evaluated, and a quoted foo doesn't. Back-quoting
reverses the idea: `foo' does not get evaluted, and a comma'd foo is.

For patterns, `foo' is computed to determine the pattern, and a quoted foo
matches exactly. Back-quoting reverse the idea: `foo' matches exactly, and a
comma'd foo is evaluated to determine its logical behavior.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-24 17:51                       ` John Wiegley
@ 2015-12-24 19:10                         ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-24 19:10 UTC (permalink / raw)
  To: Phillip Lord; +Cc: emacs-devel

John Wiegley <jwiegley@gmail.com> writes:

> They are both terrible names. Even knowing exactly what they, they
> don't help me to think about pcase.

Indeed.

The doc of pcase now uses only "QPAT" as name of a meta variable
describing the syntax of `.  I find that acceptable, but a better name
might be good.

The manual needs to be updated anyway... though this paragraph:

,----------------------------------------------------------------------
|    There are two kinds of patterns involved in ‘pcase’, called
| _U-patterns_ and _Q-patterns_.  The UPATTERN mentioned above are
| U-patterns and can take the following forms:
| 
| ‘`QPATTERN’
|  [...]
`----------------------------------------------------------------------


somewhat makes me smile ;-)


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-24  6:15       ` John Wiegley
@ 2015-12-25  5:49         ` Richard Stallman
  2015-12-25 14:59           ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Richard Stallman @ 2015-12-25  5:49 UTC (permalink / raw)
  To: John Wiegley; +Cc: acm, emacs-devel, kaushal.modi

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  > > But I think it might be useful to define _ 
  > > as a QPattern to be equivalent to ,_.
  > > It is true that this would make it an exception among QPatterns,
  > > but one exception might be worth while.

  > I don't see much value in doing so; is it just to save a comma?

Yes.

That comma won't add much to the size of the code, and typing it is
not much work.  But I think that avoiding it would make pcase more
attractive and conceptually simpler.


-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-25  5:49         ` Richard Stallman
@ 2015-12-25 14:59           ` Michael Heerdegen
  2015-12-25 16:55             ` John Wiegley
  2015-12-26  6:13             ` Richard Stallman
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-25 14:59 UTC (permalink / raw)
  To: emacs-devel

Richard Stallman <rms@gnu.org> writes:

> That comma won't add much to the size of the code, and typing it is
> not much work.  But I think that avoiding it would make pcase more
> attractive and conceptually simpler.

But it will make it conceptually more complicated, because we would
obfuscate the real semantics.  A tool with inconsistent semantics is
neither simple nor attractive.

If you understand "_" as a "concept" per se in Elisp, I think we agree
that in your case it doesn't fit the expectations of how you think it
would integrate in pcase's semantics.  If we make it just look like some
people guess it would be working, we are not doing them a favor, because
we just spare them to learn the real semantics at the moment.  That will
make it harder to learn pcase, not easier.  If for some people the thing
is different as they first expect, avoiding to let them see that it is
different is not good, just for the sake of making it look more familiar
at the first look.  I think people will then more likely forget commas
at other places in ` patterns.  They will have more problems to
understand more complicated ` patterns.  It is important to understand
that _ is a pattern in pcase, a pattern like any other pcase pattern,
and not something else or special.

OTOH after you have written ",_" for yourself a three times or so,
you'll just have gotten used to it.


Regards,

Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-25 14:59           ` Michael Heerdegen
@ 2015-12-25 16:55             ` John Wiegley
  2015-12-26  6:13             ` Richard Stallman
  1 sibling, 0 replies; 375+ messages in thread
From: John Wiegley @ 2015-12-25 16:55 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

>>>>> Michael Heerdegen <michael_heerdegen@web.de> writes:

> OTOH after you have written ",_" for yourself a three times or so, you'll
> just have gotten used to it.

I agree with Michael; special casing _ might be prettier, but it's actually
more complicated, not less, and in a really subtle way.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-25 14:59           ` Michael Heerdegen
  2015-12-25 16:55             ` John Wiegley
@ 2015-12-26  6:13             ` Richard Stallman
  2015-12-26 17:10               ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Richard Stallman @ 2015-12-26  6:13 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  >   If we make it just look like some
  > people guess it would be working, we are not doing them a favor, because
  > we just spare them to learn the real semantics at the moment.

I am not convinced, but I won't argue about it.

-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-26  6:13             ` Richard Stallman
@ 2015-12-26 17:10               ` Michael Heerdegen
  2015-12-26 20:52                 ` Aaron Ecay
  2015-12-27  2:53                 ` Richard Stallman
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-26 17:10 UTC (permalink / raw)
  To: emacs-devel

Richard Stallman <rms@gnu.org> writes:

> I am not convinced, but I won't argue about it.

I'm open to improvement suggestions, as long as they keep the thing
consistent.

We could try to define a new pattern offering destructuring looking less
"unusual" (though we already have `seq' provided by seq.el which has
very simple semantics).  OTOH I think ` is already quite optimal for the
set of features it offers.

For the _ pattern, I guess we could reinvent it's meaning in pcase in
general.  But I don't see how the resulting semantics could be made
equally simple as it is currently.

Just changing what _ does in pcase's ` to save a comma would IMHO be
what we call in German "verschlimmbessern" (my dictionary says you can
translate that into "disimprove").


Regards,

Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-26 17:10               ` Michael Heerdegen
@ 2015-12-26 20:52                 ` Aaron Ecay
  2015-12-26 23:17                   ` Michael Heerdegen
  2015-12-27  2:53                 ` Richard Stallman
  1 sibling, 1 reply; 375+ messages in thread
From: Aaron Ecay @ 2015-12-26 20:52 UTC (permalink / raw)
  To: Michael Heerdegen, emacs-devel

Hi Michael,

2015ko abenudak 26an, Michael Heerdegen-ek idatzi zuen:
> 
> Richard Stallman <rms@gnu.org> writes:
> 
>> I am not convinced, but I won't argue about it.
> 
> I'm open to improvement suggestions, as long as they keep the thing
> consistent.
> 
> We could try to define a new pattern offering destructuring looking less
> "unusual" (though we already have `seq' provided by seq.el which has
> very simple semantics).  OTOH I think ` is already quite optimal for the
> set of features it offers.
> 
> For the _ pattern, I guess we could reinvent it's meaning in pcase in
> general.  But I don't see how the resulting semantics could be made
> equally simple as it is currently.
> 
> Just changing what _ does in pcase's ` to save a comma would IMHO be
> what we call in German "verschlimmbessern" (my dictionary says you can
> translate that into "disimprove").

Atoms (strings, numbers, and keywords) are simultaneously patterns and
qpatterns.  That is, one writes `(1 2) and not `(,1 ,2) to match a list
containing 1 and 2 (though actually either form works).  Why could _ not
also be shared between the pattern and qpattern classes?

(I guess part of the answer is aesthetics – but I’m pointing out that
the set of patterns and qpatterns is already non-disjoint.)

-- 
Aaron Ecay



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-26 20:52                 ` Aaron Ecay
@ 2015-12-26 23:17                   ` Michael Heerdegen
  2016-01-01  7:57                     ` Eli Zaretskii
       [not found]                     ` <<83y4c9ag06.fsf@gnu.org>
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2015-12-26 23:17 UTC (permalink / raw)
  To: Aaron Ecay; +Cc: emacs-devel

Aaron Ecay <aaronecay@gmail.com> writes:

> Atoms (strings, numbers, and keywords) are simultaneously patterns and
> qpatterns.  That is, one writes `(1 2) and not `(,1 ,2) to match a list
> containing 1 and 2 (though actually either form works).  Why could _ not
> also be shared between the pattern and qpattern classes?

If you consider that ` quotes any element in its argument list unless it
is explicitly unquoted (that's how it actually works), an ATOM becomes
'ATOM, which is equivalent to just ATOM as a pattern.

That one can avoid the comma before atoms inside ` reflects that
equivalence on a different level.

There are more such analogies (for example `something and 'something are
equivalent if something doesn't include a comma) and it's good that they
are there, because it makes the grammar easier to memorize, aka "build a
mental model".  Maybe you can call this "aesthetics" in this regard.

Making _ a qpattern would break the logic in the design: '_ matches the
symbol _, not anything as the _ pattern does  (disjointness of
qpatterns and pcase patterns is a different thing, and I think nobody
cares about that).

Making _ a qpattern wouldn't break pcase, but it would make the thing
less consistent, because there would be a fracture somewhere in the
logic, e.g. if _ is a qpattern matching anything, `_ and '_ would have
different semantics as pcase patterns (the first would be equivalent to
_), or such things.

I would agree to do this anyway if there was a good reason.  Saving a
comma or fitting the expectations of users that haven't yet completely
understood the semantics (I don't mean Phillip by that, I mean users who
want to learn the thing) is not a sufficing reason for obfuscating the
logic behind the design, I think.

Another thing is that I think, and that's what we want to emphasize in
the docs, that qpatterns are conceptually a different thing than pcase
patterns.  Actually, the term "qpattern" has not much meaning at all, it
is only used as a helper to describe the grammar of ` (because it is
recursive, but actually, the grammar is very simple).

A qpattern is either an expression that is compared with equal, or a
placeholder for a real pattern via unquoting.  That's all.  If the
description of ` in pcase would be less formal and e.g. more like the
doc of `backquote', we probably would not even have a name for that.

Anyway, I think it's conceptually a bad thing to merge those two quite
different things.

Just my personal opinion of course.  I've worked with pcase quite a lot
now.  It took some time until I had internalized the concept (which is
why I think it's important to keep it simple).  If others who have used
the tool quite regularly do think it would be a good idea to make _ a
qpattern, let's do it.  But I think we should not hurry modifying a
thing in a way which at the first look seems like a good idea, and we
may regret later.

Sorry for the prose, this was more than you had asked for.


Regards,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-26 17:10               ` Michael Heerdegen
  2015-12-26 20:52                 ` Aaron Ecay
@ 2015-12-27  2:53                 ` Richard Stallman
  1 sibling, 0 replies; 375+ messages in thread
From: Richard Stallman @ 2015-12-27  2:53 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  > Just changing what _ does in pcase's ` to save a comma would IMHO be
  > what we call in German "verschlimmbessern" (my dictionary says you can
  > translate that into "disimprove").

I don't think so.  A special exception for a particular common case
is found in many programming languages, and it is not hard for programmers
to understand.

-- 
Dr Richard Stallman
President, Free Software Foundation (gnu.org, fsf.org)
Internet Hall-of-Famer (internethalloffame.org)
Skype: No way! See stallman.org/skype.html.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2015-12-26 23:17                   ` Michael Heerdegen
@ 2016-01-01  7:57                     ` Eli Zaretskii
  2016-01-01 17:46                       ` John Wiegley
       [not found]                     ` <<83y4c9ag06.fsf@gnu.org>
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2016-01-01  7:57 UTC (permalink / raw)
  To: Michael Heerdegen, John Wiegley; +Cc: emacs-devel

Btw, could someone please tell what are the benefits of using 'pcase'
in snippets like this one:

     (pcase skip
       (`nil nil)
       (`0 t)
       (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))

How is this different from using 'cond' in trivial ways?

(I see quite a few of such uses of 'pcase' in the sources, and when I
read them, I always wonder what is it that I'm missing about that
code.)

TIA



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
       [not found]                     ` <<83y4c9ag06.fsf@gnu.org>
@ 2016-01-01 15:18                       ` Drew Adams
  0 siblings, 0 replies; 375+ messages in thread
From: Drew Adams @ 2016-01-01 15:18 UTC (permalink / raw)
  To: Eli Zaretskii, Michael Heerdegen, John Wiegley; +Cc: emacs-devel

> Btw, could someone please tell what are the benefits of using 'pcase'
> in snippets like this one:
> 
>      (pcase skip
>        (`nil nil)
>        (`0 t)
>        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
> 
> How is this different from using 'cond' in trivial ways?
> 
> (I see quite a few of such uses of 'pcase' in the sources, and when I
> read them, I always wonder what is it that I'm missing about that
> code.)

FWIW, I noticed the same thing a while ago.  Seems like someone
went on a `pcase' rampage, or perhaps was just overly enthusiastic
with a new toy.  ("Ooooh - shiny!")

We should use `pcase' when it really helps, including helps make
reading the code easier.  And hopefully some real use of pattern
matching would typically be involved (i.e., decomposition, not
just matching `nil' or `0' or "abc" literally).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-01  7:57                     ` Eli Zaretskii
@ 2016-01-01 17:46                       ` John Wiegley
  2016-01-01 18:39                         ` David Kastrup
  2016-01-02  3:51                         ` Drew Adams
  0 siblings, 2 replies; 375+ messages in thread
From: John Wiegley @ 2016-01-01 17:46 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

>>>>> Eli Zaretskii <eliz@gnu.org> writes:

>      (pcase skip
>        (`nil nil)
>        (`0 t)
>        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))

(cond ((null skip))
      ((eq skip 0) t)
      (t (setq i (+ i skip -1)) 
         (funcall get-next-frame)))

Not much difference. Also, `0 could just be 0.

One thing it does do: avoids repeating "skip" in the first two tests. That's
the only merit I can see, but would have been more worthwhile if there were,
say, 10 value tests.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-01 17:46                       ` John Wiegley
@ 2016-01-01 18:39                         ` David Kastrup
  2016-01-01 19:05                           ` Daniel Colascione
  2016-01-02  1:15                           ` Richard Copley
  2016-01-02  3:51                         ` Drew Adams
  1 sibling, 2 replies; 375+ messages in thread
From: David Kastrup @ 2016-01-01 18:39 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

John Wiegley <jwiegley@gmail.com> writes:

>>>>>> Eli Zaretskii <eliz@gnu.org> writes:
>
>>      (pcase skip
>>        (`nil nil)
>>        (`0 t)
>>        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
>
> (cond ((null skip))
>       ((eq skip 0) t)
>       (t (setq i (+ i skip -1)) 
>          (funcall get-next-frame)))
>
> Not much difference.

If skip is nil, the first returns probably nil and the second t.  One
could probably do

(and skip
     (or (eql skip 0)
         (setq ...)))

I'm not fond of eq for numeric comparisons: that's an Elispism.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-01 18:39                         ` David Kastrup
@ 2016-01-01 19:05                           ` Daniel Colascione
  2016-01-02  8:16                             ` Eli Zaretskii
  2016-01-02  1:15                           ` Richard Copley
  1 sibling, 1 reply; 375+ messages in thread
From: Daniel Colascione @ 2016-01-01 19:05 UTC (permalink / raw)
  To: David Kastrup, Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

[-- Attachment #1: Type: text/plain, Size: 755 bytes --]

On 01/01/2016 10:39 AM, David Kastrup wrote:
> John Wiegley <jwiegley@gmail.com> writes:
> 
>>>>>>> Eli Zaretskii <eliz@gnu.org> writes:
>>
>>>      (pcase skip
>>>        (`nil nil)
>>>        (`0 t)
>>>        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
>>
>> (cond ((null skip))
>>       ((eq skip 0) t)
>>       (t (setq i (+ i skip -1)) 
>>          (funcall get-next-frame)))
>>
>> Not much difference.
> 
> If skip is nil, the first returns probably nil and the second t.  One
> could probably do
> 
> (and skip
>      (or (eql skip 0)
>          (setq ...)))
> 
> I'm not fond of eq for numeric comparisons: that's an Elispism.

That's true, but I think it's too pervasive to change now, so why fight it?


[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 819 bytes --]

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-01 18:39                         ` David Kastrup
  2016-01-01 19:05                           ` Daniel Colascione
@ 2016-01-02  1:15                           ` Richard Copley
  2016-01-02  3:50                             ` Drew Adams
  1 sibling, 1 reply; 375+ messages in thread
From: Richard Copley @ 2016-01-02  1:15 UTC (permalink / raw)
  To: David Kastrup; +Cc: Michael Heerdegen, Eli Zaretskii, Emacs Development

On 1 January 2016 at 18:39, David Kastrup <dak@gnu.org> wrote:
> John Wiegley <jwiegley@gmail.com> writes:
>
>>>>>>> Eli Zaretskii <eliz@gnu.org> writes:
>>
>>>      (pcase skip
>>>        (`nil nil)
>>>        (`0 t)
>>>        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
>>
>> (cond ((null skip))
>>       ((eq skip 0) t)
>>       (t (setq i (+ i skip -1))
>>          (funcall get-next-frame)))
>>
>> Not much difference.
>
> If skip is nil, the first returns probably nil and the second t.  One
> could probably do
>
> (and skip
>      (or (eql skip 0)
>          (setq ...)))

True, but only an unintentional slip. I think the charitable interpretation is

(cond
  ((null skip) nil)
  [...])

> I'm not fond of eq for numeric comparisons: that's an Elispism.

That's Elisp programs for you. I'd have used zerop.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-02  1:15                           ` Richard Copley
@ 2016-01-02  3:50                             ` Drew Adams
  0 siblings, 0 replies; 375+ messages in thread
From: Drew Adams @ 2016-01-02  3:50 UTC (permalink / raw)
  To: Richard Copley, David Kastrup
  Cc: Michael Heerdegen, Eli Zaretskii, Emacs Development

> > I'm not fond of eq for numeric comparisons: that's an Elispism.
> 
> That's Elisp programs for you. I'd have used zerop.

Only if you can be sure that `skip' is a number, or you want to
raise an error if it is not.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-01 17:46                       ` John Wiegley
  2016-01-01 18:39                         ` David Kastrup
@ 2016-01-02  3:51                         ` Drew Adams
  1 sibling, 0 replies; 375+ messages in thread
From: Drew Adams @ 2016-01-02  3:51 UTC (permalink / raw)
  To: John Wiegley, Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

> >      (pcase skip
> >        (`nil nil)
> >        (`0 t)
> >        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))
> 
> (cond ((null skip))
>       ((eq skip 0) t)
>       (t (setq i (+ i skip -1))
>          (funcall get-next-frame)))

Agreed.  If you don't need decomposition by pattern matching,
why would you need `pcase'?

(But as pointed out, the first clause should be ((null skip) nil).

(The `cond' is 10 chars more to type in this case, not counting
insignificant whitespace.  But that is not important.)

Or:

(cl-case skip
  ((nil) nil)
  (0 t)
  (t (setq i (+ i skip -1)) (funcall get-next-frame)))

(Same number of chars as `pcase'.  Or 3 fewer, if you use alias\
`case'.  But, again, not important.)

Or:

(and skip  (or (eql 0 skip)
               (progn (setq i  (+ i skip -1))
                      (funcall get-next-frame))))

(3 chars more than the `pcase'.  But not important.)

> Not much difference. Also, `0 could just be 0.
> 
> One thing it does do: avoids repeating "skip" in the first two tests. That's
> the only merit I can see, but would have been more worthwhile if there were,
> say, 10 value tests.

The same is true of `cl-case' (it is one of the reasons for
that macro).  But otherwise, just use `let':

(let ((sk  skip))
  (and sk  (or (eql 0 sk)
               (progn (setq i  (+ i skip -1))
                      (funcall get-next-frame))))



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-01 19:05                           ` Daniel Colascione
@ 2016-01-02  8:16                             ` Eli Zaretskii
  2016-01-02  8:35                               ` David Kastrup
  2016-01-03  0:41                               ` Dmitry Gutov
  0 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2016-01-02  8:16 UTC (permalink / raw)
  To: Daniel Colascione; +Cc: michael_heerdegen, dak, emacs-devel

> From: Daniel Colascione <dancol@dancol.org>
> Date: Fri, 1 Jan 2016 11:05:31 -0800
> Cc: Michael Heerdegen <michael_heerdegen@web.de>, emacs-devel@gnu.org
> 
> >>>      (pcase skip
> >>>        (`nil nil)
> >>>        (`0 t)
> >>>        (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
> >>
> >> (cond ((null skip))
> >>       ((eq skip 0) t)
> >>       (t (setq i (+ i skip -1)) 
> >>          (funcall get-next-frame)))
> >>
> >> Not much difference.
> > 
> > If skip is nil, the first returns probably nil and the second t.  One
> > could probably do
> > 
> > (and skip
> >      (or (eql skip 0)
> >          (setq ...)))
> > 
> > I'm not fond of eq for numeric comparisons: that's an Elispism.
> 
> That's true, but I think it's too pervasive to change now, so why fight it?

Who said anything about fighting?  I just asked if there was anything
there that I was missing.

Now that I know there isn't, I can convert such code to using 'cond'
whenever I feel like it.  Like we do with whitespace changes.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-02  8:16                             ` Eli Zaretskii
@ 2016-01-02  8:35                               ` David Kastrup
  2016-01-03  0:19                                 ` Michael Heerdegen
  2016-01-03  0:41                               ` Dmitry Gutov
  1 sibling, 1 reply; 375+ messages in thread
From: David Kastrup @ 2016-01-02  8:35 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: michael_heerdegen, Daniel Colascione, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

>> From: Daniel Colascione <dancol@dancol.org>
>> Date: Fri, 1 Jan 2016 11:05:31 -0800
>> Cc: Michael Heerdegen <michael_heerdegen@web.de>, emacs-devel@gnu.org

[pcase stuff]

>> > One could probably do
>> > 
>> > (and skip
>> >      (or (eql skip 0)
>> >          (setq ...)))
>> > 
>> > I'm not fond of eq for numeric comparisons: that's an Elispism.
>> 
>> That's true, but I think it's too pervasive to change now, so why
>> fight it?
>
> Who said anything about fighting?  I just asked if there was anything
> there that I was missing.

I am pretty sure Daniel was referring to my eq/eql side remark.
I certainly hope that "pervasive" is not a proper characterization of
pcase use yet though I haven't checked.

> Now that I know there isn't, I can convert such code to using 'cond'
> whenever I feel like it.  Like we do with whitespace changes.

Some of the quoted pcase examples indeed felt like the "if your
preferred tool is a hammer, every problem looks like a nail" phenomenon.

There certainly is a case for liberal use of complex complexity-taming
constructs (for example, overall I can appreciate how cl-loop
straightens out a lot of awkward loop constructs even though its syntax
is not really Elisp-like).  But when a simple construct is a perfect
fit, it's not helping understanding.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-02  8:35                               ` David Kastrup
@ 2016-01-03  0:19                                 ` Michael Heerdegen
  2016-01-03  2:47                                   ` Drew Adams
                                                     ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-03  0:19 UTC (permalink / raw)
  To: David Kastrup; +Cc: Eli Zaretskii, Daniel Colascione, emacs-devel

David Kastrup <dak@gnu.org> writes:

> Some of the quoted pcase examples indeed felt like the "if your
> preferred tool is a hammer, every problem looks like a nail"
> phenomenon.

Ironically, the same applies to Emacs itself  ;-)

> There certainly is a case for liberal use of complex complexity-taming
> constructs (for example, overall I can appreciate how cl-loop
> straightens out a lot of awkward loop constructs even though its syntax
> is not really Elisp-like).  But when a simple construct is a perfect
> fit, it's not helping understanding.

I don't see how a pcase used like a cl-case - as in the quoted example -
is any harder to read or understand.

And of course it has also advantages to use pcase in such cases.  If you
want to change the code or try things and you suddenly want a feature
from pcase, you don't have to rewrite the whole thing.

It just...arguable what you prefer.  What I find a bit irritating is
this seemingly upcoming kind of agreement "Please, let's all avoid this
thing, ok? - it's frightening!" I read between the lines.  Sorry if my
impression is wrong.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-02  8:16                             ` Eli Zaretskii
  2016-01-02  8:35                               ` David Kastrup
@ 2016-01-03  0:41                               ` Dmitry Gutov
  2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
  2016-01-03  3:47                                 ` Eli Zaretskii
  1 sibling, 2 replies; 375+ messages in thread
From: Dmitry Gutov @ 2016-01-03  0:41 UTC (permalink / raw)
  To: Eli Zaretskii, Daniel Colascione; +Cc: michael_heerdegen, dak, emacs-devel

On 01/02/2016 10:16 AM, Eli Zaretskii wrote:

> Now that I know there isn't, I can convert such code to using 'cond'
> whenever I feel like it.  Like we do with whitespace changes.

FWIW, converting that kind of pcase form to a cond, to my eyes, would 
look like replacing (when ...) with (if ... (progn ...))).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  0:41                               ` Dmitry Gutov
@ 2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
  2016-01-03  1:21                                   ` Dmitry Gutov
                                                     ` (2 more replies)
  2016-01-03  3:47                                 ` Eli Zaretskii
  1 sibling, 3 replies; 375+ messages in thread
From: Lars Magne Ingebrigtsen @ 2016-01-03  1:07 UTC (permalink / raw)
  To: Dmitry Gutov
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, dak,
	emacs-devel

Dmitry Gutov <dgutov@yandex.ru> writes:

> On 01/02/2016 10:16 AM, Eli Zaretskii wrote:
>
>> Now that I know there isn't, I can convert such code to using 'cond'
>> whenever I feel like it.  Like we do with whitespace changes.
>
> FWIW, converting that kind of pcase form to a cond, to my eyes, would
> look like replacing (when ...) with (if ... (progn ...))).

Well, I'd say that pcase is kinda awkward because you can't tell by
skimming whether it's complex or not (which is something it shares with
cond, in a way).  Take for instance the following I was reading in
url-http (simplified and way shortened):

             (pcase status-symbol
               (`unauthorized                   ; 401
                (url-http-handle-authentication nil))
               (`payment-required              ; 402
                (url-mark-buffer-as-dead buffer)
                (error "Somebody wants you to give them money"))
               (`forbidden                      ; 403
                t)
               (`not-found                      ; 404
                t)
               (`method-not-allowed             ; 405
                t)
               ...)

The only way you'll know whether `status-symbol' is really a symbol, and
all the cases are really symbols, is by reading the entire thing.  The
44th case could have been (_ foo bar zot), for instance.

In Common Lisp, you'd say

             (case status-symbol
               (unauthorized                    ; 401
                (url-http-handle-authentication nil))
               (payment-required              ; 402
                (url-mark-buffer-as-dead buffer)
                (error "Somebody wants you to give them money"))
               (forbidden                       ; 403
                t)
               (not-found                       ; 404
                t)
               (method-not-allowed              ; 405
                t)
               ...)

and you'd know that this was a simple `eql' thing going on here.

I kinda liked pcase at first, but the more I see of the pcase language,
the more sceptical I get.  I'm beginning to wonder whether the whole
thing is a misfeature that should be replaced with several separate
operators.

-- 
(domestic pets only, the antidote for overdose, milk.)
   bloggy blog: http://lars.ingebrigtsen.no



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
@ 2016-01-03  1:21                                   ` Dmitry Gutov
  2016-01-03  2:49                                     ` Drew Adams
  2016-01-03  1:32                                   ` Michael Heerdegen
  2016-01-03  2:48                                   ` Drew Adams
  2 siblings, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2016-01-03  1:21 UTC (permalink / raw)
  To: Lars Magne Ingebrigtsen
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, dak,
	emacs-devel

On 01/03/2016 03:07 AM, Lars Magne Ingebrigtsen wrote:

> The only way you'll know whether `status-symbol' is really a symbol, and
> all the cases are really symbols, is by reading the entire thing.  The
> 44th case could have been (_ foo bar zot), for instance.

How is that different from cond? If I have cond like this:

(cond
  ((eq status-symbol 'unauthorized)
   (url-http-handle-authentication nil))
  ((eq status-symbol 'payment-required)
   (url-mark-buffer-as-dead buffer)
   (error "Somebody wants you to give them money"))
  ...)

...you'll also have to read until its end to find out for sure whether 
the variable name lies or not:

(cond
  ((eq status-symbol 'unauthorized)
   (url-http-handle-authentication nil))
  ((eq status-symbol 'payment-required)
   (url-mark-buffer-as-dead buffer)
   (error "Somebody wants you to give them money"))
  ((memq 'zomg status-symbol)
   (give-away all-moneys)))

> In Common Lisp, you'd say

cl-case is more restricted, yes, but I thought this discussion was about 
how pcase is worse than cond.

> I kinda liked pcase at first, but the more I see of the pcase language,
> the more sceptical I get.  I'm beginning to wonder whether the whole
> thing is a misfeature that should be replaced with several separate
> operators.

You mean pattern matching? A lot of language and library designers would 
disagree with you.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
  2016-01-03  1:21                                   ` Dmitry Gutov
@ 2016-01-03  1:32                                   ` Michael Heerdegen
  2016-01-03  2:48                                   ` Drew Adams
  2 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-03  1:32 UTC (permalink / raw)
  To: Lars Magne Ingebrigtsen
  Cc: Eli Zaretskii, Daniel Colascione, emacs-devel, dak, Dmitry Gutov

Lars Magne Ingebrigtsen <larsi@gnus.org> writes:

> Well, I'd say that pcase is kinda awkward because you can't tell by
> skimming whether it's complex or not (which is something it shares with
> cond, in a way).  Take for instance the following I was reading in
> url-http (simplified and way shortened):
>
>              (pcase status-symbol
>                (`unauthorized                   ; 401
>                 (url-http-handle-authentication nil))
>                (`payment-required              ; 402
>                 (url-mark-buffer-as-dead buffer)
>                 (error "Somebody wants you to give them money"))
>                (`forbidden                      ; 403
>                 t)
>                (`not-found                      ; 404
>                 t)
>                (`method-not-allowed             ; 405
>                 t)
>                ...)
>
> The only way you'll know whether `status-symbol' is really a symbol, and
> all the cases are really symbols, is by reading the entire thing.  The
> 44th case could have been (_ foo bar zot), for instance.

That code indeed looks weird.  But you can also write similarly weird
code with `cond'.

> I kinda liked pcase at first, but the more I see of the pcase language,
> the more sceptical I get.  I'm beginning to wonder whether the whole
> thing is a misfeature that should be replaced with several separate
> operators.

The concept (one can combine different types of things and tests -
destructuring, predicate testing, matching against constants etc.) has
it's pros and cons.  In cases where one single tool doesn't fit, it is a
very good thing when the code doesn't need to nest different types of
tools, and the layout can concentrate on the different cases.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-03  0:19                                 ` Michael Heerdegen
@ 2016-01-03  2:47                                   ` Drew Adams
  2016-01-03  3:21                                     ` Michael Heerdegen
  2016-01-03  3:45                                   ` Eli Zaretskii
  2016-01-03  9:03                                   ` David Kastrup
  2 siblings, 1 reply; 375+ messages in thread
From: Drew Adams @ 2016-01-03  2:47 UTC (permalink / raw)
  To: Michael Heerdegen, David Kastrup
  Cc: Eli Zaretskii, Daniel Colascione, emacs-devel

> I don't see how a pcase used like a cl-case - as in the quoted example -
> is any harder to read or understand.
> 
> And of course it has also advantages to use pcase in such cases.  If you
> want to change the code or try things and you suddenly want a feature
> from pcase, you don't have to rewrite the whole thing.
> 
> It just...arguable what you prefer.

Yes.  So let me argue ;-) in favor of using `pcase' only, or
mainly, when decomposition pattern-matching is used, and not
just for literal tests.

Your point is that `pcase' is more general, so if you want to
later add a clause that does make use of decomposition
pattern-matching then it's easy to do so.  That is a good
argument.

It's not the argument that persuades me, however.  I generally
come down on the side of trying to have the most readable code,
even at the cost of more maintenance work, in terms of typing.

Why?  Because I think that code readability is primary, and
the biggest maintenance burden is not typing but understanding.

Why do I think that a control structure that tests only
literals is clearer for literal-testing than one that also
uses decomposition patterns?

Because the former necessarily shouts that there are ONLY literal
tests here.  `pcase' is harder to parse not just because some of
us might not be as used to it, but also precisely because of its
generality.  You have to look closely, to see whether there might
be some decomposition pattern-matching going on.

(Occam's razor.  Einstein's as-simple-as-possible-but-no-simpler.)

Because `pcase' is so general that it can handle also fancy
patterns, its syntax is more involved - overkill.  Not overkill
for the cases where it makes sense and takes advantage of pattern
matching.  But overkill for the mundane, literal-matching cases.

I prefer to use the simpler `cl-case' or whatever when possible,
because it says, loud-and-clear, to a reader: "Nothing fancy here."
The reader is the one who counts, for me, not the writer.

And I don't mind having to later rewrite the code if a feature
change or bug fix makes it possible to really take advantage of
what `pcase' has to offer.  Yes, that's an added burden, but one
that I, personally, don't mind.  (I'm talking about me and my
code.  I can understand, if Emacs maintainers feel differently
about the distributed Emacs code.)

IOW, I echo the hammer=>nail reflection that David made.  There
is no need to think that `pcase' _needs_ to be used everywhere,
just because it _can_ be used everywhere.  (And I feel the same
about `loop', FWIW.)

Just one opinion, of course.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
  2016-01-03  1:21                                   ` Dmitry Gutov
  2016-01-03  1:32                                   ` Michael Heerdegen
@ 2016-01-03  2:48                                   ` Drew Adams
  2016-01-03  3:11                                     ` Noam Postavsky
  2 siblings, 1 reply; 375+ messages in thread
From: Drew Adams @ 2016-01-03  2:48 UTC (permalink / raw)
  To: Lars Magne Ingebrigtsen, Dmitry Gutov
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, dak,
	emacs-devel

> Well, I'd say that pcase is kinda awkward because you can't tell by
> skimming whether it's complex or not

100% agreement.  That's really the point, for me.

* `pcase' shouts: "This might be complicated.  Better look closely."

* `cond' and `cl-case' and `if' ... shout: "Nothing fancy here.
  We're only testing literals"

>              (pcase status-symbol ...)
> 
> The only way you'll know whether `status-symbol' is really a symbol, and
> all the cases are really symbols, is by reading the entire thing.  The
> 44th case could have been (_ foo bar zot), for instance.
> 
>              (case status-symbol ...)
> 
> and you'd know that this was a simple `eql' thing going on here.
> 
> I kinda liked pcase at first, but the more I see of the pcase language,

Good one.  That's really it.  When you have a very general
construct it can begin to be its own _language_.  This is the
case for UNIX `find', for instance, and for Common Lisp `loop'.

That's not to say that using such a language can't be useful.
It's only to say that I use it when it is most useful.  If I
don't need it then I tend not to use it.

> the more sceptical I get.  I'm beginning to wonder whether the whole
> thing is a misfeature that should be replaced with several separate
> operators.

That's an interesting question.  Maybe you have something in mind?
Could be an interesting thread, even if it ultimately went nowhere.
Certainly, something like `pcase' provides a good deal of food for
thought, which can also mean room for improvement.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-03  1:21                                   ` Dmitry Gutov
@ 2016-01-03  2:49                                     ` Drew Adams
  2016-01-03 10:49                                       ` David Kastrup
  0 siblings, 1 reply; 375+ messages in thread
From: Drew Adams @ 2016-01-03  2:49 UTC (permalink / raw)
  To: Dmitry Gutov, Lars Magne Ingebrigtsen
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, dak,
	emacs-devel

> cl-case is more restricted, yes, but I thought this discussion was about
> how pcase is worse than cond.

I don't think so.  To me, this discussion is about whether to use `pcase':

* Only when it really offers something,
* All the time, everywhere,
* Or something in between (what?).

> > I kinda liked pcase at first, but the more I see of the pcase language,
> > the more sceptical I get.  I'm beginning to wonder whether the whole
> > thing is a misfeature that should be replaced with several separate
> > operators.
> 
> You mean pattern matching? A lot of language and library designers would
> disagree with you.

Decomposition pattern-matching.  Use it when it helps.

Literal "pattern" matching does not require `pcase'.  Should
`pcase' be used for such mundane cases anyway, since it can be?

That's the question that I think is being discussed.  Whether
wholesale replacement of `cond', `case', `if', etc. by `pcase'
is a good idea, just because it could do the job.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  2:48                                   ` Drew Adams
@ 2016-01-03  3:11                                     ` Noam Postavsky
  2016-01-03  3:18                                       ` Dmitry Gutov
  2016-01-03  3:45                                       ` Drew Adams
  0 siblings, 2 replies; 375+ messages in thread
From: Noam Postavsky @ 2016-01-03  3:11 UTC (permalink / raw)
  To: Drew Adams
  Cc: dak, michael_heerdegen, emacs-devel, Dmitry Gutov,
	Lars Magne Ingebrigtsen, Daniel Colascione, Eli Zaretskii

On Sat, Jan 2, 2016 at 9:48 PM, Drew Adams <drew.adams@oracle.com> wrote:
>> Well, I'd say that pcase is kinda awkward because you can't tell by
>> skimming whether it's complex or not
>
> 100% agreement.  That's really the point, for me.
>
> * `pcase' shouts: "This might be complicated.  Better look closely."
>
> * `cond' and `cl-case' and `if' ... shout: "Nothing fancy here.
>   We're only testing literals"

I don't see how `cond' and `if' shout that at all, they can test
anything, no restrictions. I would prefer `pcase` over `cond` (if
there were some reason to exclude `cl-case') because the code is
shorter and simpler so I can skim it faster than the equivalent
`cond'.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  3:11                                     ` Noam Postavsky
@ 2016-01-03  3:18                                       ` Dmitry Gutov
  2016-01-03  3:55                                         ` John Wiegley
  2016-01-03  3:45                                       ` Drew Adams
  1 sibling, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2016-01-03  3:18 UTC (permalink / raw)
  To: Noam Postavsky, Drew Adams
  Cc: dak, michael_heerdegen, emacs-devel, Lars Magne Ingebrigtsen,
	Daniel Colascione, Eli Zaretskii

On 01/03/2016 05:11 AM, Noam Postavsky wrote:

> (if
> there were some reason to exclude `cl-case')

It's a minor thing, but `pcase' is actually faster at macro-expansion, 
in addition to being more powerful. Try:

(benchmark 10000 '(cl-case 1 (2 3) (4 5) (1 6)))

(benchmark 10000 '(pcase 1 (2 3) (4 5) (1 6)))



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  2:47                                   ` Drew Adams
@ 2016-01-03  3:21                                     ` Michael Heerdegen
  2016-01-03  3:46                                       ` Drew Adams
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-03  3:21 UTC (permalink / raw)
  To: emacs-devel

Drew Adams <drew.adams@oracle.com> writes:

> Just one opinion, of course.

I think I do the same most of the time.

Probably some examples of pcase in the sources are not good code, and
not good examples of how work with pcase.  You can write good and bad
pcase code, code that emphasizes what it's doing, and code that looks
more like the result of a mechanical replacement.  Maybe the latter is
the case for a lot of places in the sources.

But I think I agree to the goal to use cl-case where possible.  cond is
a bit different, since it is as powerful as pcase (in principle), so
when you see a cond, you can't assume much about what is (not) done
there.  pcase is not only useful when destructuring is involved (though
it is the most important feature).

The often cited case of a long list of conditions that only tests for
equality for a longer list of symbols is a good example, but also an
extreme one, because this is a case that doesn't appear so often in
practise.

Oh, and I also think there are a lot of places in the sources that would
get simpler when using pcase.


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  0:19                                 ` Michael Heerdegen
  2016-01-03  2:47                                   ` Drew Adams
@ 2016-01-03  3:45                                   ` Eli Zaretskii
  2016-01-03  4:21                                     ` Michael Heerdegen
  2016-01-03  9:03                                   ` David Kastrup
  2 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2016-01-03  3:45 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: dak, dancol, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Eli Zaretskii <eliz@gnu.org>,  Daniel Colascione <dancol@dancol.org>,  emacs-devel@gnu.org
> Date: Sun, 03 Jan 2016 01:19:55 +0100
> 
> I don't see how a pcase used like a cl-case - as in the quoted example -
> is any harder to read or understand.

Are you serious?  We've just had a long discussion about its missing
or incomplete or inadequate documentation, including a long dispute
about whether it would be better to quote _.

My summary of that discussion is that the syntax is complicated and
quite weird.

Using such a beast where it is not required makes reading harder
because it requires the reader to understand its syntax, if nothing
else.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-03  3:11                                     ` Noam Postavsky
  2016-01-03  3:18                                       ` Dmitry Gutov
@ 2016-01-03  3:45                                       ` Drew Adams
  1 sibling, 0 replies; 375+ messages in thread
From: Drew Adams @ 2016-01-03  3:45 UTC (permalink / raw)
  To: Noam Postavsky
  Cc: dak, michael_heerdegen, emacs-devel, Dmitry Gutov,
	Lars Magne Ingebrigtsen, Daniel Colascione, Eli Zaretskii

> >> Well, I'd say that pcase is kinda awkward because you can't tell by
> >> skimming whether it's complex or not
> >
> > 100% agreement.  That's really the point, for me.
> >
> > * `pcase' shouts: "This might be complicated.  Better look closely."
> >
> > * `cond' and `cl-case' and `if' ... shout: "Nothing fancy here.
> >   We're only testing literals"
> 
> I don't see how `cond' and `if' shout that at all, they can test
> anything, no restrictions. I would prefer `pcase` over `cond` (if
> there were some reason to exclude `cl-case') because the code is
> shorter and simpler so I can skim it faster than the equivalent
> `cond'.

I tried to consistently contrast what they do with the
"_decomposition pattern-matching_" that `pcase' can do (in
addition to only matching literal "patterns" - `eql').

Sorry if that wasn't clear.  Of course the ordinary control
structures can perform any kind of test.  That's not in
question.  But when it comes to _pattern matching_ (e.g.,
for `cl-case'), only literal matches are done.

`pcase' is unique among control structures in being able to
decompose what a pattern matches, i.e., to bind local variables.
This is really what it has to offer (IMHO).  The rest is nothing
new.  And I would (personally) typically use it only when it
was doing that.

You could get `pcase' behavior with just a decomposing
let combined with the classic control structures.  You
might even argue that that might be clearer.

(I used to use a Lisp, many moon ago, that had such a let,
but I've forgotten what it was.  Maybe it was something I
wrote, instead of being part of the language - I don't recall.)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-03  3:21                                     ` Michael Heerdegen
@ 2016-01-03  3:46                                       ` Drew Adams
  2016-01-03  5:17                                         ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Drew Adams @ 2016-01-03  3:46 UTC (permalink / raw)
  To: Michael Heerdegen, emacs-devel

> You can write good and bad
> pcase code, code that emphasizes what it's doing, and code that looks
> more like the result of a mechanical replacement.

+1 for that formulation: "code that emphasizes what it's doing".
When I see a `pcase' I want it to be telling me that there is
some local-binding (decomposition pattern-matching) going on.

> But I think I agree to the goal to use cl-case where possible.

> cond is a bit different,

Definitely different from `cl-case', since it does not do any
pattern-matching (except perhaps by explicit testing with a
predicate).

> since it is as powerful as pcase (in principle),

See previous - it does not do pattern-matching.  And that is
the particular "power" of `pcase' - what it really has to
offer (IMO).

> so when you see a cond, you can't assume much about what is (not) done
> there.

> pcase is not only useful when destructuring is involved (though
> it is the most important feature).

I disagree.  I think it is only useful when destructuring is
involved.  If it is just doing literal pattern-matching then
it offers nothing more than does `cl-case'.

(Unless it lets you change the equality predicate (does it?).
That's one thing that I wish `cl-case' (and Common lisp `case')
would let you do: specify something a comparer other than `eql'.)

> The often cited case of a long list of conditions that only tests for
> equality for a longer list of symbols is a good example,

I don't know what example you mean.  Do you mean testing
for equality against more than one symbol, as in multiple
`cl-case's?  Or testing the same symbol value more than once
(just use a `let')?

> but also an extreme one, because this is a case that doesn't appear
> so often in practise.
> 
> Oh, and I also think there are a lot of places in the sources that would
> get simpler when using pcase.

To vague to judge whether you are right.  But maybe so, if you
mean taking advantage of destructuring.

The same would be true of a let construct that only destructures
(e.g., `destructuring-bind').



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  0:41                               ` Dmitry Gutov
  2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
@ 2016-01-03  3:47                                 ` Eli Zaretskii
       [not found]                                   ` <56889EC3.3040108@yandex.ru>
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2016-01-03  3:47 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: michael_heerdegen, dancol, dak, emacs-devel

> Cc: michael_heerdegen@web.de, dak@gnu.org, emacs-devel@gnu.org
> From: Dmitry Gutov <dgutov@yandex.ru>
> Date: Sun, 3 Jan 2016 02:41:22 +0200
> 
> On 01/02/2016 10:16 AM, Eli Zaretskii wrote:
> 
> > Now that I know there isn't, I can convert such code to using 'cond'
> > whenever I feel like it.  Like we do with whitespace changes.
> 
> FWIW, converting that kind of pcase form to a cond, to my eyes, would 
> look like replacing (when ...) with (if ... (progn ...))).

The syntax of 'when' is nowhere as complex as that of 'pcase'.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  3:18                                       ` Dmitry Gutov
@ 2016-01-03  3:55                                         ` John Wiegley
  0 siblings, 0 replies; 375+ messages in thread
From: John Wiegley @ 2016-01-03  3:55 UTC (permalink / raw)
  To: emacs-devel

[-- Attachment #1: Type: text/plain, Size: 561 bytes --]

We're now entering emacs-tangents territory here. We should discuss the merits
of various programming constructions over on that list, since it is has no
objective answer here.

We are all volunteers. Use whichever construction suits you best for the code
you write or maintain. Do not mechanically translate what others have written
to your preferred style unless there is a genuine need to do so.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 629 bytes --]

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  3:45                                   ` Eli Zaretskii
@ 2016-01-03  4:21                                     ` Michael Heerdegen
  2016-01-03  9:13                                       ` David Kastrup
  2016-01-03 15:29                                       ` Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-03  4:21 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: dak, dancol, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> Are you serious?  We've just had a long discussion about its missing
> or incomplete or inadequate documentation,

I know that, but that we can and want to fix, so it is no argument about
whether pcase is really eval or not.

> including a long dispute about whether it would be better to quote _.

Yes, and...???

> My summary of that discussion is that the syntax is complicated and
> quite weird.

Where did we at all talk about the syntax?

Or do you just mean those examples that were shorter than with any other
tool?  Or those that were faster?

> Using such a beast where it is not required makes reading harder
> because it requires the reader to understand its syntax, if nothing
> else.

And that's the real problem: (some) people refrain to try to understand
the syntax and prefer to complain.  The syntax is very simple for its
expressiveness.  But maybe I'm just obsessed by the beast.

Sorry, I give up.  pcase seems to scare off people somehow.  If 50
percent of the people are not able to cope with the thing, for whatever
reason, and get stalled whenever they see it, I think we probably can't
use it.  A pity.

Is it even worth to update the docs of pcase?  Will anyone from those
antagonizing it really try to learn how the thing is supposed to be
used?  I've got the feeling some people anyway prefer to gain their
knowledge from such pcase-bashing discussions.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  3:46                                       ` Drew Adams
@ 2016-01-03  5:17                                         ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-03  5:17 UTC (permalink / raw)
  To: emacs-devel

Drew Adams <drew.adams@oracle.com> writes:

> > pcase is not only useful when destructuring is involved (though
> > it is the most important feature).
>
> I disagree.  I think it is only useful when destructuring is
> involved.  If it is just doing literal pattern-matching then
> it offers nothing more than does `cl-case'.

Well, there are some more pattern types available, and you can all
combine them.

> (Unless it lets you change the equality predicate (does it?).

No, but you can just use (pred (my-eq thing)) as pattern.  That would
test whether `thing' is `my-eq' to the object.

> > The often cited case of a long list of conditions that only tests
> > for equality for a longer list of symbols is a good example,
>
> I don't know what example you mean.  Do you mean testing
> for equality against more than one symbol, as in multiple
> `cl-case's?  Or testing the same symbol value more than once
> (just use a `let')?

I was talking about Lars' example.

> The same would be true of a let construct that only destructures
> (e.g., `destructuring-bind').

destructuring-bind is much less powerful than pcase.  pcase can test
whether something matches, combined with condition testing, boolean
operations and local variable binding.  There are cases where it's worth
it to prefer pcase over other tools where no destr-bind is involved.
But that's a minority of cases, yes.


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  0:19                                 ` Michael Heerdegen
  2016-01-03  2:47                                   ` Drew Adams
  2016-01-03  3:45                                   ` Eli Zaretskii
@ 2016-01-03  9:03                                   ` David Kastrup
  2016-01-04  2:08                                     ` Michael Heerdegen
  2 siblings, 1 reply; 375+ messages in thread
From: David Kastrup @ 2016-01-03  9:03 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, Daniel Colascione, emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> David Kastrup <dak@gnu.org> writes:
>
>> Some of the quoted pcase examples indeed felt like the "if your
>> preferred tool is a hammer, every problem looks like a nail"
>> phenomenon.
>
> Ironically, the same applies to Emacs itself  ;-)
>
>> There certainly is a case for liberal use of complex complexity-taming
>> constructs (for example, overall I can appreciate how cl-loop
>> straightens out a lot of awkward loop constructs even though its syntax
>> is not really Elisp-like).  But when a simple construct is a perfect
>> fit, it's not helping understanding.
>
> I don't see how a pcase used like a cl-case - as in the quoted example -
> is any harder to read or understand.

Quasiquotes are quasiquotes.  They are harder to read for the Lisp
reader, and they are harder to read for the human reader.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  4:21                                     ` Michael Heerdegen
@ 2016-01-03  9:13                                       ` David Kastrup
  2016-01-03 16:52                                         ` Clément Pit--Claudel
  2016-01-04  1:28                                         ` Michael Heerdegen
  2016-01-03 15:29                                       ` Eli Zaretskii
  1 sibling, 2 replies; 375+ messages in thread
From: David Kastrup @ 2016-01-03  9:13 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, dancol, emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> The syntax is very simple for its expressiveness.

So?  In ancient Greek, "you two should have started feeling a bit
ashamed of yourself" is a single word (employing the numerus Dual, the
mode Optative, the time Aorist, and a compounded word).

The syntax is very simple for its expressiveness.  There is a reason we
don't use it any more.

> But maybe I'm just obsessed by the beast.

If you want to use the syntax where no expressiveness is required
because you find it to be a nice tradeoff in case where huge amounts of
expressiveness are required, yes, you may be obsessed by it.

As it stands, we are just converging on the syntax.  It makes sense to
do that on those cases where the differences count, namely the complex
ones, so that we don't need to change the simple ones all over the map
for every change we make.

> Sorry, I give up.  pcase seems to scare off people somehow.

We don't use any constructs for the sake of using them.  We use them to
get stuff done in a manner where other people feel comfortable picking
up where we left off.  Using complex constructs for simple, well-covered
cases tends not to do that.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  2:49                                     ` Drew Adams
@ 2016-01-03 10:49                                       ` David Kastrup
  0 siblings, 0 replies; 375+ messages in thread
From: David Kastrup @ 2016-01-03 10:49 UTC (permalink / raw)
  To: Drew Adams
  Cc: michael_heerdegen, emacs-devel, Dmitry Gutov,
	Lars Magne Ingebrigtsen, Daniel Colascione, Eli Zaretskii

Drew Adams <drew.adams@oracle.com> writes:

> That's the question that I think is being discussed.  Whether
> wholesale replacement of `cond', `case', `if', etc. by `pcase' is a
> good idea, just because it could do the job.

I don't write `("blabla") on the off-chance that someone would want to
replace it with `(,(concat `"bla" `"bla")).  We don't quote self-quoting
forms gratuitously, and we don't use quasiquote gratuitously: the latter
only gets used when we indeed use an unquoting form inside.

In short, we don't use constructs for the sake of using constructs.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  4:21                                     ` Michael Heerdegen
  2016-01-03  9:13                                       ` David Kastrup
@ 2016-01-03 15:29                                       ` Eli Zaretskii
  2016-01-04  2:05                                         ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2016-01-03 15:29 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: dak, dancol, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: dak@gnu.org,  dancol@dancol.org,  emacs-devel@gnu.org
> Date: Sun, 03 Jan 2016 05:21:48 +0100
> 
> > Are you serious?  We've just had a long discussion about its missing
> > or incomplete or inadequate documentation,
> 
> I know that, but that we can and want to fix, so it is no argument about
> whether pcase is really eval or not.

The discussion is IMO a clear indication that at least some people
have difficulties reading the code which involves 'pcase'.  Which
means, IMO, that it shouldn't be used where simpler, more clear forms
will do.

> > including a long dispute about whether it would be better to quote _.
> 
> Yes, and...???

And that was IMO a clear indication that even the tiniest syntax
issues related to 'pcase' raise problems.

> > My summary of that discussion is that the syntax is complicated and
> > quite weird.
> 
> Where did we at all talk about the syntax?

If the semantics are not clear, the syntax is the first suspect.

> > Using such a beast where it is not required makes reading harder
> > because it requires the reader to understand its syntax, if nothing
> > else.
> 
> And that's the real problem: (some) people refrain to try to understand
> the syntax and prefer to complain.

That's not my concern.  I'm not one of those people.

> Sorry, I give up.  pcase seems to scare off people somehow.  If 50
> percent of the people are not able to cope with the thing, for whatever
> reason, and get stalled whenever they see it, I think we probably can't
> use it.  A pity.

I never said anything even close to such an extreme.  I don't think
there's any danger of refraining to use 'pcase' any time soon.  It
does its job well, and where it's needed, it should definitely be
used.

> Is it even worth to update the docs of pcase?

Yes, definitely.  With the current proliferation of its use in our
sources, we cannot leave it under-documented.  I hope to see proposals
for documentation patches soon, thank you.

> Will anyone from those antagonizing it really try to learn how the
> thing is supposed to be used?

I'm sure more than one will, indeed.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
       [not found]                                                   ` <56893C8C.3060200@yandex.ru>
@ 2016-01-03 15:52                                                     ` David Kastrup
  2016-01-03 15:59                                                       ` Dmitry Gutov
  2016-01-04  2:54                                                       ` The poor state of documentation of pcase like things Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: David Kastrup @ 2016-01-03 15:52 UTC (permalink / raw)
  To: Dmitry Gutov
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, emacs-devel

Dmitry Gutov <dgutov@yandex.ru> writes:

> On 01/03/2016 05:15 PM, David Kastrup wrote:
>
>> So why would people write
>>
>> (pcase exp
>>    (`nil nil) ...
>
> Easier to just use the same kind of quote everywhere?

More like "easier" to just use the _only_ documented kind of quote for
pcase everywhere.  We don't use quasiquote all over the rest of Emacs
just because it is "easier to just use the same kind of quote
everywhere".

>> ?  What's with the overuse of quasiquote?
>
> You should ask those people.

I suspect it would be the poor state of documentation of pcase like
things.

At any rate, while we are still figuring out how to use and not use
pcase in the Emacs code base, I don't see the point in diverting the
discussion to emacs-tangents silently.

However, it would seem to indicate that the proponents of pcase do not
want to see their actions discussed, so I'm not going to respond to this
thread anymore either way.  It would appear that we are on course
replacing consensual agreed-upon action with battling commits and
stifling speech.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 15:52                                                     ` David Kastrup
@ 2016-01-03 15:59                                                       ` Dmitry Gutov
  2016-01-03 17:15                                                         ` David Kastrup
  2016-01-04  2:54                                                       ` The poor state of documentation of pcase like things Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2016-01-03 15:59 UTC (permalink / raw)
  To: David Kastrup
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, emacs-devel

On 01/03/2016 05:52 PM, David Kastrup wrote:

> More like "easier" to just use the _only_ documented kind of quote for
> pcase everywhere.

 From pcase docstring:

     'VAL		matches if the object is ‘equal’ to VAL




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  9:13                                       ` David Kastrup
@ 2016-01-03 16:52                                         ` Clément Pit--Claudel
  2016-01-04  1:28                                         ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Clément Pit--Claudel @ 2016-01-03 16:52 UTC (permalink / raw)
  To: emacs-devel

On 01/03/2016 04:13 AM, David Kastrup wrote:
> So?  In ancient Greek, "you two should have started feeling a bit
> ashamed of yourself" is a single word (employing the numerus Dual, the
> mode Optative, the time Aorist, and a compounded word).
> 
> The syntax is very simple for its expressiveness.  There is a reason we
> don't use it any more.

???



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 15:59                                                       ` Dmitry Gutov
@ 2016-01-03 17:15                                                         ` David Kastrup
  2016-01-03 17:52                                                           ` Dmitry Gutov
  0 siblings, 1 reply; 375+ messages in thread
From: David Kastrup @ 2016-01-03 17:15 UTC (permalink / raw)
  To: Dmitry Gutov
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, emacs-devel

Dmitry Gutov <dgutov@yandex.ru> writes:

> On 01/03/2016 05:52 PM, David Kastrup wrote:
>
>> More like "easier" to just use the _only_ documented kind of quote for
>> pcase everywhere.
>
> From pcase docstring:
>
>     'VAL		matches if the object is ‘equal’ to VAL

Congratulations.  From

<URL:https://www.gnu.org/software/emacs/manual/html_node/elisp/Pattern-matching-case-statement.html#index-pcase>

    To compare a particular value against various possible cases, the
    macro pcase can come handy. It takes the following form:

    (pcase exp branch1 branch2 branch3 …)

    where each branch takes the form (upattern body-forms…).

    It will first evaluate exp and then compare the value against each
    upattern to see which branch to use, after which it will run the
    corresponding body-forms. A common use case is to distinguish
    between a few different constant values:

    (pcase (get-return-code x)
      (`success       (message "Done!"))
      (`would-block   (message "Sorry, can't do it now"))
      (`read-only     (message "The shmliblick is read-only"))
      (`access-denied (message "You do not have the needed rights"))
      (code           (message "Unknown return code %S" code)))

    In the last clause, code is a variable that gets bound to the value that
    was returned by (get-return-code x).

And so forth and so on.  The whole documentation idea of "qpattern" and
"upattern" does not even _allow_ discussing different ways of quoting
(since of course '-quoted entries are different from "qpatterns" as they
don't interpret unquote and unquote-splicing, namely , and ,@) so the
Elisp manual entry, arguably the decisive reference for use of pcase,
actively avoids mentioning ' at all in order not to have to upset its
terminology.

This is not helpful, as witnessed by the actual code extracts seen in
the Emacs code base and mailing list.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 17:15                                                         ` David Kastrup
@ 2016-01-03 17:52                                                           ` Dmitry Gutov
  2016-01-03 18:17                                                             ` David Kastrup
  0 siblings, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2016-01-03 17:52 UTC (permalink / raw)
  To: David Kastrup
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, emacs-devel

On 01/03/2016 07:15 PM, David Kastrup wrote:

> This is not helpful, as witnessed by the actual code extracts seen in
> the Emacs code base and mailing list.

Why don't you suggest an improvement (with a patch)?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 17:52                                                           ` Dmitry Gutov
@ 2016-01-03 18:17                                                             ` David Kastrup
  2016-01-04  2:34                                                               ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: David Kastrup @ 2016-01-03 18:17 UTC (permalink / raw)
  To: Dmitry Gutov
  Cc: michael_heerdegen, Eli Zaretskii, Daniel Colascione, emacs-devel

Dmitry Gutov <dgutov@yandex.ru> writes:

> On 01/03/2016 07:15 PM, David Kastrup wrote:
>
>> This is not helpful, as witnessed by the actual code extracts seen in
>> the Emacs code base and mailing list.
>
> Why don't you suggest an improvement (with a patch)?

Because I am not the one interested in promoting pcase?  Frankly, I
don't even have enough time to get the stuff I am interested in done.

-- 
David Kastrup



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  9:13                                       ` David Kastrup
  2016-01-03 16:52                                         ` Clément Pit--Claudel
@ 2016-01-04  1:28                                         ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-04  1:28 UTC (permalink / raw)
  To: emacs-devel

David Kastrup <dak@gnu.org> writes:

> > But maybe I'm just obsessed by the beast.
>
> If you want to use the syntax where no expressiveness is required
> because you find it to be a nice tradeoff in case where huge amounts of
> expressiveness are required, yes, you may be obsessed by it.

Where did I say I would want that?  And didn't I already agree to Drew's
complete message suggesting the opposite, and said that I do this
myself?


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 15:29                                       ` Eli Zaretskii
@ 2016-01-04  2:05                                         ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-04  2:05 UTC (permalink / raw)
  To: emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > > including a long dispute about whether it would be better to quote _.
> > 
> > Yes, and...???
>
> And that was IMO a clear indication that even the tiniest syntax
> issues related to 'pcase' raise problems.

If the fact that some people suggested to make it possible to leave out
a comma counts as a relevant problem or bug, I must say I'm surprised
how well this quite new thing works, after all, a complete new library.

The syntax still has been changed by Stefan himself recently, so it's
normal that we still discuss it, even when we didn't find a conclusion.


> If the semantics are not clear, the syntax is the first suspect.

> > > Using such a beast where it is not required makes reading harder
> > > because it requires the reader to understand its syntax, if nothing
> > > else.
> > 
> > And that's the real problem: (some) people refrain to try to understand
> > the syntax and prefer to complain.
>
> That's not my concern.  I'm not one of those people.

Ok.  So, what aspect of the semantics did you find not clear after
reading the documentation we currently have?


> > Sorry, I give up.  pcase seems to scare off people somehow.  If 50
> > percent of the people are not able to cope with the thing, for whatever
> > reason, and get stalled whenever they see it, I think we probably can't
> > use it.  A pity.
>
> I never said anything even close to such an extreme.  I don't think
> there's any danger of refraining to use 'pcase' any time soon.  It
> does its job well, and where it's needed, it should definitely be
> used.

That sounds somewhat different from what you said previously ("beast",
your conclusions about the discussion that the thing is "weird", etc).


Regards,

Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03  9:03                                   ` David Kastrup
@ 2016-01-04  2:08                                     ` Michael Heerdegen
  2016-01-04 22:05                                       ` John Wiegley
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-04  2:08 UTC (permalink / raw)
  To: emacs-devel

David Kastrup <dak@gnu.org> writes:

> > I don't see how a pcase used like a cl-case - as in the quoted example -
> > is any harder to read or understand.
>
> Quasiquotes are quasiquotes.  They are harder to read for the Lisp
> reader, and they are harder to read for the human reader.

I already said it multiple times, and I will say it again, every time
this complaint is formulated: This is outdated syntax, you don't have to
use backquote to quote symbols, only when you really want to do
list destructuring.


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 18:17                                                             ` David Kastrup
@ 2016-01-04  2:34                                                               ` Michael Heerdegen
  2016-01-04  6:19                                                                 ` Drew Adams
                                                                                   ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-04  2:34 UTC (permalink / raw)
  To: emacs-devel

David Kastrup <dak@gnu.org> writes:

> >> Elisp manual entry, arguably the decisive reference for use of pcase,
> >> actively avoids mentioning ' at all in order not to have to upset its
> >> terminology.

The reason is that the manual had not been updated after 'VAL had been
introduced.  It dates from a time where ` was indeed the only way of
quoting.

> >> This is not helpful, as witnessed by the actual code extracts seen in
> >> the Emacs code base and mailing list.
> >
> > Why don't you suggest an improvement (with a patch)?
>
> Because I am not the one interested in promoting pcase?  Frankly, I
> don't even have enough time to get the stuff I am interested in done.

I'll try to take care of that stuff.


After all, despite of the tone on both sides, I think we came to
some conclusions:

  - The pcase docs must be updated, esp. wrt quoting/ backquote, and
  missing stuff (e.g. first matching branches' body is executed,
  remaining branches are ignored).

  - We should not use it in cases where a different thing (esp. cl-case)
  exactly fits.  "Promoters" should use it sparse in contributions and
  only in cases where it improves readability or makes the case
  distinction clearer (given the reader read the documentation).  Others
  should accept that some people find it handy and will use it in such
  cases in their contributions.

  - Occurrences in the sources must be revised.


The only substantial difference, I think, was whether the design and
concept of pcase is useful.  I think it's ok when people have different
preferences here (like with `loop', which I personally avoid btw).


Thanks everyone,

Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-03 15:52                                                     ` David Kastrup
  2016-01-03 15:59                                                       ` Dmitry Gutov
@ 2016-01-04  2:54                                                       ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2016-01-04  2:54 UTC (permalink / raw)
  To: emacs-devel

David Kastrup <dak@gnu.org> writes:

> However, it would seem to indicate that the proponents of pcase do not
> want to see their actions discussed, so I'm not going to respond to this
> thread anymore either way.  It would appear that we are on course
> replacing consensual agreed-upon action with battling commits and
> stifling speech.

I've got a very similar impression from "your" side.  Maybe we should
all read a book about how to manage such discussions.  This was not fun.


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* RE: The poor state of documentation of pcase like things.
  2016-01-04  2:34                                                               ` Michael Heerdegen
@ 2016-01-04  6:19                                                                 ` Drew Adams
  2016-01-04 22:07                                                                   ` John Wiegley
  2016-01-04 15:52                                                                 ` Eli Zaretskii
  2018-10-23 13:04                                                                 ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Michael Heerdegen
  2 siblings, 1 reply; 375+ messages in thread
From: Drew Adams @ 2016-01-04  6:19 UTC (permalink / raw)
  To: Michael Heerdegen, emacs-devel

> I'll try to take care of that stuff.
> 
> After all, despite of the tone on both sides, I think we came to
> some conclusions:
> 
>   - The pcase docs must be updated, esp. wrt quoting/ backquote, and
>   missing stuff (e.g. first matching branches' body is executed,
>   remaining branches are ignored).
> 
>   - We should not use it in cases where a different thing (esp. cl-case)
>   exactly fits.  "Promoters" should use it sparse in contributions and
>   only in cases where it improves readability or makes the case
>   distinction clearer (given the reader read the documentation).  Others
>   should accept that some people find it handy and will use it in such
>   cases in their contributions.
> 
>   - Occurrences in the sources must be revised.
> 
> The only substantial difference, I think, was whether the design and
> concept of pcase is useful.  I think it's ok when people have different
> preferences here (like with `loop', which I personally avoid btw).
> 
> Thanks everyone, Michael.

A very constructive contribution to the discussion, IMO.

Thanks for taking a stab at the doc improvement.  That will be
a great help, including in terms of guiding our use of `pcase'.

And thanks for the consensus summary - sounds good to me.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-04  2:34                                                               ` Michael Heerdegen
  2016-01-04  6:19                                                                 ` Drew Adams
@ 2016-01-04 15:52                                                                 ` Eli Zaretskii
  2018-10-23 13:04                                                                 ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Michael Heerdegen
  2 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2016-01-04 15:52 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Date: Mon, 04 Jan 2016 03:34:39 +0100
> 
> After all, despite of the tone on both sides, I think we came to
> some conclusions:
> 
>   - The pcase docs must be updated, esp. wrt quoting/ backquote, and
>   missing stuff (e.g. first matching branches' body is executed,
>   remaining branches are ignored).
> 
>   - We should not use it in cases where a different thing (esp. cl-case)
>   exactly fits.  "Promoters" should use it sparse in contributions and
>   only in cases where it improves readability or makes the case
>   distinction clearer (given the reader read the documentation).  Others
>   should accept that some people find it handy and will use it in such
>   cases in their contributions.
> 
>   - Occurrences in the sources must be revised.

100% agreement.

Hope to see the documentation patches some time soon.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-04  2:08                                     ` Michael Heerdegen
@ 2016-01-04 22:05                                       ` John Wiegley
  0 siblings, 0 replies; 375+ messages in thread
From: John Wiegley @ 2016-01-04 22:05 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

>>>>> Michael Heerdegen <michael_heerdegen@web.de> writes:

> I already said it multiple times, and I will say it again, every time this
> complaint is formulated: This is outdated syntax, you don't have to use
> backquote to quote symbols, only when you really want to do list
> destructuring.

Please move this discussion to emacs-tangents.

Thank you,
-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: The poor state of documentation of pcase like things.
  2016-01-04  6:19                                                                 ` Drew Adams
@ 2016-01-04 22:07                                                                   ` John Wiegley
  0 siblings, 0 replies; 375+ messages in thread
From: John Wiegley @ 2016-01-04 22:07 UTC (permalink / raw)
  To: Drew Adams; +Cc: Michael Heerdegen, emacs-devel

>>>>> Drew Adams <drew.adams@oracle.com> writes:

>> After all, despite of the tone on both sides, I think we came to
>> some conclusions:
>> 
>> - The pcase docs must be updated, esp. wrt quoting/ backquote, and
>> missing stuff (e.g. first matching branches' body is executed,
>> remaining branches are ignored).
>> 
>> - We should not use it in cases where a different thing (esp. cl-case)
>> exactly fits.  "Promoters" should use it sparse in contributions and
>> only in cases where it improves readability or makes the case
>> distinction clearer (given the reader read the documentation).  Others
>> should accept that some people find it handy and will use it in such
>> cases in their contributions.
>> 
>> - Occurrences in the sources must be revised.
>> 
>> The only substantial difference, I think, was whether the design and
>> concept of pcase is useful.  I think it's ok when people have different
>> preferences here (like with `loop', which I personally avoid btw).
>> 
>> Thanks everyone, Michael.

> A very constructive contribution to the discussion, IMO.

> Thanks for taking a stab at the doc improvement.  That will be
> a great help, including in terms of guiding our use of `pcase'.

> And thanks for the consensus summary - sounds good to me.

Excellent summary and resolution, I agree. We can continue debate on
emacs-tangents, but this is resolved now from emacs-devel's point of view.
Michael and I will produce new documentation shortly.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.)
  2016-01-04  2:34                                                               ` Michael Heerdegen
  2016-01-04  6:19                                                                 ` Drew Adams
  2016-01-04 15:52                                                                 ` Eli Zaretskii
@ 2018-10-23 13:04                                                                 ` Michael Heerdegen
  2018-10-23 14:43                                                                   ` Clément Pit-Claudel
                                                                                     ` (2 more replies)
  2 siblings, 3 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-23 13:04 UTC (permalink / raw)
  To: emacs-devel; +Cc: Eli Zaretskii, Stefan Monnier

Hello,

>   [pcase] - Occurrences in the sources must be revised.

Some time (two years) ago I volunteered to replace lots of the `pcase'
occurrences in the Emacs sources (back) to cl-case where possible.  Lots
of people wanted this because they found understanding pcase expressions
hard.

I would like to do that now.  Stefan, can you live with that (AFAIR you
didn't participate in the discussion at that time)?

Or has the mood of people changed in the meantime due to the improved
documentation of `pcase'?

In a second step, I also would want to replace the unnecessarily
backquoted patterns to use quotes, i.e. `DOESNT-UNQUOTE ->
'DOESNT-UNQUOTE (the `ATOM patterns go back to a time where the quoted
syntax wasn't yet implemented).

A question: when I compose the commit message, I can write something
like "Change all affected callers in all files" instead of listing all
individual changed functions separately, right?


Thanks,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.)
  2018-10-23 13:04                                                                 ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Michael Heerdegen
@ 2018-10-23 14:43                                                                   ` Clément Pit-Claudel
  2018-10-23 14:46                                                                     ` Replace trivial pcase occurrences in the Emacs sources Michael Heerdegen
  2018-10-23 15:17                                                                   ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Eli Zaretskii
  2018-10-23 17:16                                                                   ` Stefan Monnier
  2 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-23 14:43 UTC (permalink / raw)
  To: emacs-devel

On 23/10/2018 09.04, Michael Heerdegen wrote:
> In a second step, I also would want to replace the unnecessarily
> backquoted patterns to use quotes

IIRC, one issue with that is that the quoted form doesn't work in some old-but-still-popular Emacsen.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 14:43                                                                   ` Clément Pit-Claudel
@ 2018-10-23 14:46                                                                     ` Michael Heerdegen
  2018-10-23 14:57                                                                       ` Clément Pit-Claudel
  2018-10-23 15:07                                                                       ` Noam Postavsky
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-23 14:46 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

Clément Pit-Claudel <cpitclaudel@gmail.com> writes:

> On 23/10/2018 09.04, Michael Heerdegen wrote:
> > In a second step, I also would want to replace the unnecessarily
> > backquoted patterns to use quotes
>
> IIRC, one issue with that is that the quoted form doesn't work in some
> old-but-still-popular Emacsen.

I'm not sure I understand.  I plan to do that only in the Emacs sources
(in master).  How can that be problematic for older Emacsen?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 14:46                                                                     ` Replace trivial pcase occurrences in the Emacs sources Michael Heerdegen
@ 2018-10-23 14:57                                                                       ` Clément Pit-Claudel
  2018-10-23 15:16                                                                         ` Michael Heerdegen
  2018-10-23 15:07                                                                       ` Noam Postavsky
  1 sibling, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-23 14:57 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

On 23/10/2018 10.46, Michael Heerdegen wrote:
> Clément Pit-Claudel <cpitclaudel@gmail.com> writes:
> 
>> On 23/10/2018 09.04, Michael Heerdegen wrote:
>>> In a second step, I also would want to replace the unnecessarily
>>> backquoted patterns to use quotes
>>
>> IIRC, one issue with that is that the quoted form doesn't work in some
>> old-but-still-popular Emacsen.
> 
> I'm not sure I understand.  I plan to do that only in the Emacs sources
> (in master).  How can that be problematic for older Emacsen?
The first pcase I wrote was adapted from an example in the sources that used quotes; that code broke when a user tried it on an older Emacsen.
It's not a huge issue, of course.

Clément.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 14:46                                                                     ` Replace trivial pcase occurrences in the Emacs sources Michael Heerdegen
  2018-10-23 14:57                                                                       ` Clément Pit-Claudel
@ 2018-10-23 15:07                                                                       ` Noam Postavsky
  2018-10-23 15:24                                                                         ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Noam Postavsky @ 2018-10-23 15:07 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Clément Pit-Claudel, Emacs developers

On Tue, 23 Oct 2018 at 10:47, Michael Heerdegen
<michael_heerdegen@web.de> wrote:
>
> Clément Pit-Claudel <cpitclaudel@gmail.com> writes:
>
> > On 23/10/2018 09.04, Michael Heerdegen wrote:
> > > In a second step, I also would want to replace the unnecessarily
> > > backquoted patterns to use quotes
> >
> > IIRC, one issue with that is that the quoted form doesn't work in some
> > old-but-still-popular Emacsen.
>
> I'm not sure I understand.  I plan to do that only in the Emacs sources
> (in master).  How can that be problematic for older Emacsen?

There are some files in Emacs master branch that are also distributed
in GNU ELPA for older Emacs, e.g., python.el (I don't know if it has
any pcase instances that you might want to replace, it's just the
first example that came to mind).

Another thing to watch out for is that pcase is available earlier than
cl-case in the bootstrap sequence.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 14:57                                                                       ` Clément Pit-Claudel
@ 2018-10-23 15:16                                                                         ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-23 15:16 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

Clément Pit-Claudel <cpitclaudel@gmail.com> writes:

> The first pcase I wrote was adapted from an example in the sources
> that used quotes; that code broke when a user tried it on an older
> Emacsen.
> It's not a huge issue, of course.

I see.  But measured from now, if the Emacs is only a bit older than
that one, there is no pcase at all.  And the semantics of pcase also saw
some more additions in the meantime.  So I tend to do what I suggested.

BTW, why I do want to do these replacements is because I think `ATOM
looks frightening to people: they think "what the hell does this mean"
though it's actually something simple.  Or, with other words, I think
replacing `ATOM with 'ATOM would improve readability.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.)
  2018-10-23 13:04                                                                 ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Michael Heerdegen
  2018-10-23 14:43                                                                   ` Clément Pit-Claudel
@ 2018-10-23 15:17                                                                   ` Eli Zaretskii
  2018-10-23 17:14                                                                     ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
  2018-10-23 17:22                                                                     ` John Wiegley
  2018-10-23 17:16                                                                   ` Stefan Monnier
  2 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-23 15:17 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Stefan Monnier <monnier@iro.umontreal.ca>,
>     Eli Zaretskii <eliz@gnu.org>
> Date: Tue, 23 Oct 2018 15:04:45 +0200
> 
> Some time (two years) ago I volunteered to replace lots of the `pcase'
> occurrences in the Emacs sources (back) to cl-case where possible.  Lots
> of people wanted this because they found understanding pcase expressions
> hard.
> 
> I would like to do that now.

Thank you.  If you find places where pcase is used, but a simple cond
will do (without obfuscating the code, of course), please use cond
where appropriate.

> Or has the mood of people changed in the meantime due to the improved
> documentation of `pcase'?

Mine didn't (and I do appreciate the improvement in the docs).

> A question: when I compose the commit message, I can write something
> like "Change all affected callers in all files" instead of listing all
> individual changed functions separately, right?

"All callers changed" is the usual wording.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 15:07                                                                       ` Noam Postavsky
@ 2018-10-23 15:24                                                                         ` Michael Heerdegen
  2018-10-23 15:31                                                                           ` Noam Postavsky
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-23 15:24 UTC (permalink / raw)
  To: Noam Postavsky; +Cc: Clément Pit-Claudel, Emacs developers

Noam Postavsky <npostavs@gmail.com> writes:

> There are some files in Emacs master branch that are also distributed
> in GNU ELPA for older Emacs, e.g., python.el (I don't know if it has
> any pcase instances that you might want to replace, it's just the
> first example that came to mind).

Ok, I guess I can just leave out these for now.

> Another thing to watch out for is that pcase is available earlier than
> cl-case in the bootstrap sequence.

What does that mean in concrete - should I leave out even more files -
which are these?  I don't think that replacing such pcase expressions
with something different instead - e.g. an equivalent `cond' - would be
a real improvement.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 15:24                                                                         ` Michael Heerdegen
@ 2018-10-23 15:31                                                                           ` Noam Postavsky
  2018-10-24 13:15                                                                             ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Noam Postavsky @ 2018-10-23 15:31 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Clément Pit-Claudel, Emacs developers

On Tue, 23 Oct 2018 at 11:24, Michael Heerdegen
<michael_heerdegen@web.de> wrote:

> > Another thing to watch out for is that pcase is available earlier than
> > cl-case in the bootstrap sequence.
>
> What does that mean in concrete - should I leave out even more files -
> which are these?

I'm not sure exactly files this would be, possibly the ones listed in
lisp/loadup.el, but anyway, testing that 'make bootstrap' succeeds
would be a good idea.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 15:17                                                                   ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Eli Zaretskii
@ 2018-10-23 17:14                                                                     ` Stefan Monnier
  2018-10-23 17:24                                                                       ` Michael Heerdegen
  2018-10-24  4:51                                                                       ` Richard Stallman
  2018-10-23 17:22                                                                     ` John Wiegley
  1 sibling, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-23 17:14 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

>> Some time (two years) ago I volunteered to replace lots of the `pcase'
>> occurrences in the Emacs sources (back) to cl-case where possible.

You're suggesting changing

    (pcase X
      ('a (fooa))
      ('b (foob))
      ...)

with

     (cl-case X
      (a (fooa))
      (b (foob))
      ...)

?

>> Lots of people wanted this because they found understanding pcase
>> expressions hard.

In what sense is the above cl-case more clear than the pcase equivalent?
I'm not saying the pcase version is better in those cases, but I think
the respective advantages and disadvantages pretty much balance out.


        Stefan


PS: In case anyone still doubts it, I'm opposed to replacing `pcase` uses
with `cl-case` uses.  I think it'd be at best a waste of time.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 13:04                                                                 ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Michael Heerdegen
  2018-10-23 14:43                                                                   ` Clément Pit-Claudel
  2018-10-23 15:17                                                                   ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Eli Zaretskii
@ 2018-10-23 17:16                                                                   ` Stefan Monnier
  2 siblings, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-23 17:16 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, emacs-devel

> In a second step, I also would want to replace the unnecessarily
> backquoted patterns to use quotes, i.e. `DOESNT-UNQUOTE ->
> 'DOESNT-UNQUOTE (the `ATOM patterns go back to a time where the quoted
> syntax wasn't yet implemented).

Sounds good to me,


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 15:17                                                                   ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Eli Zaretskii
  2018-10-23 17:14                                                                     ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
@ 2018-10-23 17:22                                                                     ` John Wiegley
  1 sibling, 0 replies; 375+ messages in thread
From: John Wiegley @ 2018-10-23 17:22 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, monnier, emacs-devel

>>>>> "EZ" == Eli Zaretskii <eliz@gnu.org> writes:

>> I would like to do that now.

EZ> Thank you. If you find places where pcase is used, but a simple cond will
EZ> do (without obfuscating the code, of course), please use cond where
EZ> appropriate.

I'm also all for a gain in simplicity, even though I'm a pcase-lover myself.

-- 
John Wiegley                  GPG fingerprint = 4710 CF98 AF9B 327B B80F
http://newartisans.com                          60E1 46C4 BD1A 7AC1 4BA2



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 17:14                                                                     ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
@ 2018-10-23 17:24                                                                       ` Michael Heerdegen
  2018-10-23 18:12                                                                         ` Stefan Monnier
  2018-10-24  4:51                                                                       ` Richard Stallman
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-23 17:24 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: Eli Zaretskii, emacs-devel

Stefan Monnier <monnier@IRO.UMontreal.CA> writes:

> You're suggesting changing
>
>     (pcase X
>       ('a (fooa))
>       ('b (foob))
>       ...)
>
> with
>
>      (cl-case X
>       (a (fooa))
>       (b (foob))
>       ...)
>
> ?

Yes.

> >> Lots of people wanted this because they found understanding pcase
> >> expressions hard.
>
> In what sense is the above cl-case more clear than the pcase equivalent?
> I'm not saying the pcase version is better in those cases, but I think
> the respective advantages and disadvantages pretty much balance out.

> PS: In case anyone still doubts it, I'm opposed to replacing `pcase` uses
> with `cl-case` uses.  I think it'd be at best a waste of time.

I think so too, but it seems the majority of developers has a different
option, at least in this (old) thread.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 17:24                                                                       ` Michael Heerdegen
@ 2018-10-23 18:12                                                                         ` Stefan Monnier
  2018-10-23 19:52                                                                           ` pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
  2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-23 18:12 UTC (permalink / raw)
  To: emacs-devel

> I think so too, but it seems the majority of developers has a different
> option, at least in this (old) thread.

So I guess I'm gonna have to try and argue my case.
OK, here are the advantages I see for `cl-case`:

- simpler doc because its functionality is much more limited.
- easier for people who already know Common-Lisp (or those who learned
  `case` from the cl.el package).
- more concise syntax for branches that match multiple constants.

Here are the problems I see with cl-case (regardless of pcase):

- some users naturally write (case X ('a fooa) ...) without realizing
  that it also matches thew `quote` value.
- tricky corner cases when trying to match the `t` or `nil` values (or
  `otherwise` as well, tho this one is much more rarely needed).
- in (case X (a fooa)), the syntax looks a bit like a call to the
  function `a`:  emacs-lisp-mode gets confused in terms of
  highlighting and completion, last I checked.
- only works with numbers and symbols: can't use it to match against strings.

In the specific case of using `pcase` where `cl-case` could also be
used, the downsides I know of `pcase` are the following:

- because it can also do a lot more, its doc is much more complex.
- you have to use the more verbose ((or 'a 'b 'c) ...) syntax when
  matching several alternative values.
- if you forget to quote your constant symbols the code behaves
  differently (and arguably surprisingly for some user) rather than
  giving you an error, tho in many cases the macro will detect a problem
  and give you a warning about a subsequent redundant branch (but the
  unsuspecting user will likely find it puzzling and it will take
  a while for him to figure out what's going on).

The advantages are:

- it fixes all four problems I described about `cl-case`.
- it can accommodate many more cases, so it offers a smoother evolution.
  IOW, you will rarely find yourself having to stop using `pcase` and
  to rewrite the code to use `cond` instead just because you need to
  add a case that's a bit different from the others.
- once you learn it, you can use it elsewhere, e.g. pcase-let,
  pcase-dolist, ...
- Elisp+pcase is simpler than Elisp+clcase+pcase, so if we aim for
  overall simplicity we'd be better off without cl-case (to the extend
  that `cl-case` is too limited and hence we'll still want to use
  `pcase`).


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-23 18:12                                                                         ` Stefan Monnier
@ 2018-10-23 19:52                                                                           ` Garreau, Alexandre
  2018-10-23 20:19                                                                             ` Stefan Monnier
  2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-23 19:52 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-23 at 14:12, Stefan Monnier wrote:
> In the specific case of using `pcase` where `cl-case` could also be
> used, the downsides I know of `pcase` are the following:

> - if you forget to quote your constant symbols the code behaves
>   differently (and arguably surprisingly for some user) rather than
>   giving you an error, tho in many cases the macro will detect a problem
>   and give you a warning about a subsequent redundant branch (but the
>   unsuspecting user will likely find it puzzling and it will take
>   a while for him to figure out what's going on).

Aren’t non-quoted for bind? what should give an error or a warning? I
didn’t understood?

Also, in either pcase or case: can’t they eval a symbol as a variable
value to be used in tests?

> [but] because it can also do a lot more, its doc is much more complex.

> The advantages are:

> - it can accommodate many more cases, so it offers a smoother evolution.
>   IOW, you will rarely find yourself having to stop using `pcase` and
>   to rewrite the code to use `cond` instead just because you need to
>   add a case that's a bit different from the others.

To push the reasoning on an extreme: would that be a reason for
abandoning cond, lambda, etc. in favor of pcase?  ML do that, and I find
it sad and less minimal and lightweight.

> - once you learn it, you can use it elsewhere, e.g. pcase-let,
>   pcase-dolist, ...

Could have been the same for cl-destructuring-bind.

> - Elisp+pcase is simpler than Elisp+clcase+pcase, so if we aim for
>   overall simplicity we'd be better off without cl-case (to the extend
>   that `cl-case` is too limited and hence we'll still want to use
>   `pcase`).

> the advantages I see for `cl-case`:

You forgot simplicity and concision of implementation: easier to
understand and reimplement, thus more hackable upon and widespread.  For
instance, I personally have my own case* implementation for using other
test-fn than eql (such as equal, the only possible one for pcase, and I
don’t even hope making my own version for eq/eql/etc.).

Many people will want case anyway, probably much code uses it (including
but not limited to fragments of common lisp afaik), so it’ll stay
anyway, because it is a trivial and obvious factorization of cond,
already existing in most languages, and simpler to make.  While pcase is
much more questionable, trivial, straightforward and widespread.
elisp+clcase is simpler than elisp+pcase, overall.  So for any codebase,
one only needing case (more likely) will be simpler and have less
dependency burden that one needing pcase.

Also, from a more reductionist point of view: pcase can be implemented
more simply and readably using case, typecase, etc.  so that’s yet
another argument for case to stay used and widespread.

> - easier for people who already know Common-Lisp (or those who learned
>   `case` from the cl.el package).

Also it is basically the equivalent of “switch/case/etc.” many will
search for, coming from another language such as C: and not everybody is
fond of destructuring and pattern matching

> Here are the problems I see with cl-case (regardless of pcase):

> - only works with numbers and symbols: can't use it to match against
> strings.

Can be fixed, and without breaking backward-compatibility.

> - in (case X (a fooa)), the syntax looks a bit like a call to the
> function `a`: emacs-lisp-mode gets confused in terms of highlighting
> and completion, last I checked.

case is a macro: why making assumption on calls in macros arguments?
from time case known as a macro (I’ve a hard time imagining what a
“case” *function* would be anyway)…  Also, with an unquoted symbol (so
to bind the default case), you have this very same problem with pcase:
(pcase X (a (fooa))) (and emacs syntax highlighting is confused here
too: (pcase X (cond (fooa))), (pcase X (function (fooa))).  So
emacs-lisp-mode would better be fixed at some point rather than macros
arbitrarily disapproved.  Then:
> - [pcase] fixes all four problems I described about `cl-case`.
hence not even.

> - tricky corner cases when trying to match the `t` or `nil` values (or
>   `otherwise` as well, tho this one is much more rarely needed).

I find these interface details sadening, it would have been more useful
the other way.  Btw as said before, matching the default case can be
considered confusing as well with pcase.

> - some users naturally write (case X ('a fooa) ...) without realizing
>   that it also matches thew `quote` value.

I find sad cl case doesn’t eval its arguments :/ The two last issue
would be lessened it it was this way btw.  But doing otherwise would be
incompatible with cl, with which I find neat emacs lisp is partially
compatible with, and it would break backward-compatibility, and much
code (as much as it would to remove it at all).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-23 19:52                                                                           ` pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
@ 2018-10-23 20:19                                                                             ` Stefan Monnier
  2018-10-23 22:24                                                                               ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-23 20:19 UTC (permalink / raw)
  To: emacs-devel

>> - if you forget to quote your constant symbols the code behaves
>>   differently (and arguably surprisingly for some user) rather than
>>   giving you an error, tho in many cases the macro will detect a problem
>>   and give you a warning about a subsequent redundant branch (but the
>>   unsuspecting user will likely find it puzzling and it will take
>>   a while for him to figure out what's going on).
> Aren’t non-quoted for bind? what should give an error or a warning?
> I didn’t understood?

If the naive user wrote

    (pcase X
      (a fooa)
      (b foob))

when the intended behavior was

    (pcase X
      ('a fooa)
      ('b foob))

pcase will give a warning during macro-expansion that the second branch
is redundant (since the first branch matches everything already).

So, in a sense the user's error is detected, but the resulting warning
is hard to understand if you don't know that the pattern `a` matches
everything and binds it to the variable `a`.

> Also, in either pcase or case: can’t they eval a symbol as a variable
> value to be used in tests?

Sorry, I don't understand what you mean: X can be a variable that's
evaluated, yes.  Or do you mean the case where we want to test equality
with Y?  `pcase` can do that with

    (pcase X ((pred (equal Y)) foo-equal-Y) ...)

but I think this is irrelevant for the discussion at hand.

> To push the reasoning on an extreme:

Given Turing-equivalence, I don't think pushing the reasoning to the
extreme will be a good guide.

>> - once you learn it, you can use it elsewhere, e.g. pcase-let,
>>   pcase-dolist, ...
> Could have been the same for cl-destructuring-bind.

Except cl-destructuring-bind only covers (a subset of) pcase-let.
It could cover pcase-let as well pcase-dolist, but not `pcase` itself.
[ And even then, it would be less flexible than pcase-let because the
  syntax of cl-destructuring-bind's patterns doesn't leave much space
  for extensions.  ]

> You forgot simplicity and concision of implementation: easier to
> understand and reimplement, thus more hackable upon and widespread.

I don't think it's particularly important, indeed.

> For instance, I personally have my own case* implementation for using
> other test-fn than eql (such as equal,

That highlights the problem that cl-case doesn't work with strings,
forcing users like you to write their own alternative.

> the only possible one for pcase, and I don’t even hope making my own
> version for eq/eql/etc.).

Could you show me a pcase pattern where pcase's choice of equality
is problematic?
[ FWIW, there's only one case to comes to my mind.  ]

>> - easier for people who already know Common-Lisp (or those who learned
>>   `case` from the cl.el package).
> Also it is basically the equivalent of “switch/case/etc.” many will
> search for, coming from another language such as C: and not everybody is
> fond of destructuring and pattern matching

pcase works just as well to replace "switch/case/etc."
You don't have to use pcase's destrucuring, and this discussion is about
the subset of case covered by `cl-case`, so destructuring is outside of
its scope, AFAIC.

>> - in (case X (a fooa)), the syntax looks a bit like a call to the
>> function `a`: emacs-lisp-mode gets confused in terms of highlighting
>> and completion, last I checked.
> case is a macro: why making assumption on calls in macros arguments?
> from time case known as a macro (I’ve a hard time imagining what a
> “case” *function* would be anyway)…  Also, with an unquoted symbol (so
> to bind the default case), you have this very same problem with pcase:
> (pcase X (a (fooa))) (and emacs syntax highlighting is confused here

Not again that the pattern `a` here is outside the scope of this
discussion (except to the extent that user can write it by mistake).


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-23 20:19                                                                             ` Stefan Monnier
@ 2018-10-23 22:24                                                                               ` Garreau, Alexandre
  0 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-23 22:24 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-23 at 16:19, Stefan Monnier wrote:
>> To push the reasoning on an extreme:
>
> Given Turing-equivalence, I don't think pushing the reasoning to the
> extreme will be a good guide.

Why?  We’re talking about what’s standard or not (so what need to be
redefined or not), what is (to be) popularized, common, etc. or not:
“if”, simple lambda, etc. exist in ML, but according “good ML style” are
(almost) never used, and pattern-matching forms is prefered (even when
there’s no destructuring).  The question is: do we want the same for
emacs-lisp?  I’m not personally fond enough of pattern-matching.  That
recalls me the kind of falsely consensual trends that created Rust.

pattern-matching is more intuitive, familiar and straightforward to read
to the unused user, but it is more complex (including but not limited to
of implementation), and I believe its familiarity is subjective or at
least deeply specific to the human cognition, not as systematically
particularly interesting on a logical or mathematical level.  As forms
such as case/switch/etc. are simpler, with some habit you can get
quickly get as much used to it as to pattern-matching, just like sexps:
more simple, less familiar, but then not long to get used to it.

Imho cases where simple `case' become unreadable and pcase becomes
necessary are symptoms of trying to implement something too complex at
once, that could be either breaked down into simpler and more meaningful
parts, or themselves symptoms of a complex spec or interface (where
pcase would then become a necessary evil, but it should be there to
indicate it as such).  But that might exit the subject scope.

>>> - once you learn it, you can use it elsewhere, e.g. pcase-let,
>>>   pcase-dolist, ...
>>
>> Could have been the same for cl-destructuring-bind.
>
> Except cl-destructuring-bind only covers (a subset of) pcase-let.
> It could cover pcase-let as well pcase-dolist, but not `pcase` itself.
> [ And even then, it would be less flexible than pcase-let because the
>   syntax of cl-destructuring-bind's patterns doesn't leave much space
>   for extensions.  ]

pcase is about pattern matching, that implies conditions, or at least
recognition or tests, pcase-let only does destructuring afaik, so
shouldn’t cl-destructuring-bind be improved instead, and all the pcase-*
functions actually only doing destructuring be based on it?

>> For instance, I personally have my own case* implementation for using
>> other test-fn than eql (such as equal,
>
> That highlights the problem that cl-case doesn't work with strings,
> forcing users like you to write their own alternative.

Ahh, that’s what you meant by “doesn’t work”.  Well, eq can still be
useful, for strings, I believe, otherwise eq wouldn’t exist and we would
only have equal (though this is what pcase does), so I wouldn’t call
that “doesn’t work”.  But a * version that takes a testfn as argument
can improve expressivity I believe (what if you want to compare, dunno,
hashes?)

>> the only possible one for pcase, and I don’t even hope making my own
>> version for eq/eql/etc.).
>
> Could you show me a pcase pattern where pcase's choice of equality
> is problematic?
> [ FWIW, there's only one case to comes to my mind.  ]

Now I know about the (equal ) pattern form, I guess a (eq ) wouldn’t be
that difficult to add, and as one of these would be mandatory to specify
non-constant (hence possibly same) strings (though maybe there’s a way
to trigger arbitrary computation from inside the pattern before another
get tried), it stays under control, so I don’t have any (case) anymore.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 17:14                                                                     ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
  2018-10-23 17:24                                                                       ` Michael Heerdegen
@ 2018-10-24  4:51                                                                       ` Richard Stallman
  2018-10-24  8:34                                                                         ` Joost Kremers
  2018-10-24 10:16                                                                         ` Replace trivial pcase occurrences in the Emacs sources João Távora
  1 sibling, 2 replies; 375+ messages in thread
From: Richard Stallman @ 2018-10-24  4:51 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: michael_heerdegen, eliz, emacs-devel

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  > In what sense is the above cl-case more clear than the pcase equivalent?
  > I'm not saying the pcase version is better in those cases, but I think
  > the respective advantages and disadvantages pretty much balance out.

I also wonder.  Is it simply that people find pcase unfamiliar?

-- 
Dr Richard Stallman
President, Free Software Foundation (https://gnu.org, https://fsf.org)
Internet Hall-of-Famer (https://internethalloffame.org)





^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24  4:51                                                                       ` Richard Stallman
@ 2018-10-24  8:34                                                                         ` Joost Kremers
  2018-10-24 12:37                                                                           ` Stefan Monnier
  2018-10-24 13:03                                                                           ` pcase pattern syntax (was: Replace trivial pcase occurrences in the Emacs sources) Stefan Monnier
  2018-10-24 10:16                                                                         ` Replace trivial pcase occurrences in the Emacs sources João Távora
  1 sibling, 2 replies; 375+ messages in thread
From: Joost Kremers @ 2018-10-24  8:34 UTC (permalink / raw)
  To: Richard Stallman

On Wed, Oct 24, 2018 at 12:51:35AM -0400, Richard Stallman wrote:
> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
> [[[ whether defending the US Constitution against all enemies,     ]]]
> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
> 
>   > In what sense is the above cl-case more clear than the pcase equivalent?
>   > I'm not saying the pcase version is better in those cases, but I think
>   > the respective advantages and disadvantages pretty much balance out.
> 
> I also wonder.  Is it simply that people find pcase unfamiliar?

Well, I can't speak for others, but personally, though I find pattern matching as a concept straightforward and intuitive, pcase syntax seems unnecessarily complex and unintuitive.

For example, John Wiegley's tutorial on pcase at <http://newartisans.com/2016/01/pattern-matching-with-pcase/> has the following example:

```
(pcase value
  (`(,_ 1 2)
   (message "Matched a list of anything followed by (1 2)")))
```

It is not clear to me why I couldn't simply write:

```
(pcase value
  ((_ 1 2)
   (message "Matched a list of anything followed by (1 2)")))
```

I *can* understand the need to write:

```
(pcase value
  (`(1 2 ,foo 3)
   (message "Matched 1, 2, something now bound to foo, and 3")))
```

Instead of:

```
(pcase value
  ((1 2 foo 3)
   (message "Matched 1, 2, something now bound to foo, and 3")))
```

This is obviously done in order to be able to match against the symbol `foo' while at the same time be able to match anything and bind it to the symbol `foo'. And even though this syntax with backquote and comma looks familiar to anyone who's ever written a macro, their meaning is subtly different from their meaning in macros. In pcase, «,foo» does *not* mean «evaluate `foo'», it means something like «use `foo' as a variable».

So, while I understand the reasoning, it still makes me wonder why I can't write something like this:

```
(pcase value
  ((1 2 % 3)
   (message "Matched 1, 2, something now bound to %, and 3")))
```

That is, use a special symbol (I borrowed % from Clojure's anonymous functions) to indicate that I want to match against any value and at the same time bind that value. Obviously, the following:

```
(pcase value
  ((1 2 % %)
   (message "Matched 1, 2, something now bound to %, and that same something again")))
```

would then match lists of the form (1 2 3 3), not (1 2 3 4). If you need to bind multiple values, I could imagine using something like:

```
(pcase value
  ((1 2 %1 %2)
   (message "Matched 1, 2, something now bound to %1, and something (else) bound to %2")))
```

Also, the use of `pred' and `guard' seem unnecessary. Instead of:

```
(pcase value
  (`(1 2 ,(or 3 4)
     ,(and (pred stringp)
           (pred (string> "aaa"))
           (pred (lambda (x) (> (length x) 10)))))
   (message "Matched 1, 2, 3 or 4, and a long string "
            "that is lexically greater than 'aaa'")))
```

why not write:

```
(pcase value
  ((1 2 (or 3 4)
    (and (stringp %)
         (string> "aaa" %)
         (> (length %) 10)))
   (message "Matched 1, 2, 3 or 4, and a long string "
            "that is lexically greater than 'aaa'")))
```

Similarly, the example:

```
(pcase value
  (`(1 2 ,(and foo (guard (and (not (numberp foo)) (/= foo 10)))) _)
   (message "Matched 1, 2, anything, and then anything again, "
            "but only if the first anything wasn't the number 10"))))
```

uses `(and foo (guard ...))' to bind a value to `foo' and apply a predicate to it. That's a coding pattern that you need to be familiar with in order to understand what it does. (John explains it in his tutorial, but if I had met this in the wild, I'd probably be puzzled by it at first). The % syntax would seem to make this simpler as well:

```
(pcase value
  ((1 2 (and (not (numberp %)) (/= % 10)) _)
   (message "Matched 1, 2, anything, and then anything again, "
            "but only if the first anything wasn't the number 10"))))
```

This example also shows that `and' has a meaning in pcase that is subtly different from its usual meaning in Lisp: `and' in a pcase 'UPattern' (as the manual calls it) is not a logical `and' in the sense that it tests its arguments for truthiness. Rather, it means «both arguments of `and' must apply to the value at this position *regardless of truthiness*». (The `and' inside the guard does have the usual meaning, of course.)

Mind you, I'm not arguing that pcase should be changed or replaced with something that has this more intuitive (to me, anyway) syntax. I'm just trying to explain why I personally find pcase difficult to wrap my head around, and why I think this difficulty has to do with its syntax, which is different in subtle ways, to such an extent that you can't, as an Elisp programmer tackling pcase for the first time, just build on what you already know. You need to actually bend your mind to incorporate the new stuff. Moreover, at first sight, there doesn't seem to be much of an advantage to this syntax, since an alternative syntax that doesn't have the same disadvantage seems feasible.

I say "seems", because it's entirely possible that this particular syntax has capabilities that wouldn't be possible with a simpler syntax. But for a pcase newbie, that's not immediately obvious. The only reason that I can think of why the %-syntax or something similar isn't used is that it's dangerous in an environment that doesn't have lexical scope...

Just my two cents, of course.


-- 
Joost Kremers
Life has its moments



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24  4:51                                                                       ` Richard Stallman
  2018-10-24  8:34                                                                         ` Joost Kremers
@ 2018-10-24 10:16                                                                         ` João Távora
  2018-10-24 13:05                                                                           ` Stefan Monnier
  2018-10-25  3:11                                                                           ` Richard Stallman
  1 sibling, 2 replies; 375+ messages in thread
From: João Távora @ 2018-10-24 10:16 UTC (permalink / raw)
  To: Richard Stallman; +Cc: michael_heerdegen, eliz, Stefan Monnier, emacs-devel

Richard Stallman <rms@gnu.org> writes:

> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
> [[[ whether defending the US Constitution against all enemies,     ]]]
> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
>
>   > In what sense is the above cl-case more clear than the pcase equivalent?
>   > I'm not saying the pcase version is better in those cases, but I think
>   > the respective advantages and disadvantages pretty much balance out.
>
> I also wonder.  Is it simply that people find pcase unfamiliar?

My two cents: I like to write it, I don't like to read it.

I like to write it because it's fun.  I write some dummy '(1 2 (3 4 5) 6
7) into my code and then semi-randomly hammer out parenthesis,
backquotes, commas and underscores until it does what I want.  In the
end I'm happy for winning this little game, and happily convinced it
saved me a ton of LOC (which it probably did).  When reading it, I
shudder a little.  The backquote syntax helps in warning that something
potentially difficult is in front of me, so please don't remove it.

I can't explain, but I don't feel this way about destructuring-bind (or
its destructuring-case variants [0]): they're boring to write and easy
to read.

João

[0]:
http://www.crategus.com/books/alexandria/pages/alexandria.0.dev_fun_destructuring-case.html




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24  8:34                                                                         ` Joost Kremers
@ 2018-10-24 12:37                                                                           ` Stefan Monnier
  2018-10-24 13:08                                                                             ` Daniel Pittman
  2018-10-24 13:03                                                                           ` pcase pattern syntax (was: Replace trivial pcase occurrences in the Emacs sources) Stefan Monnier
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-24 12:37 UTC (permalink / raw)
  To: emacs-devel

>>   > In what sense is the above cl-case more clear than the pcase equivalent?
>>   > I'm not saying the pcase version is better in those cases, but I think
>>   > the respective advantages and disadvantages pretty much balance out.
>> I also wonder.  Is it simply that people find pcase unfamiliar?

> Well, I can't speak for others, but personally, though I find pattern
> matching as a concept straightforward and intuitive, pcase syntax
> seems unnecessarily complex and unintuitive.

Joost, could you post this in another thread?  You're discussing
destructuring pcase patterns, whereas this discussion is about cl-case
vs pcase, where there's no destructuring and no backquote in sight.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* pcase pattern syntax (was: Replace trivial pcase occurrences in the Emacs sources)
  2018-10-24  8:34                                                                         ` Joost Kremers
  2018-10-24 12:37                                                                           ` Stefan Monnier
@ 2018-10-24 13:03                                                                           ` Stefan Monnier
  2018-10-26  7:16                                                                             ` Joost Kremers
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-24 13:03 UTC (permalink / raw)
  To: emacs-devel

> (pcase value
>   (`(,_ 1 2)
>    (message "Matched a list of anything followed by (1 2)")))
>
> It is not clear to me why I couldn't simply write:
>
> (pcase value
>   ((_ 1 2)
>    (message "Matched a list of anything followed by (1 2)")))

The reason is simple: because pcase uses a more verbose pattern syntax.
There are many different choices for pattern syntax, with various
tradeoffs between conciseness, regularity, and extensibility.

pcase's syntax leans in favor of regularity and extensibility to the
detriment of conciseness.

In your above example, if you allow (_ 1 2) to mean the same as pcase's
`(,_ 1 2), then you need some special syntax for the case where you
meant to match the same as pcase's '(_ 1 2).

> would then match lists of the form (1 2 3 3), not (1 2 3 4). If you
> need to bind multiple values, I could imagine using something like:
>
> (pcase value
>   ((1 2 %1 %2)
>    (message "Matched 1, 2, something now bound to %1, and something (else) bound to %2")))

that's getting pretty close to (1 2 ,x ,y): the only differences being
the use of % instead of comma and the absence of a surrounding backquote.

> why not write:
>
> ```
> (pcase value
>   ((1 2 (or 3 4)
>     (and (stringp %)
>          (string> "aaa" %)
>          (> (length %) 10)))
>    (message "Matched 1, 2, 3 or 4, and a long string "
>             "that is lexically greater than 'aaa'")))

Why wouldn't that be matching the same as pcase's

    (pcase value
      (`(1 2 (or 3 4)
        (and (stringp ,x)
             (string> "aaa" ,y)
             (> (length ,z) 10)))
       (message "Matched 1, 2, 3 or 4, and a long string "
                "that is lexically greater than 'aaa'")))

or alternatively, what special syntax would you introduce in order to
say "this (or 3 4) shouldn't match "either 3 or 4" but should match
a the 3-element list (or 3 4)"?

> uses `(and foo (guard ...))' to bind a value to `foo' and apply
> a predicate to it. That's a coding pattern that you need to be
> familiar with in order to understand what it does. (John explains it
> in his tutorial, but if I had met this in the wild, I'd probably be
> puzzled by it at first). The % syntax would seem to make this simpler
> as well:

Yes, the and+guard thingy sucks.  I've been thinking of changing `guard`
so it automatically does an `and`, i.e. make it so that

    (guard foo EXP)

is the same as

    (and foo (guard EXP))

but I don't find this terribly good either.  Note that you can also
write it as

    (pred (lambda (foo) EXP))

which is clearly not more friendly but I just mention it in case it
might help someone come up with yet another solution.

Many pattern matching systems don't have guards as part of the patterns
and instead have them "on the side", in which case you'd write

    ... ,foo ...

in the pattern and

    (guard EXP)

elsewhere.  I find this to be a nice way to solve the problem, but:
- I don't know where to place this EXP.  Maybe a branch could take the
  form (PATTERN :guard EXP BODY)?
- This forces the guard expressions to be evaluated at the very end,
  so it's a bit less expressive.  In practice this is not too bad, tho.
- There's a similar problem for the (let PAT EXP) pattern, where it
  often/generally has to be coupled with an `and` as in
  (and PAT1 (let PAT EXP)), but this problem can't be solved by moving
  the `let` outside of the pattern like we can for the `guard`.

> This example also shows that `and' has a meaning in pcase that is
> subtly different from its usual meaning in Lisp: `and' in a pcase
> 'UPattern' (as the manual calls it) is not a logical `and' in the
> sense that it tests its arguments for truthiness. Rather, it means
> «both arguments of `and' must apply to the value at this position
> *regardless of truthiness*». (The `and' inside the guard does have the
> usual meaning, of course.)

That's right: the `and` pattern is really an intersection of patterns.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 10:16                                                                         ` Replace trivial pcase occurrences in the Emacs sources João Távora
@ 2018-10-24 13:05                                                                           ` Stefan Monnier
  2018-10-25  3:11                                                                           ` Richard Stallman
  1 sibling, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-24 13:05 UTC (permalink / raw)
  To: emacs-devel

>> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
>> [[[ whether defending the US Constitution against all enemies,     ]]]
>> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
>>
>>   > In what sense is the above cl-case more clear than the pcase equivalent?
>>   > I'm not saying the pcase version is better in those cases, but I think
>>   > the respective advantages and disadvantages pretty much balance out.
>>
>> I also wonder.  Is it simply that people find pcase unfamiliar?
>
> My two cents: I like to write it, I don't like to read it.

Same as for Joost: you're talking about the backquote syntax of pcase,
whereas this thread is about cl-case vs pcase, where there's no backquote
in sight.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 12:37                                                                           ` Stefan Monnier
@ 2018-10-24 13:08                                                                             ` Daniel Pittman
  2018-10-24 14:35                                                                               ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Daniel Pittman @ 2018-10-24 13:08 UTC (permalink / raw)
  To: monnier; +Cc: emacs-devel

[-- Attachment #1: Type: text/plain, Size: 1075 bytes --]

On Wed, Oct 24, 2018 at 8:38 AM Stefan Monnier <monnier@iro.umontreal.ca>
wrote:

> >>   > In what sense is the above cl-case more clear than the pcase
> equivalent?
> >>   > I'm not saying the pcase version is better in those cases, but I
> think
> >>   > the respective advantages and disadvantages pretty much balance out.
> >> I also wonder.  Is it simply that people find pcase unfamiliar?
>
> > Well, I can't speak for others, but personally, though I find pattern
> > matching as a concept straightforward and intuitive, pcase syntax
> > seems unnecessarily complex and unintuitive.
>
> Joost, could you post this in another thread?  You're discussing
> destructuring pcase patterns, whereas this discussion is about cl-case
> vs pcase, where there's no destructuring and no backquote in sight.


For what it is worth, I agree with Joost, and I thought this *was* the
required syntax for the use case being discussed.  Which, despite having
written a fair bit of pcase and pcase-let based code recently, probably
tells you a bit about the learning curve for the tool.

[-- Attachment #2: Type: text/html, Size: 1437 bytes --]

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 15:31                                                                           ` Noam Postavsky
@ 2018-10-24 13:15                                                                             ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-24 13:15 UTC (permalink / raw)
  To: Noam Postavsky; +Cc: Emacs developers

Noam Postavsky <npostavs@gmail.com> writes:

> I'm not sure exactly files this would be, possibly the ones listed in
> lisp/loadup.el, but anyway, testing that 'make bootstrap' succeeds
> would be a good idea.

Sure, I'll do that.

BTW, what about org files?  I heard they use a separate repository for
development.  Should I also skip all org files?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 13:08                                                                             ` Daniel Pittman
@ 2018-10-24 14:35                                                                               ` Stefan Monnier
  0 siblings, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-24 14:35 UTC (permalink / raw)
  To: emacs-devel

> For what it is worth, I agree with Joost, and I thought this *was* the
> required syntax for the use case being discussed.

What do you mean by "this"?

The use cases being discussed are those which could be rewritten to use
`cl-case`.  So which "pcase required syntax" are you thinking of which
is covered by the cl-case functionality?


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-23 18:12                                                                         ` Stefan Monnier
  2018-10-23 19:52                                                                           ` pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
@ 2018-10-24 15:03                                                                           ` Eli Zaretskii
  2018-10-24 15:30                                                                             ` Michael Heerdegen
                                                                                               ` (3 more replies)
  1 sibling, 4 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-24 15:03 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Tue, 23 Oct 2018 14:12:34 -0400
> 
> > I think so too, but it seems the majority of developers has a different
> > option, at least in this (old) thread.
> 
> So I guess I'm gonna have to try and argue my case.
> OK, here are the advantages I see for `cl-case`:

FWIW, my main problem is not even with cl-case, it's with 'cond'.  It
seems like we have some 'pcase' epidemic, whose first symptom is that
people stop using 'cond' and start using 'pcase' instead.  A few
examples:

todo-mode.el:

    (pcase this-param
      ('edit (todo-edit-item--text))
      ('header (todo-edit-item--text 'include-header))
      ('multiline (todo-edit-item--text 'multiline))
      ('add/edit (todo-edit-item--text 'comment-edit))
      ('delete (todo-edit-item--text 'comment-delete))
      ('diary (todo-edit-item--diary-inclusion))
      ('nonmarking (todo-edit-item--diary-inclusion 'nonmarking))
      [...]

auth-source-pass.el:

    (pcase (length matching-entries)
      (0 (auth-source-pass--do-debug "no match found")
         nil)
      (1 (auth-source-pass--do-debug "found 1 match: %s" (car matching-entries))
         (car matching-entries))
      (_ (auth-source-pass--select-one-entry matching-entries user)))))

bs.el:

           (setq bs-buffer-show-mark (pcase bs-buffer-show-mark
                                       (`nil   'never)
                                       (`never 'always)
                                       (_       nil))))))

calculator.el:

               (<= inp (pcase calculator-input-radix
                         (`nil ?9) (`bin ?1) (`oct ?7) (_ 999))))

lpr.el:

                 (pcase (count-lines (point-min) (point-max))
                   (0 "")
                   (1 ": ")
                   (_ ":\n"))

My favorite is imap.el, which does something like the above in 3
nested levels.  I will spare you the code, you can look it up.

Is it because people are too lazy to write (eq a b) as part of 'cond'?
Or is there something else I'm missing?  

You may wonder why I'm bothered by such uses.  It's because people are
evidently confused by 'pcase's arcane syntax, and therefore produce
obfuscated code even in the simple usage.  For example:

apropos.el:

      (pcase (car-safe x)
	;; (autoload (push (cdr x) autoloads))
	(`require (push (cdr x) requires))
	(`provide (push (cdr x) provides))
        (`t nil) ; Skip "was an autoload" entries.
        ;; FIXME: Print information about each individual method: both
        ;; its docstring and specializers (bug#21422).
        (`cl-defmethod (push (cadr x) provides))
	(_ (push (or (cdr-safe x) x) symbols))))

(Quick: what's the difference between `require and 'require in this
case?)

easy-mmode.el:

      (pcase keyw
	(`:group (setq group (nconc group (list :group (pop keys)))))
	(`:global (setq keys (cdr keys)))
	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))

(Aren't keywords supposed to be self-quoting? then why they are
explicitly quoted?)

We have dozens of such fragments in our codebase, which just makes the
sources harder to read, especially for people who aren't fluent with
'pcase' (which seems to be the case with many of us).

So I think we should begin by rewriting all of such uses as simple
'cond', and ask contributors not to use 'pcase' where a simple 'cond'
will do.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
@ 2018-10-24 15:30                                                                             ` Michael Heerdegen
  2018-10-24 15:40                                                                               ` Eli Zaretskii
                                                                                                 ` (2 more replies)
  2018-10-24 15:47                                                                             ` Clément Pit-Claudel
                                                                                               ` (2 subsequent siblings)
  3 siblings, 3 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-24 15:30 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> FWIW, my main problem is not even with cl-case, it's with 'cond'.  It
> seems like we have some 'pcase' epidemic, whose first symptom is that
> people stop using 'cond' and start using 'pcase' instead.  A few
> examples:
>
> todo-mode.el:
>
>     (pcase this-param
>       ('edit (todo-edit-item--text))
>       ('header (todo-edit-item--text 'include-header))
>       ('multiline (todo-edit-item--text 'multiline))
>       ('add/edit (todo-edit-item--text 'comment-edit))
>       ('delete (todo-edit-item--text 'comment-delete))
>       ('diary (todo-edit-item--diary-inclusion))
>       ('nonmarking (todo-edit-item--diary-inclusion 'nonmarking))
>       [...]
>
> auth-source-pass.el:
>
>     (pcase (length matching-entries)
>       (0 (auth-source-pass--do-debug "no match found")
>          nil)
>       (1 (auth-source-pass--do-debug "found 1 match: %s" (car matching-entries))
>          (car matching-entries))
>       (_ (auth-source-pass--select-one-entry matching-entries user)))))
>
> bs.el:
>
>            (setq bs-buffer-show-mark (pcase bs-buffer-show-mark
>                                        (`nil   'never)
>                                        (`never 'always)
>                                        (_       nil))))))
>
> calculator.el:
>
>                (<= inp (pcase calculator-input-radix
>                          (`nil ?9) (`bin ?1) (`oct ?7) (_ 999))))
>
> lpr.el:
>
>                  (pcase (count-lines (point-min) (point-max))
>                    (0 "")
>                    (1 ": ")
>                    (_ ":\n"))

FWIW, these are the major cases I wanted to treat, but I wanted to
replace them with equivalent cl-case forms, not with `cond's.

> (Quick: what's the difference between `require and 'require in this
> case?)

There is none any more.

> easy-mmode.el:
>
>       (pcase keyw
> 	(`:group (setq group (nconc group (list :group (pop keys)))))
> 	(`:global (setq keys (cdr keys)))
> 	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))
>
> (Aren't keywords supposed to be self-quoting? then why they are
> explicitly quoted?)

Yes.

> We have dozens of such fragments in our codebase, which just makes the
> sources harder to read, especially for people who aren't fluent with
> 'pcase' (which seems to be the case with many of us).

These are all cases I would want to fix, but unless the whole pcase form
can be trivially rewritten as cl-case, I want to leave pcase, really.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:30                                                                             ` Michael Heerdegen
@ 2018-10-24 15:40                                                                               ` Eli Zaretskii
  2018-10-24 15:48                                                                                 ` Michael Heerdegen
  2018-10-24 18:47                                                                               ` Garreau, Alexandre
  2018-10-27 15:19                                                                               ` Michael Heerdegen
  2 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-24 15:40 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Stefan Monnier <monnier@iro.umontreal.ca>,  emacs-devel@gnu.org
> Date: Wed, 24 Oct 2018 17:30:26 +0200
> 
> > We have dozens of such fragments in our codebase, which just makes the
> > sources harder to read, especially for people who aren't fluent with
> > 'pcase' (which seems to be the case with many of us).
> 
> These are all cases I would want to fix, but unless the whole pcase form
> can be trivially rewritten as cl-case, I want to leave pcase, really.

I agree with the "trivial" part, but why cl-case and not cond (with
the same "trivial" caveat)?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  2018-10-24 15:30                                                                             ` Michael Heerdegen
@ 2018-10-24 15:47                                                                             ` Clément Pit-Claudel
  2018-10-24 16:00                                                                               ` Eli Zaretskii
  2018-10-24 16:12                                                                             ` Alan Mackenzie
  2018-10-24 20:52                                                                             ` Stefan Monnier
  3 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-24 15:47 UTC (permalink / raw)
  To: emacs-devel

On 24/10/2018 11.03, Eli Zaretskii wrote:
> Is it because people are too lazy to write (eq a b) as part of 'cond'?
> Or is there something else I'm missing?  
I think some of us (me, at least), just like the forms you posted better :)  It's not a matter of lazyness, just preference.  The repetition of "eq" in each "cond" branch just looks redundant to me, and I have no trouble reading the pcase forms.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:40                                                                               ` Eli Zaretskii
@ 2018-10-24 15:48                                                                                 ` Michael Heerdegen
  2018-10-24 17:35                                                                                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-24 15:48 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> I agree with the "trivial" part, but why cl-case and not cond (with
> the same "trivial" caveat)?

Just because `cl-case' fits better? - for an equivalent rewrite using
`cond', I need to define an extra local variable to bind the treated
value to, event a name for it (we speak about ~ 300 cases!) and all cond
branches would look equally like (eq VAR 'VAL).  Not an improvement in
readability in my mind.

There is a minority (around ~ 20 cases) that look like

  (pcase EXPR
    ('X1 foo1)
    ('X2 foo2)
    ...
    (VAR EXPR-USING-THE-VAR))

with a catchall last branch that already use a variable binding.  These
would fit a bit better to `cond', but as said, that's a minority.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:47                                                                             ` Clément Pit-Claudel
@ 2018-10-24 16:00                                                                               ` Eli Zaretskii
  2018-10-24 19:00                                                                                 ` Clément Pit-Claudel
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-24 16:00 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
> Date: Wed, 24 Oct 2018 11:47:03 -0400
> 
> On 24/10/2018 11.03, Eli Zaretskii wrote:
> > Is it because people are too lazy to write (eq a b) as part of 'cond'?
> > Or is there something else I'm missing?  
> I think some of us (me, at least), just like the forms you posted better :)

Which forms? with or without the mistakes? ;-)

> The repetition of "eq" in each "cond" branch just looks redundant to me

If that's what bugs you, then how about

  (setq foo (assoc bar '((1 . one) (2 . two) ...)))

?

> and I have no trouble reading the pcase forms.

Please don't forget those who will read your code.  A code is written
once, but read many times.  It should be readable and
self-explanatory.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  2018-10-24 15:30                                                                             ` Michael Heerdegen
  2018-10-24 15:47                                                                             ` Clément Pit-Claudel
@ 2018-10-24 16:12                                                                             ` Alan Mackenzie
  2018-10-24 20:52                                                                             ` Stefan Monnier
  3 siblings, 0 replies; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-24 16:12 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

Hello, Eli.

On Wed, Oct 24, 2018 at 18:03:26 +0300, Eli Zaretskii wrote:
> > From: Stefan Monnier <monnier@iro.umontreal.ca>
> > Date: Tue, 23 Oct 2018 14:12:34 -0400

> > > I think so too, but it seems the majority of developers has a different
> > > option, at least in this (old) thread.

> > So I guess I'm gonna have to try and argue my case.
> > OK, here are the advantages I see for `cl-case`:

> FWIW, my main problem is not even with cl-case, it's with 'cond'.  It
> seems like we have some 'pcase' epidemic, whose first symptom is that
> people stop using 'cond' and start using 'pcase' instead.  A few
> examples:

[ .... ]

> My favorite is imap.el, which does something like the above in 3
> nested levels.  I will spare you the code, you can look it up.

> Is it because people are too lazy to write (eq a b) as part of 'cond'?
> Or is there something else I'm missing?  

> You may wonder why I'm bothered by such uses.  It's because people are
> evidently confused by 'pcase's arcane syntax, and therefore produce
> obfuscated code even in the simple usage.  For example:

[ .... ]

I'm somebody else who doesn't like pcase.  I don't like the way it has
purloined symbols which previously had a strong fixed meaning (``', `,',
`and', `or', and possibly more) and rendered them vague and with several
context dependent meanings.

For an Emacs Lisp beginner, `and' and `or' used to be easy to grasp,
once past the concept of short-circuit evaluation.  ``' and `,' were
somewhat more difficult.  Now, given the ambiguity introduced by pcase,
they are all much more difficult to understand.

The documentation for pcase is now good, but it still gives me a
headache to trundle through it.  Unless it's changed very recently, that
for pcase variants such as pcase-let is still inadequate.

I find pcase uses hard to understand, and definitely prefer cond.

[ .... ]

> We have dozens of such fragments in our codebase, which just makes the
> sources harder to read, especially for people who aren't fluent with
> 'pcase' (which seems to be the case with many of us).

> So I think we should begin by rewriting all of such uses as simple
> 'cond', and ask contributors not to use 'pcase' where a simple 'cond'
> will do.

+1.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:48                                                                                 ` Michael Heerdegen
@ 2018-10-24 17:35                                                                                   ` Eli Zaretskii
  2018-10-24 17:55                                                                                     ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-24 17:35 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Wed, 24 Oct 2018 17:48:50 +0200
> 
> Eli Zaretskii <eliz@gnu.org> writes:
> 
> > I agree with the "trivial" part, but why cl-case and not cond (with
> > the same "trivial" caveat)?
> 
> Just because `cl-case' fits better? - for an equivalent rewrite using
> `cond', I need to define an extra local variable to bind the treated
> value to, event a name for it (we speak about ~ 300 cases!) and all cond
> branches would look equally like (eq VAR 'VAL).  Not an improvement in
> readability in my mind.

I guess we will have to disagree about that.  At the very least, you
require people to be acquainted with cl-case well enough.

And if repeating (eq foo 'bar) is the issue, you can use assoc and a
data structure, see my other message.  Just a thought.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 17:35                                                                                   ` Eli Zaretskii
@ 2018-10-24 17:55                                                                                     ` Michael Heerdegen
  2018-10-24 18:32                                                                                       ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-24 17:55 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> And if repeating (eq foo 'bar) is the issue, you can use assoc and a
> data structure, see my other message.  Just a thought.

That won't do it: pcase (or cl-case) clauses specify expressions to
evaluate instead of only values to return.  Only those pcase forms that
have no side effects could be transformed into such an cdr-assoc
combination.

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 17:55                                                                                     ` Michael Heerdegen
@ 2018-10-24 18:32                                                                                       ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-24 18:32 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Wed, 24 Oct 2018 19:55:28 +0200
> 
> > And if repeating (eq foo 'bar) is the issue, you can use assoc and a
> > data structure, see my other message.  Just a thought.
> 
> That won't do it: pcase (or cl-case) clauses specify expressions to
> evaluate instead of only values to return.  Only those pcase forms that
> have no side effects could be transformed into such an cdr-assoc
> combination.

Yes, but there are gobs of those.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:30                                                                             ` Michael Heerdegen
  2018-10-24 15:40                                                                               ` Eli Zaretskii
@ 2018-10-24 18:47                                                                               ` Garreau, Alexandre
  2018-10-27 15:19                                                                               ` Michael Heerdegen
  2 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-24 18:47 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, Stefan Monnier, emacs-devel

On 2018-10-24 at 17:30, Michael Heerdegen wrote:
> Eli Zaretskii <eliz@gnu.org> writes:
>
>> FWIW, my main problem is not even with cl-case, it's with 'cond'.  It
>> seems like we have some 'pcase' epidemic, whose first symptom is that
>> people stop using 'cond' and start using 'pcase' instead.  A few
>> examples:
>>
>> todo-mode.el:
>>
>>     (pcase this-param
>>       ('edit (todo-edit-item--text))
>>       ('header (todo-edit-item--text 'include-header))
>>       ('multiline (todo-edit-item--text 'multiline))
>>       ('add/edit (todo-edit-item--text 'comment-edit))
>>       ('delete (todo-edit-item--text 'comment-delete))
>>       ('diary (todo-edit-item--diary-inclusion))
>>       ('nonmarking (todo-edit-item--diary-inclusion 'nonmarking))
>>       [...]
>>
>> auth-source-pass.el:
>>
>>     (pcase (length matching-entries)
>>       (0 (auth-source-pass--do-debug "no match found")
>>          nil)
>>       (1 (auth-source-pass--do-debug "found 1 match: %s" (car matching-entries))
>>          (car matching-entries))
>>       (_ (auth-source-pass--select-one-entry matching-entries user)))))
>>
>> bs.el:
>>
>>            (setq bs-buffer-show-mark (pcase bs-buffer-show-mark
>>                                        (`nil   'never)
>>                                        (`never 'always)
>>                                        (_       nil))))))
>>
>> calculator.el:
>>
>>                (<= inp (pcase calculator-input-radix
>>                          (`nil ?9) (`bin ?1) (`oct ?7) (_ 999))))
>>
>> lpr.el:
>>
>>                  (pcase (count-lines (point-min) (point-max))
>>                    (0 "")
>>                    (1 ": ")
>>                    (_ ":\n"))
>
> FWIW, these are the major cases I wanted to treat, but I wanted to
> replace them with equivalent cl-case forms, not with `cond's.
>
>> (Quick: what's the difference between `require and 'require in this
>> case?)
>
> There is none any more.
>
>> easy-mmode.el:
>>
>>       (pcase keyw
>> 	(`:group (setq group (nconc group (list :group (pop keys)))))
>> 	(`:global (setq keys (cdr keys)))
>> 	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))
>>
>> (Aren't keywords supposed to be self-quoting? then why they are
>> explicitly quoted?)
>
> Yes.
>
>> We have dozens of such fragments in our codebase, which just makes the
>> sources harder to read, especially for people who aren't fluent with
>> 'pcase' (which seems to be the case with many of us).
>
> These are all cases I would want to fix, but unless the whole pcase form
> can be trivially rewritten as cl-case, I want to leave pcase, really.

I’d prefer much this, as I find `case' well much less redundant, it’s
just basic factorization.  Programming is here to factorize, so it
should be factorized.  Even C do that.  Case is the simpler, most
obvious and straightforward to factorize a lot of cond (it is a shame we
don’t have it with equal, some case* or case-equal would be
appreciated).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 16:00                                                                               ` Eli Zaretskii
@ 2018-10-24 19:00                                                                                 ` Clément Pit-Claudel
  2018-10-24 19:09                                                                                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-24 19:00 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

On 24/10/2018 12.00, Eli Zaretskii wrote:
>> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
>> The repetition of "eq" in each "cond" branch just looks redundant to me
> 
> If that's what bugs you, then how about
> 
>   (setq foo (assoc bar '((1 . one) (2 . two) ...)))

This only works for constant branch bodies, and I find it marginally harder to read (especially if a default value is specified).
But I agree that it's not a bad solution when the branch body is constant.
For large collections, I imagine you would use a hashtable? Is that how the switch bytecode is implemented? IIUC, cond and pcase will be translated to a switch, but not assoc, even with a constant association list.

>> and I have no trouble reading the pcase forms.
> 
> Please don't forget those who will read your code.  A code is written
> once, but read many times.  It should be readable and
> self-explanatory.

Of course. Note that I mentioned reading the pcase forms, not writing them. I'm just pointing out that there are readers who find pcase more readable than either assoc or cond with eq tests.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 19:00                                                                                 ` Clément Pit-Claudel
@ 2018-10-24 19:09                                                                                   ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-24 19:09 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

> Cc: emacs-devel@gnu.org
> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
> Date: Wed, 24 Oct 2018 15:00:46 -0400
> 
> For large collections, I imagine you would use a hashtable?

I doubt that you will see in practice collections that are so long
that assoc is too slow.

> > Please don't forget those who will read your code.  A code is written
> > once, but read many times.  It should be readable and
> > self-explanatory.
> 
> Of course. Note that I mentioned reading the pcase forms, not writing them. I'm just pointing out that there are readers who find pcase more readable than either assoc or cond with eq tests.

I think the complicated quoting (frequently used incorrectly) of pcase
makes it harder to read for at least some, if nothing else, because
they need to waste time trying to understand what is the reason for
using those quotes.  I know it happened to me.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
                                                                                               ` (2 preceding siblings ...)
  2018-10-24 16:12                                                                             ` Alan Mackenzie
@ 2018-10-24 20:52                                                                             ` Stefan Monnier
  2018-10-25  7:17                                                                               ` Stephen Berman
  2018-10-25 14:47                                                                               ` Eli Zaretskii
  3 siblings, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-24 20:52 UTC (permalink / raw)
  To: emacs-devel

>     (pcase this-param
>       ('edit (todo-edit-item--text))
>       ('header (todo-edit-item--text 'include-header))
>       ('multiline (todo-edit-item--text 'multiline))
>       ('add/edit (todo-edit-item--text 'comment-edit))
>       ('delete (todo-edit-item--text 'comment-delete))
>       ('diary (todo-edit-item--diary-inclusion))
>       ('nonmarking (todo-edit-item--diary-inclusion 'nonmarking))
>       [...]

Is the below any better?

    (cond
      ((eq this-param 'edit) (todo-edit-item--text))
      ((eq this-param 'header) (todo-edit-item--text 'include-header))
      ((eq this-param 'multiline) (todo-edit-item--text 'multiline))
      ((eq this-paran 'add/edit) (todo-edit-item--text 'comment-edit))
      ((eq this-parom 'delete) (todo-edit-item--text 'comment-delete))
      ((eq this-param 'diary) (todo-edit-item--diary-inclusion))
      ((eq this-param 'nonmarking) (todo-edit-item--diary-inclusion 'nonmarking))
      [...]

To me, it's more verbose and more complex because you need to double
check that the same var is tested each time before you can know that it's
equivalent to a C-style `switch`.

IOW, I consider rewriting the `cond` to use `pcase` to be a form of
"common sub-expression elimination", or reduction of copy&paste.

I think rewriting those pcase uses into cond+eq would be equivalent for
me to rewriting dolists into while+pop loops (where you similarly can't
tell whether the loop advances by a single element each time without
consulting the loop body looking for all assignments to the temp var on
which the iteration is performed).

I prefer pcase to cl-case but I even much more strongly prefer cl-case
over cond+eq.

> My favorite is imap.el, which does something like the above in 3
> nested levels.  I will spare you the code, you can look it up.

We clearly have very different programming backgrounds: to me the "case
style" is much nicer and easier to read, closer to what I think in
my head, whereas the "cond+eq style" is like a "assembly-language"
version of the same.

> Is it because people are too lazy to write (eq a b) as part of 'cond'?
> Or is there something else I'm missing?

As a researcher in programming languages, I consider that my job is to
design and bring to practitioners tools that let them write in ways that
are closer to how they think than to how the machine thinks (while
still being able to turn it into something the machine can run efficiently).

The above argument of "too lazy to write ..." reminds me of the
resistance against the introduction of "high-level languages" instead of
the use of assembly language.

> You may wonder why I'm bothered by such uses.  It's because people are
> evidently confused by 'pcase's arcane syntax, and therefore produce
> obfuscated code even in the simple usage.  For example:
>
> apropos.el:
>
>       (pcase (car-safe x)
> 	;; (autoload (push (cdr x) autoloads))
> 	(`require (push (cdr x) requires))
> 	(`provide (push (cdr x) provides))
>         (`t nil) ; Skip "was an autoload" entries.
>         ;; FIXME: Print information about each individual method: both
>         ;; its docstring and specializers (bug#21422).
>         (`cl-defmethod (push (cadr x) provides))
> 	(_ (push (or (cdr-safe x) x) symbols))))
>
> (Quick: what's the difference between `require and 'require in this
> case?)

Same difference as between 'require and `require in normal Elisp code.
Why is that a problem in pcase and not in the rest of Elisp?

[ The story behind this is that the first version of pcase
  only supported the ` syntax and the syntax was added to provide
  a "target" for the expansion of ` when ` was made into
  a pcase-macro rather than a core pcase functionality.  ]

> easy-mmode.el:
>
>       (pcase keyw
> 	(`:group (setq group (nconc group (list :group (pop keys)))))
> 	(`:global (setq keys (cdr keys)))
> 	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))
>
> (Aren't keywords supposed to be self-quoting? then why they are
> explicitly quoted?)

Same reason why keyaords might be (back)quoted in some Elisp code?
[ Or maybe also because keywords were originally not self-quoting in
  pcase macros?  ]

> So I think we should begin by rewriting all of such uses as simple
> 'cond', and ask contributors not to use 'pcase' where a simple 'cond'
> will do.

From where I stand it would be a very sad step backward.
Rewriting those to use ' quoting (or no quoting at all when not needed)
is fine (tho not important), but the cond form is clearly inferior IMO.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 10:16                                                                         ` Replace trivial pcase occurrences in the Emacs sources João Távora
  2018-10-24 13:05                                                                           ` Stefan Monnier
@ 2018-10-25  3:11                                                                           ` Richard Stallman
  2018-10-25 12:42                                                                             ` Stefan Monnier
  1 sibling, 1 reply; 375+ messages in thread
From: Richard Stallman @ 2018-10-25  3:11 UTC (permalink / raw)
  To: João Távora
  Cc: michael_heerdegen, eliz, monnier, emacs-devel

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

Several people say they find pcase unclear.  Indeed, its documentation
describes various special cases.

This raises the question: can we develop a clearer alternative spec
for a new constuct?  Would people like to try out various
alternatives?

-- 
Dr Richard Stallman
President, Free Software Foundation (https://gnu.org, https://fsf.org)
Internet Hall-of-Famer (https://internethalloffame.org)





^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 20:52                                                                             ` Stefan Monnier
@ 2018-10-25  7:17                                                                               ` Stephen Berman
  2018-10-25 14:47                                                                               ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: Stephen Berman @ 2018-10-25  7:17 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On Wed, 24 Oct 2018 16:52:23 -0400 Stefan Monnier <monnier@iro.umontreal.ca> wrote:

>>     (pcase this-param
>>       ('edit (todo-edit-item--text))
>>       ('header (todo-edit-item--text 'include-header))
>>       ('multiline (todo-edit-item--text 'multiline))
>>       ('add/edit (todo-edit-item--text 'comment-edit))
>>       ('delete (todo-edit-item--text 'comment-delete))
>>       ('diary (todo-edit-item--diary-inclusion))
>>       ('nonmarking (todo-edit-item--diary-inclusion 'nonmarking))
>>       [...]
>
> Is the below any better?
>
>     (cond
>       ((eq this-param 'edit) (todo-edit-item--text))
>       ((eq this-param 'header) (todo-edit-item--text 'include-header))
>       ((eq this-param 'multiline) (todo-edit-item--text 'multiline))
>       ((eq this-paran 'add/edit) (todo-edit-item--text 'comment-edit))
>       ((eq this-parom 'delete) (todo-edit-item--text 'comment-delete))
>       ((eq this-param 'diary) (todo-edit-item--diary-inclusion))
>       ((eq this-param 'nonmarking) (todo-edit-item--diary-inclusion 'nonmarking))
>       [...]
>
> To me, it's more verbose and more complex because you need to double
> check that the same var is tested each time before you can know that it's
> equivalent to a C-style `switch`.
>
> IOW, I consider rewriting the `cond` to use `pcase` to be a form of
> "common sub-expression elimination", or reduction of copy&paste.

FWIW, this is basically the reason I used pcase instead of cond in the
above code, it wasn't just to jump on the pcase bandwagon (and it didn't
occur to me at the time to use cl-case).

Steve Berman



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25  3:11                                                                           ` Richard Stallman
@ 2018-10-25 12:42                                                                             ` Stefan Monnier
  2018-10-25 23:53                                                                               ` Andy Moreton
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-25 12:42 UTC (permalink / raw)
  To: emacs-devel

> This raises the question: can we develop a clearer alternative spec
> for a new constuct?  Would people like to try out various alternatives?

Indeed, this can be done without having to re-implement the underlying
machinery since you can easily use a macro-layer on top of pcase
(either via normal defmacro or via pcase-defmacro, or both).


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 20:52                                                                             ` Stefan Monnier
  2018-10-25  7:17                                                                               ` Stephen Berman
@ 2018-10-25 14:47                                                                               ` Eli Zaretskii
  2018-10-25 15:32                                                                                 ` Stefan Monnier
  2018-10-27 17:48                                                                                 ` Garreau, Alexandre
  1 sibling, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-25 14:47 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Wed, 24 Oct 2018 16:52:23 -0400
> 
> >     (pcase this-param
> >       ('edit (todo-edit-item--text))
> >       ('header (todo-edit-item--text 'include-header))
> >       ('multiline (todo-edit-item--text 'multiline))
> >       ('add/edit (todo-edit-item--text 'comment-edit))
> >       ('delete (todo-edit-item--text 'comment-delete))
> >       ('diary (todo-edit-item--diary-inclusion))
> >       ('nonmarking (todo-edit-item--diary-inclusion 'nonmarking))
> >       [...]
> 
> Is the below any better?
> 
>     (cond
>       ((eq this-param 'edit) (todo-edit-item--text))
>       ((eq this-param 'header) (todo-edit-item--text 'include-header))
>       ((eq this-param 'multiline) (todo-edit-item--text 'multiline))
>       ((eq this-paran 'add/edit) (todo-edit-item--text 'comment-edit))
>       ((eq this-parom 'delete) (todo-edit-item--text 'comment-delete))
>       ((eq this-param 'diary) (todo-edit-item--diary-inclusion))
>       ((eq this-param 'nonmarking) (todo-edit-item--diary-inclusion 'nonmarking))
>       [...]

Yes (modulo the typos).

> To me, it's more verbose and more complex because you need to double
> check that the same var is tested each time before you can know that it's
> equivalent to a C-style `switch`.

But it isn't equivalent to C-style 'switch': it doesn't compare like C
does, and it doesn't dispatch like C does.  (I find it generally not
useful to think in C concepts when programming in Lisp, because it
might cause confusion and mistakes.)

> IOW, I consider rewriting the `cond` to use `pcase` to be a form of
> "common sub-expression elimination", or reduction of copy&paste.

Unfortunately, it makes the code more subtle and less
self-explanatory.  Not for you and me, perhaps, but for quite a few
people who aren't as familiar with these macros, it seems.

> I think rewriting those pcase uses into cond+eq would be equivalent for
> me to rewriting dolists into while+pop loops

IMO, it isn't equivalent, because dolist doesn't invent new syntax,
not as much as pcase does.

> I prefer pcase to cl-case but I even much more strongly prefer cl-case
> over cond+eq.

The thing is, both cl-case and pcase are subtly different from the
"boring" cond, and from each other.  E.g., cl-case uses eql to
compare, so works with floats, but not with strings; pcase decides
what predicate to use according to the data, so works with strings,
but strangely doesn't work with floats.  Again, perhaps this is not a
problem for you and me, but newcomers might well stumble on these
subtleties, and at the very least will have to consult the docs to
know for sure.

By contrast, with cond everything is explicit and self-explanatory.
The programmer decides which equality to use.  Yes, that does come for
a price, but copy-yanking is cheap and fast, as is "M-/", and also
avoids typos.

> We clearly have very different programming backgrounds: to me the "case
> style" is much nicer and easier to read, closer to what I think in
> my head, whereas the "cond+eq style" is like a "assembly-language"
> version of the same.

This isn't about style, this is about using macro facilities to
significantly change the syntax of a language.

E.g., what do you think about people who use cpp to define macros
BEGIN and END that expand into braces?  One could argue that it is
"closer to what one thinks in their head", or being "higher-level",
and yet such practices are generally discouraged.

> > (Quick: what's the difference between `require and 'require in this
> > case?)
> 
> Same difference as between 'require and `require in normal Elisp code.
> Why is that a problem in pcase and not in the rest of Elisp?

Because people stumble on this and are likely to waste time trying to
understand what kind of magic hides behind this.  Worse, they might
copy this without understanding (as we already see in our sources),
thus proliferating the obfuscation.

Mind you: I'm not against pcase where its power is needed.  It is IMO
needed where using the underlying core facilities would produce
something that is hard to follow and even harder to understand.
Simple comparisons against a collection of fixed values doesn't fit
that bill, IMO.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25 14:47                                                                               ` Eli Zaretskii
@ 2018-10-25 15:32                                                                                 ` Stefan Monnier
  2018-10-26 15:34                                                                                   ` Stefan Monnier
  2018-10-27 17:48                                                                                 ` Garreau, Alexandre
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-25 15:32 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

> Unfortunately, it makes the code more subtle and less
> self-explanatory.  Not for you and me, perhaps, but for quite a few
> people who aren't as familiar with these macros, it seems.

I can see why someone would feel this way when looking at
a destructuring pcase macro.  But for something like:

    (pcase this-param
      ('edit (todo-edit-item--text))
      ('header (todo-edit-item--text 'include-header))
      ('multiline (todo-edit-item--text 'multiline))
      ('add/edit (todo-edit-item--text 'comment-edit))
      ('delete (todo-edit-item--text 'comment-delete))

I have a hard time believing that there are more users who find it less
clear than its cond+eq expansion.

> The thing is, both cl-case and pcase are subtly different from the
> "boring" cond, and from each other.  E.g., cl-case uses eql to
> compare, so works with floats, but not with strings;

Right.

> pcase decides what predicate to use according to the data,

No: it uses `equal` (the implementation may optimize it to something
else, but the documented behavior is that it compares with `equal` for
all patterns of the form 'VAL and for the corresponding accepted
shorthands (i.e. non-quoted strings, keywords and integers)).

> so works with strings, but strangely doesn't work with floats.

Actually it does for a pattern like '4.5
What it doesn't currently is provide the non-quoted shorthand for floats.
Maybe it can be considered strange, but at least it rejects such
a pattern upfront with an error.  Of course, it's trivial to change it
to accept non-quoted floats if we want to do it.

> Again, perhaps this is not a problem for you and me, but newcomers
> might well stumble on these subtleties, and at the very least will
> have to consult the docs to know for sure.

When reading pcase code, all they need to know is that comparison is
done with `equal`, which AFAIK is always the most obvious and
natural behavior.

Restrictions like non-quoted floats only impact those rare people which
will *write* a pcase pattern in which they want to put a float.

> By contrast, with cond everything is explicit and self-explanatory.

Every *step* is self-explanatory, but the overall goal is not: as
a reader, I have to scrutinize every condition to see if the overall
goal was indeed to "dispatch based on the value of X".

>> We clearly have very different programming backgrounds: to me the "case
>> style" is much nicer and easier to read, closer to what I think in
>> my head, whereas the "cond+eq style" is like a "assembly-language"
>> version of the same.
> This isn't about style, this is about using macro facilities to
> significantly change the syntax of a language.

`pcase` doesn't just change the syntax of cond+eq, like your
BEGIN/END example.  Instead it provides a new abstraction.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25 12:42                                                                             ` Stefan Monnier
@ 2018-10-25 23:53                                                                               ` Andy Moreton
  2018-10-26 14:59                                                                                 ` Stefan Monnier
  2018-10-28 21:44                                                                                 ` Stefan Monnier
  0 siblings, 2 replies; 375+ messages in thread
From: Andy Moreton @ 2018-10-25 23:53 UTC (permalink / raw)
  To: emacs-devel

On Thu 25 Oct 2018, Stefan Monnier wrote:

>> This raises the question: can we develop a clearer alternative spec
>> for a new constuct?  Would people like to try out various alternatives?
>
> Indeed, this can be done without having to re-implement the underlying
> machinery since you can easily use a macro-layer on top of pcase
> (either via normal defmacro or via pcase-defmacro, or both).

...which does not help existing users, who are still dealing with
inadequate documentation of the pcase family of macros, and with the
baffling syntax. pcase-lambda, pcase-let, pcase-let*, and pcase-dolist
still have no meaningful documentation, and are not even mentioned in
the manual.

Pattern matching is a useful facility, but pcase is woefully hard to use
correctly, as the existing (mis-)usage shows. Something that is
significantly easier to read and comprehend is needed.

    AndyM




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase pattern syntax (was: Replace trivial pcase occurrences in the Emacs sources)
  2018-10-24 13:03                                                                           ` pcase pattern syntax (was: Replace trivial pcase occurrences in the Emacs sources) Stefan Monnier
@ 2018-10-26  7:16                                                                             ` Joost Kremers
  0 siblings, 0 replies; 375+ messages in thread
From: Joost Kremers @ 2018-10-26  7:16 UTC (permalink / raw)
  To: Stefan Monnier

On Wed, Oct 24, 2018 at 09:03:51AM -0400, Stefan Monnier wrote:
> > (pcase value
> >   (`(,_ 1 2)
> >    (message "Matched a list of anything followed by (1 2)")))
> >
> > It is not clear to me why I couldn't simply write:
> >
> > (pcase value
> >   ((_ 1 2)
> >    (message "Matched a list of anything followed by (1 2)")))
> 
> The reason is simple: because pcase uses a more verbose pattern syntax.

Perhaps I should have said "not immediately clear".

I've snipped the rest of your reply, not because it's not interesting (it is) but because I'm really not qualified to argue better pattern matching syntax with you. I was just trying to answer Richard's question, who was wondering why people don't seem to use/like pcase as much as one might expect. And since I had tried a few times in the past to grok pcase but never really got it, I thought it might be helpful to offer my perspective.

I'm sure that with some practice I could "get" pcase, it's not *that* difficult. I just find it noticeably more difficult to grok than other Elisp constructs that are new to me. Usually, it's enough to read the manual to get a basic idea of how and when to use something. Not so with pcase.



-- 
Joost Kremers
Life has its moments



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25 23:53                                                                               ` Andy Moreton
@ 2018-10-26 14:59                                                                                 ` Stefan Monnier
  2018-10-26 15:44                                                                                   ` Garreau, Alexandre
  2018-10-27 12:09                                                                                   ` Andy Moreton
  2018-10-28 21:44                                                                                 ` Stefan Monnier
  1 sibling, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-26 14:59 UTC (permalink / raw)
  To: emacs-devel

> Pattern matching is a useful facility, but pcase is woefully hard to use
> correctly, as the existing (mis-)usage shows.  Something that is
> significantly easier to read and comprehend is needed.

I was just pointing out that it is easy to *experiment* with new
syntaxes (in order to find a new syntax so as to solve the current
problems).


        Stefan "not convinced there's a solution to this problem, tho"




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25 15:32                                                                                 ` Stefan Monnier
@ 2018-10-26 15:34                                                                                   ` Stefan Monnier
  0 siblings, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-26 15:34 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

>     (pcase this-param
>       ('edit (todo-edit-item--text))
>       ('header (todo-edit-item--text 'include-header))
>       ('multiline (todo-edit-item--text 'multiline))
>       ('add/edit (todo-edit-item--text 'comment-edit))
>       ('delete (todo-edit-item--text 'comment-delete))
>
> I have a hard time believing that there are more users who find it less
> clear than its cond+eq expansion.

BTW, I just bumped into another benefit of `pcase` for such code:

When I converted a particular cond+eq thingy yesterday, pcase gave me
a warning about redundant pattern, because indeed one of the original
`cond` branches was unreachable.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-26 14:59                                                                                 ` Stefan Monnier
@ 2018-10-26 15:44                                                                                   ` Garreau, Alexandre
  2018-10-27 12:09                                                                                   ` Andy Moreton
  1 sibling, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-26 15:44 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-26 at 10:59, Stefan Monnier wrote:
>> Pattern matching is a useful facility, but pcase is woefully hard to use
>> correctly, as the existing (mis-)usage shows.  Something that is
>> significantly easier to read and comprehend is needed.
>
> I was just pointing out that it is easy to *experiment* with new
> syntaxes (in order to find a new syntax so as to solve the current
> problems).
>
>
>         Stefan "not convinced there's a solution to this problem, tho"

I think liking current pcase or not, more or less than cl-case or cond,
everybody would like to get pcase improved, anyway.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-26 14:59                                                                                 ` Stefan Monnier
  2018-10-26 15:44                                                                                   ` Garreau, Alexandre
@ 2018-10-27 12:09                                                                                   ` Andy Moreton
  1 sibling, 0 replies; 375+ messages in thread
From: Andy Moreton @ 2018-10-27 12:09 UTC (permalink / raw)
  To: emacs-devel

On Fri 26 Oct 2018, Stefan Monnier wrote:

>> Pattern matching is a useful facility, but pcase is woefully hard to use
>> correctly, as the existing (mis-)usage shows.  Something that is
>> significantly easier to read and comprehend is needed.
>
> I was just pointing out that it is easy to *experiment* with new
> syntaxes (in order to find a new syntax so as to solve the current
> problems).

Sure, but you have also removed the other part of my comment. Where is
the missing documentation ? Why was it not added at the same time as the
code ? Meaningful doc strings and entries in the manual are long
overdue.

    AndyM




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-24 15:30                                                                             ` Michael Heerdegen
  2018-10-24 15:40                                                                               ` Eli Zaretskii
  2018-10-24 18:47                                                                               ` Garreau, Alexandre
@ 2018-10-27 15:19                                                                               ` Michael Heerdegen
  2018-10-27 16:56                                                                                 ` Garreau, Alexandre
                                                                                                   ` (2 more replies)
  2 siblings, 3 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-27 15:19 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

[-- Attachment #1: Type: text/plain, Size: 2640 bytes --]

Michael Heerdegen <michael_heerdegen@web.de> writes:

> > easy-mmode.el:
> >
> >       (pcase keyw
> > 	(`:group (setq group (nconc group (list :group (pop keys)))))
> > 	(`:global (setq keys (cdr keys)))
> > 	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))
> >
> > (Aren't keywords supposed to be self-quoting? then why they are
> > explicitly quoted?)

> These are all cases I would want to fix, but unless the whole pcase form
> can be trivially rewritten as cl-case, I want to leave pcase, really.

Here is the first patch addressing quoted selfquoting patterns.  I left
out cl-generic.el which is distributed via Gnu Elpa because selfquoting
pattern types are two years younger than pcase is.

Is the commit message ok as it is?  Or should I list the changed files
to say "All callers changed" every time?

Here and there the patch also fixes indentation of surrounding code.

In the next step I want to replace `DOESNT-UNQUOTE -> DOESNT-UNQUOTE,
though we have one opinion that didn't want me to do this so that the
code looks more frightening and people are warned.  I don't think it is
necessary to warn people about pcase, and I don't think warning people
about hard to read code by making the code even harder to read is a good
thing ;-)

What's then left is the task to replace all pcase forms that can be
trivially rewritten by using case or cond/assoc.  I must admit that
I'm very skeptical about this now.  Not only that we would only replace
exactly these pcase occurrences that are really trivial to read for
anybody, which could be, at the end, counterproductive for those people
who dislike pcase because the pcase forms left are the harder ones (Eli,
I know you don't think like that).

I also saw that people have very different likings, independent from
pcase.  Say, we have one third of people who want to keep pcase in these
cases, one third who want to replace it with cl-case, and one third who
want cond or assoc instead.  We have a clear majority against pcase.
But we also have a clear majority against cl-case, and a majority
against cond/assoc.

With all input I got, I came to the conclusion that what we have is
quite ok: A pcase with branches whose condition all look like 'CONSTANT
is not too hard to read for anyone.  I saw there are pros and cons for
and against keeping these in the code, but I didn't get the impression
that one side clearly prevails.

Eli and Stefan, if you could agree about something I should do, or if
the maintainer(s) tell me I should do these replacement, I still offer
to do it, but I don't think we came to any conclusion yet.

And here is the first patch:


[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0001-Don-t-quote-self-quoting-pcase-patterns.patch --]
[-- Type: text/x-diff, Size: 39052 bytes --]

From 0045835058ed5f0af07bfe2c67940824c6c084fd Mon Sep 17 00:00:00 2001
From: Michael Heerdegen <michael_heerdegen@web.de>
Date: Sat, 27 Oct 2018 01:48:35 +0200
Subject: [PATCH] Don't quote self-quoting pcase patterns

---
 admin/bzrmerge.el                   |  6 +--
 lisp/char-fold.el                   |  2 +-
 lisp/dired.el                       |  8 ++--
 lisp/emacs-lisp/derived.el          |  8 ++--
 lisp/emacs-lisp/easy-mmode.el       | 62 ++++++++++++++---------------
 lisp/emacs-lisp/easymenu.el         | 28 ++++++-------
 lisp/emacs-lisp/eieio-core.el       |  6 +--
 lisp/emacs-lisp/package.el          | 22 +++++-----
 lisp/emacs-lisp/smie.el             |  4 +-
 lisp/faces.el                       | 22 +++++-----
 lisp/filesets.el                    |  2 +-
 lisp/progmodes/modula2.el           | 22 +++++-----
 lisp/progmodes/octave.el            | 36 ++++++++---------
 lisp/progmodes/opascal.el           | 14 +++----
 lisp/progmodes/perl-mode.el         |  4 +-
 lisp/progmodes/prolog.el            | 14 +++----
 lisp/progmodes/ruby-mode.el         | 18 ++++-----
 lisp/progmodes/sh-script.el         | 18 ++++-----
 lisp/server.el                      | 32 +++++++--------
 lisp/subr.el                        |  2 +-
 lisp/textmodes/css-mode.el          |  2 +-
 test/lisp/emacs-lisp/pcase-tests.el |  2 +-
 22 files changed, 167 insertions(+), 167 deletions(-)

diff --git a/admin/bzrmerge.el b/admin/bzrmerge.el
index cedb625fb0..d54ba330f9 100644
--- a/admin/bzrmerge.el
+++ b/admin/bzrmerge.el
@@ -150,12 +150,12 @@ bzrmerge-missing
                              (format "%s: Skip (y/n/N/q/%s)? " str
                                      (key-description (vector help-char)))
                              '(?y ?n ?N ?q)))
-                      (`?y (setq skip t))
-                      (`?q (keyboard-quit))
+                      (?y (setq skip t))
+                      (?q (keyboard-quit))
                       ;; A single log entry can match skip-regexp multiple
                       ;; times.  If you are sure you don't want to skip it,
                       ;; you don't want to be asked multiple times.
-                      (`?N (setq skip 'no))))))
+                      (?N (setq skip 'no))))))
               (if (eq skip t)
                   (push revno skipped)
                 (push revno revnos)))))
diff --git a/lisp/char-fold.el b/lisp/char-fold.el
index 86bd6038e3..907d49e4f2 100644
--- a/lisp/char-fold.el
+++ b/lisp/char-fold.el
@@ -170,7 +170,7 @@ char-fold-to-regexp
     ;; need to keep them grouped together like this: "\\(  \\|[ ...][ ...]\\)".
     (while (< i end)
       (pcase (aref string i)
-        (`?\s (setq spaces (1+ spaces)))
+        (?\s (setq spaces (1+ spaces)))
         (c (when (> spaces 0)
              (push (char-fold--make-space-string spaces) out)
              (setq spaces 0))
diff --git a/lisp/dired.el b/lisp/dired.el
index 5c7bb9599c..f2f2b76eb7 100644
--- a/lisp/dired.el
+++ b/lisp/dired.el
@@ -3046,10 +3046,10 @@ dired-delete-file
                              ("no"   ?n "skip to next")
                              ("all"  ?! "delete all remaining directories with no more questions")
                              ("quit" ?q "exit")))
-                     ('"all" (setq recursive 'always dired-recursive-deletes recursive))
-                     ('"yes" (if (eq recursive 'top) (setq recursive 'always)))
-                     ('"no" (setq recursive nil))
-                     ('"quit" (keyboard-quit))
+                     ("all" (setq recursive 'always dired-recursive-deletes recursive))
+                     ("yes" (if (eq recursive 'top) (setq recursive 'always)))
+                     ("no" (setq recursive nil))
+                     ("quit" (keyboard-quit))
                      (_ (keyboard-quit))))) ; catch all unknown answers
              (setq recursive nil)) ; Empty dir or recursive is nil.
            (delete-directory file recursive trash))))
diff --git a/lisp/emacs-lisp/derived.el b/lisp/emacs-lisp/derived.el
index 6b47ffea07..483d6fbfa4 100644
--- a/lisp/emacs-lisp/derived.el
+++ b/lisp/emacs-lisp/derived.el
@@ -193,10 +193,10 @@ define-derived-mode
     ;; Process the keyword args.
     (while (keywordp (car body))
       (pcase (pop body)
-	(`:group (setq group (pop body)))
-	(`:abbrev-table (setq abbrev (pop body)) (setq declare-abbrev nil))
-	(`:syntax-table (setq syntax (pop body)) (setq declare-syntax nil))
-        (`:after-hook (setq after-hook (pop body)))
+	(:group (setq group (pop body)))
+	(:abbrev-table (setq abbrev (pop body)) (setq declare-abbrev nil))
+	(:syntax-table (setq syntax (pop body)) (setq declare-syntax nil))
+        (:after-hook (setq after-hook (pop body)))
 	(_ (pop body))))
 
     (setq docstring (derived-mode-make-docstring
diff --git a/lisp/emacs-lisp/easy-mmode.el b/lisp/emacs-lisp/easy-mmode.el
index 4d8a502026..d74c3ddb97 100644
--- a/lisp/emacs-lisp/easy-mmode.el
+++ b/lisp/emacs-lisp/easy-mmode.el
@@ -217,30 +217,30 @@ define-minor-mode
     (while (keywordp (setq keyw (car body)))
       (setq body (cdr body))
       (pcase keyw
-	(`:init-value (setq init-value (pop body)))
-	(`:lighter (setq lighter (purecopy (pop body))))
-	(`:global (setq globalp (pop body))
-         (when (and globalp (symbolp mode))
-           (setq setter `(setq-default ,mode))
-           (setq getter `(default-value ',mode))))
-	(`:extra-args (setq extra-args (pop body)))
-	(`:set (setq set (list :set (pop body))))
-	(`:initialize (setq initialize (list :initialize (pop body))))
-	(`:group (setq group (nconc group (list :group (pop body)))))
-	(`:type (setq type (list :type (pop body))))
-	(`:require (setq require (pop body)))
-	(`:keymap (setq keymap (pop body)))
-        (`:variable (setq variable (pop body))
-         (if (not (and (setq tmp (cdr-safe variable))
-                       (or (symbolp tmp)
-                           (functionp tmp))))
-             ;; PLACE is not of the form (GET . SET).
-             (progn
-               (setq setter `(setf ,variable))
-               (setq getter variable))
-           (setq getter (car variable))
-           (setq setter `(funcall #',(cdr variable)))))
-	(`:after-hook (setq after-hook (pop body)))
+	(:init-value (setq init-value (pop body)))
+	(:lighter (setq lighter (purecopy (pop body))))
+	(:global (setq globalp (pop body))
+                 (when (and globalp (symbolp mode))
+                   (setq setter `(setq-default ,mode))
+                   (setq getter `(default-value ',mode))))
+	(:extra-args (setq extra-args (pop body)))
+	(:set (setq set (list :set (pop body))))
+	(:initialize (setq initialize (list :initialize (pop body))))
+	(:group (setq group (nconc group (list :group (pop body)))))
+	(:type (setq type (list :type (pop body))))
+	(:require (setq require (pop body)))
+	(:keymap (setq keymap (pop body)))
+        (:variable (setq variable (pop body))
+                   (if (not (and (setq tmp (cdr-safe variable))
+                                 (or (symbolp tmp)
+                                     (functionp tmp))))
+                       ;; PLACE is not of the form (GET . SET).
+                       (progn
+                         (setq setter `(setf ,variable))
+                         (setq getter variable))
+                     (setq getter (car variable))
+                     (setq setter `(funcall #',(cdr variable)))))
+	(:after-hook (setq after-hook (pop body)))
 	(_ (push keyw extra-keywords) (push (pop body) extra-keywords))))
 
     (setq keymap-sym (if (and keymap (symbolp keymap)) keymap
@@ -407,8 +407,8 @@ define-globalized-minor-mode
     (while (keywordp (setq keyw (car keys)))
       (setq keys (cdr keys))
       (pcase keyw
-	(`:group (setq group (nconc group (list :group (pop keys)))))
-	(`:global (setq keys (cdr keys)))
+	(:group (setq group (nconc group (list :group (pop keys)))))
+	(:global (setq keys (cdr keys)))
 	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))
 
     (unless group
@@ -533,11 +533,11 @@ easy-mmode-define-keymap
       (let ((key (pop args))
 	    (val (pop args)))
 	(pcase key
-	 (`:name (setq name val))
-	 (`:dense (setq dense val))
-	 (`:inherit (setq inherit val))
-	 (`:suppress (setq suppress val))
-	 (`:group)
+	  (:name (setq name val))
+	  (:dense (setq dense val))
+	  (:inherit (setq inherit val))
+	  (:suppress (setq suppress val))
+	  (:group)
 	 (_ (message "Unknown argument %s in defmap" key)))))
     (unless (keymapp m)
       (setq bs (append m bs))
diff --git a/lisp/emacs-lisp/easymenu.el b/lisp/emacs-lisp/easymenu.el
index 94d035f374..403829ac46 100644
--- a/lisp/emacs-lisp/easymenu.el
+++ b/lisp/emacs-lisp/easymenu.el
@@ -226,14 +226,14 @@ easy-menu-create-menu
       (let ((arg (cadr menu-items)))
         (setq menu-items (cddr menu-items))
         (pcase keyword
-          (`:filter
+          (:filter
            (setq filter (lambda (menu)
                           (easy-menu-filter-return (funcall arg menu)
                                                    menu-name))))
-          ((or `:enable `:active) (setq enable (or arg ''nil)))
-          (`:label (setq label arg))
-          (`:help (setq help arg))
-          ((or `:included `:visible) (setq visible (or arg ''nil))))))
+          ((or :enable :active) (setq enable (or arg ''nil)))
+          (:label (setq label arg))
+          (:help (setq help arg))
+          ((or :included :visible) (setq visible (or arg ''nil))))))
     (if (equal visible ''nil)
 	nil				; Invisible menu entry, return nil.
       (if (and visible (not (easy-menu-always-true-p visible)))
@@ -325,15 +325,15 @@ easy-menu-convert-item-1
 		(setq arg (aref item (1+ count)))
 		(setq count (+ 2 count))
 		(pcase keyword
-                  ((or `:included `:visible) (setq visible (or arg ''nil)))
-                  (`:key-sequence (setq cache arg cache-specified t))
-                  (`:keys (setq keys arg no-name nil))
-                  (`:label (setq label arg))
-                  ((or `:active `:enable) (setq active (or arg ''nil)))
-                  (`:help (setq prop (cons :help (cons arg prop))))
-                  (`:suffix (setq suffix arg))
-                  (`:style (setq style arg))
-                  (`:selected (setq selected (or arg ''nil)))))
+                  ((or :included :visible) (setq visible (or arg ''nil)))
+                  (:key-sequence (setq cache arg cache-specified t))
+                  (:keys (setq keys arg no-name nil))
+                  (:label (setq label arg))
+                  ((or :active :enable) (setq active (or arg ''nil)))
+                  (:help (setq prop (cons :help (cons arg prop))))
+                  (:suffix (setq suffix arg))
+                  (:style (setq style arg))
+                  (:selected (setq selected (or arg ''nil)))))
 	      (if suffix
 		  (setq label
 			(if (stringp suffix)
diff --git a/lisp/emacs-lisp/eieio-core.el b/lisp/emacs-lisp/eieio-core.el
index e5ea33c003..e5c4f198f5 100644
--- a/lisp/emacs-lisp/eieio-core.el
+++ b/lisp/emacs-lisp/eieio-core.el
@@ -388,9 +388,9 @@ eieio-defclass-internal
 	;; Clean up the meaning of protection.
         (setq prot
               (pcase prot
-                ((or 'nil 'public ':public) nil)
-                ((or 'protected ':protected) 'protected)
-                ((or 'private ':private) 'private)
+                ((or 'nil 'public :public) nil)
+                ((or 'protected :protected) 'protected)
+                ((or 'private :private) 'private)
                 (_ (signal 'invalid-slot-type (list :protection prot)))))
 
 	;; The default type specifier is supposed to be t, meaning anything.
diff --git a/lisp/emacs-lisp/package.el b/lisp/emacs-lisp/package.el
index 9c4c3e9fe7..f2ffef8da7 100644
--- a/lisp/emacs-lisp/package.el
+++ b/lisp/emacs-lisp/package.el
@@ -2911,17 +2911,17 @@ package-menu--print-info-simple
 Return (PKG-DESC [NAME VERSION STATUS DOC])."
   (let* ((status  (package-desc-status pkg))
          (face (pcase status
-                 (`"built-in"  'package-status-built-in)
-                 (`"external"  'package-status-external)
-                 (`"available" 'package-status-available)
-                 (`"avail-obso" 'package-status-avail-obso)
-                 (`"new"       'package-status-new)
-                 (`"held"      'package-status-held)
-                 (`"disabled"  'package-status-disabled)
-                 (`"installed" 'package-status-installed)
-                 (`"dependency" 'package-status-dependency)
-                 (`"unsigned"  'package-status-unsigned)
-                 (`"incompat"  'package-status-incompat)
+                 ("built-in"  'package-status-built-in)
+                 ("external"  'package-status-external)
+                 ("available" 'package-status-available)
+                 ("avail-obso" 'package-status-avail-obso)
+                 ("new"       'package-status-new)
+                 ("held"      'package-status-held)
+                 ("disabled"  'package-status-disabled)
+                 ("installed" 'package-status-installed)
+                 ("dependency" 'package-status-dependency)
+                 ("unsigned"  'package-status-unsigned)
+                 ("incompat"  'package-status-incompat)
                  (_            'font-lock-warning-face)))) ; obsolete.
     (list pkg
           `[(,(symbol-name (package-desc-name pkg))
diff --git a/lisp/emacs-lisp/smie.el b/lisp/emacs-lisp/smie.el
index c01a40172b..4b82172984 100644
--- a/lisp/emacs-lisp/smie.el
+++ b/lisp/emacs-lisp/smie.el
@@ -1856,9 +1856,9 @@ smie-setup
     (let ((k (pop keywords))
           (v (pop keywords)))
       (pcase k
-        (`:forward-token
+        (:forward-token
          (set (make-local-variable 'smie-forward-token-function) v))
-        (`:backward-token
+        (:backward-token
          (set (make-local-variable 'smie-backward-token-function) v))
         (_ (message "smie-setup: ignoring unknown keyword %s" k)))))
   (let ((ca (cdr (assq :smie-closer-alist grammar))))
diff --git a/lisp/faces.el b/lisp/faces.el
index 18b821a0b6..a8c1546d5a 100644
--- a/lisp/faces.el
+++ b/lisp/faces.el
@@ -1084,27 +1084,27 @@ face-valid-attribute-values
 an integer value."
   (let ((valid
          (pcase attribute
-           (`:family
+           (:family
             (if (window-system frame)
                 (mapcar (lambda (x) (cons x x))
                         (font-family-list))
 	      ;; Only one font on TTYs.
 	      (list (cons "default" "default"))))
-           (`:foundry
+           (:foundry
 	    (list nil))
-	   (`:width
+	   (:width
 	    (mapcar #'(lambda (x) (cons (symbol-name (aref x 1)) (aref x 1)))
 		    font-width-table))
-           (`:weight
+           (:weight
 	    (mapcar #'(lambda (x) (cons (symbol-name (aref x 1)) (aref x 1)))
 		    font-weight-table))
-	   (`:slant
+	   (:slant
 	    (mapcar #'(lambda (x) (cons (symbol-name (aref x 1)) (aref x 1)))
 		    font-slant-table))
-	   (`:inverse-video
+	   (:inverse-video
 	    (mapcar #'(lambda (x) (cons (symbol-name x) x))
 		    (internal-lisp-face-attribute-values attribute)))
-           ((or `:underline `:overline `:strike-through `:box)
+           ((or :underline :overline :strike-through :box)
             (if (window-system frame)
                 (nconc (mapcar #'(lambda (x) (cons (symbol-name x) x))
                                (internal-lisp-face-attribute-values attribute))
@@ -1112,12 +1112,12 @@ face-valid-attribute-values
                                (defined-colors frame)))
 	      (mapcar #'(lambda (x) (cons (symbol-name x) x))
 		      (internal-lisp-face-attribute-values attribute))))
-           ((or `:foreground `:background)
+           ((or :foreground :background)
             (mapcar #'(lambda (c) (cons c c))
                     (defined-colors frame)))
-           (`:height
+           (:height
             'integerp)
-           (`:stipple
+           (:stipple
             (and (memq (window-system frame) '(x ns)) ; No stipple on w32
                  (mapcar #'list
                          (apply #'nconc
@@ -1126,7 +1126,7 @@ face-valid-attribute-values
                                                (file-directory-p dir)
                                                (directory-files dir)))
                                         x-bitmap-file-path)))))
-           (`:inherit
+           (:inherit
             (cons '("none" . nil)
                   (mapcar #'(lambda (c) (cons (symbol-name c) c))
                           (face-list))))
diff --git a/lisp/filesets.el b/lisp/filesets.el
index c1e6ef10d5..8ccfa570e3 100644
--- a/lisp/filesets.el
+++ b/lisp/filesets.el
@@ -1559,7 +1559,7 @@ filesets-file-close
 (defun filesets-get-fileset-from-name (name &optional mode)
   "Get fileset definition for NAME."
   (pcase mode
-    ((or `:ingroup `:tree) name)
+    ((or :ingroup :tree) name)
     (_ (assoc name filesets-data))))
 
 
diff --git a/lisp/progmodes/modula2.el b/lisp/progmodes/modula2.el
index 582e495a2b..ef12352457 100644
--- a/lisp/progmodes/modula2.el
+++ b/lisp/progmodes/modula2.el
@@ -232,11 +232,11 @@ m2-smie-refine-semi
 ;; FIXME: "^." are two tokens, not one.
 (defun m2-smie-forward-token ()
   (pcase (smie-default-forward-token)
-    (`"VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
-    (`"CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
-    (`";" (save-excursion (m2-smie-refine-semi)))
-    (`"OF" (save-excursion (forward-char -2) (m2-smie-refine-of)))
-    (`":" (save-excursion (forward-char -1) (m2-smie-refine-colon)))
+    ("VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
+    ("CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
+    (";" (save-excursion (m2-smie-refine-semi)))
+    ("OF" (save-excursion (forward-char -2) (m2-smie-refine-of)))
+    (":" (save-excursion (forward-char -1) (m2-smie-refine-colon)))
     ;; (`"END" (if (and (looking-at "[ \t\n]*\\(\\(?:\\sw\\|\\s_\\)+\\)")
     ;;                  (not (assoc (match-string 1) m2-smie-grammar)))
     ;;             "END-proc" "END"))
@@ -244,11 +244,11 @@ m2-smie-forward-token
 
 (defun m2-smie-backward-token ()
   (pcase (smie-default-backward-token)
-    (`"VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
-    (`"CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
-    (`";" (save-excursion (forward-char 1) (m2-smie-refine-semi)))
-    (`"OF" (save-excursion (m2-smie-refine-of)))
-    (`":" (save-excursion (m2-smie-refine-colon)))
+    ("VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
+    ("CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
+    (";" (save-excursion (forward-char 1) (m2-smie-refine-semi)))
+    ("OF" (save-excursion (m2-smie-refine-of)))
+    (":" (save-excursion (m2-smie-refine-colon)))
     ;; (`"END" (if (and (looking-at "\\sw+[ \t\n]+\\(\\(?:\\sw\\|\\s_\\)+\\)")
     ;;                  (not (assoc (match-string 1) m2-smie-grammar)))
     ;;             "END-proc" "END"))
@@ -272,7 +272,7 @@ m2-smie-rules
   (pcase (cons kind token)
     (`(:elem . basic) m2-indent)
     (`(:after . ":=") (or m2-indent smie-indent-basic))
-    (`(:after . ,(or `"CONST" `"VAR" `"TYPE"))
+    (`(:after . ,(or "CONST" "VAR" "TYPE"))
      (or m2-indent smie-indent-basic))
     ;; (`(:before . ,(or `"VAR" `"TYPE" `"CONST"))
     ;;  (if (smie-rule-parent-p "PROCEDURE") 0))
diff --git a/lisp/progmodes/octave.el b/lisp/progmodes/octave.el
index 13510eef80..cce5e17e79 100644
--- a/lisp/progmodes/octave.el
+++ b/lisp/progmodes/octave.el
@@ -1065,8 +1065,8 @@ octave-goto-function-definition
              (unless found (goto-char orig))
              found))))
     (pcase (and buffer-file-name (file-name-extension buffer-file-name))
-      (`"cc" (funcall search
-                      "\\_<DEFUN\\(?:_DLD\\)?\\s-*(\\s-*\\(\\(?:\\sw\\|\\s_\\)+\\)" 1))
+      ("cc" (funcall search
+                     "\\_<DEFUN\\(?:_DLD\\)?\\s-*(\\s-*\\(\\(?:\\sw\\|\\s_\\)+\\)" 1))
       (_ (funcall search octave-function-header-regexp 3)))))
 
 (defun octave-function-file-p ()
@@ -1135,19 +1135,19 @@ octave-sync-function-file-names
                       (read-char-choice
                        "Which name to use? (a/b/q) " '(?a ?b ?q))))))
           (pcase c
-            (`?a (let ((newname (expand-file-name
-                                 (concat func (file-name-extension
-                                               buffer-file-name t)))))
-                   (when (or (not (file-exists-p newname))
-                             (yes-or-no-p
-                              (format "Target file %s exists; proceed? " newname)))
-                     (when (file-exists-p buffer-file-name)
-                       (rename-file buffer-file-name newname t))
-                     (set-visited-file-name newname))))
-            (`?b (save-excursion
-                   (goto-char name-start)
-                   (delete-region name-start name-end)
-                   (insert file)))))))))
+            (?a (let ((newname (expand-file-name
+                                (concat func (file-name-extension
+                                              buffer-file-name t)))))
+                  (when (or (not (file-exists-p newname))
+                            (yes-or-no-p
+                             (format "Target file %s exists; proceed? " newname)))
+                    (when (file-exists-p buffer-file-name)
+                      (rename-file buffer-file-name newname t))
+                    (set-visited-file-name newname))))
+            (?b (save-excursion
+                  (goto-char name-start)
+                  (delete-region name-start name-end)
+                  (insert file)))))))))
 
 (defun octave-update-function-file-comment (beg end)
   "Query replace function names in function file comment."
@@ -1801,19 +1801,19 @@ octave-find-definition-filename-function
 (defun octave-find-definition-default-filename (name)
   "Default value for `octave-find-definition-filename-function'."
   (pcase (file-name-extension name)
-    (`"oct"
+    ("oct"
      (octave-find-definition-default-filename
       (concat "libinterp/dldfcn/"
               (file-name-sans-extension (file-name-nondirectory name))
               ".cc")))
-    (`"cc"
+    ("cc"
      (let ((file (or (locate-file name (octave-source-directories))
                      (locate-file (file-name-nondirectory name)
                                   (octave-source-directories)))))
        (or (and file (file-exists-p file))
            (error "File `%s' not found" name))
        file))
-    (`"mex"
+    ("mex"
      (if (yes-or-no-p (format-message "File `%s' may be binary; open? "
 				      (file-name-nondirectory name)))
          name
diff --git a/lisp/progmodes/opascal.el b/lisp/progmodes/opascal.el
index 4606621951..7d055b735d 100644
--- a/lisp/progmodes/opascal.el
+++ b/lisp/progmodes/opascal.el
@@ -393,17 +393,17 @@ opascal-literal-kind
         (if (null (nth 8 ppss))
             (when (looking-at opascal--literal-start-re)
               (pcase (char-after)
-                (`?/  'comment-single-line)
-                (`?\{ 'comment-multi-line-1)
-                (`?\( 'comment-multi-line-2)
-                (`?\' 'string)
-                (`?\" 'double-quoted-string)))
+                (?/  'comment-single-line)
+                (?\{ 'comment-multi-line-1)
+                (?\( 'comment-multi-line-2)
+                (?\' 'string)
+                (?\" 'double-quoted-string)))
           (if (nth 3 ppss)   ;String.
               (if (eq (nth 3 ppss) ?\")
                   'double-quoted-string 'string)
             (pcase (nth 7 ppss)
-              (`2 'comment-single-line)
-              (`1 'comment-multi-line-2)
+              (2 'comment-single-line)
+              (1 'comment-multi-line-2)
               (_  'comment-multi-line-1))))))))
 
 (defun opascal-literal-start-pattern (literal-kind)
diff --git a/lisp/progmodes/perl-mode.el b/lisp/progmodes/perl-mode.el
index b96aad7a6e..a61d1adcb7 100644
--- a/lisp/progmodes/perl-mode.el
+++ b/lisp/progmodes/perl-mode.el
@@ -323,8 +323,8 @@ perl-syntax-propertize-function
               (cons (car (string-to-syntax "< c"))
                     ;; Remember the names of heredocs found on this line.
                     (cons (cons (pcase (aref name 0)
-                                  (`?\\ (substring name 1))
-                                  ((or `?\" `?\' `?\`) (substring name 1 -1))
+                                  (?\\ (substring name 1))
+                                  ((or ?\" ?\' ?\`) (substring name 1 -1))
                                   (_ name))
                                 indented)
                           (cdr st)))))))
diff --git a/lisp/progmodes/prolog.el b/lisp/progmodes/prolog.el
index 3bcc9bebcd..b530c61f97 100644
--- a/lisp/progmodes/prolog.el
+++ b/lisp/progmodes/prolog.el
@@ -954,9 +954,9 @@ prolog-smie-rules
     ;;    ->  thenrule
     ;;    ;   elserule
     ;;    )
-    (`(:before . ,(or `"->" `";"))
+    (`(:before . ,(or "->" ";"))
      (and (smie-rule-bolp) (smie-rule-parent-p "(") (smie-rule-parent 0)))
-    (`(:after . ,(or `"->" `"*->"))
+    (`(:after . ,(or "->" "*->"))
      ;; We distinguish
      ;;
      ;;     (a ->
@@ -3247,11 +3247,11 @@ prolog-electric--underscore
 
 (defun prolog-post-self-insert ()
   (pcase last-command-event
-    (`?_ (prolog-electric--underscore))
-    (`?- (prolog-electric--dash))
-    (`?: (prolog-electric--colon))
-    ((or `?\( `?\; `?>) (prolog-electric--if-then-else))
-    (`?. (prolog-electric--dot))))
+    (?_ (prolog-electric--underscore))
+    (?- (prolog-electric--dash))
+    (?: (prolog-electric--colon))
+    ((or ?\( ?\; ?>) (prolog-electric--if-then-else))
+    (?. (prolog-electric--dot))))
 
 (defun prolog-find-term (functor arity &optional prefix)
   "Go to the position at the start of the next occurrence of a term.
diff --git a/lisp/progmodes/ruby-mode.el b/lisp/progmodes/ruby-mode.el
index fad7bc1fb8..32130cee8e 100644
--- a/lisp/progmodes/ruby-mode.el
+++ b/lisp/progmodes/ruby-mode.el
@@ -612,7 +612,7 @@ ruby-smie-rules
       ;; For (invalid) code between switch and case.
       ;; (if (smie-parent-p "switch") 4)
       ))
-    (`(:before . ,(or `"(" `"[" `"{"))
+    (`(:before . ,(or "(" "[" "{"))
      (cond
       ((and (equal token "{")
             (not (smie-rule-prev-p "(" "{" "[" "," "=>" "=" "return" ";"))
@@ -639,7 +639,7 @@ ruby-smie-rules
            (forward-char -1))
          (smie-indent-virtual))
         (t (smie-rule-parent))))))
-    (`(:after . ,(or `"(" "[" "{"))
+    (`(:after . ,(or "(" "[" "{"))
      ;; FIXME: Shouldn't this be the default behavior of
      ;; `smie-indent-after-keyword'?
      (save-excursion
@@ -660,7 +660,7 @@ ruby-smie-rules
        (smie-backward-sexp ".")
        (cons 'column (+ (current-column)
                         ruby-indent-level))))
-    (`(:before . ,(or `"else" `"then" `"elsif" `"rescue" `"ensure"))
+    (`(:before . ,(or "else" "then" "elsif" "rescue" "ensure"))
      (smie-rule-parent))
     (`(:before . "when")
      ;; Align to the previous `when', but look up the virtual
@@ -1544,8 +1544,8 @@ ruby-backward-sexp
             (cond ((looking-at "\\s)")
                    (goto-char (scan-sexps (1+ (point)) -1))
                    (pcase (char-before)
-                     (`?% (forward-char -1))
-                     ((or `?q `?Q `?w `?W `?r `?x)
+                     (?% (forward-char -1))
+                     ((or ?q ?Q ?w ?W ?r ?x)
                       (if (eq (char-before (1- (point))) ?%)
                           (forward-char -2))))
                    nil)
@@ -1562,13 +1562,13 @@ ruby-backward-sexp
                    (forward-char 1)
                    (while (progn (forward-word-strictly -1)
                                  (pcase (char-before)
-                                   (`?_ t)
-                                   (`?. (forward-char -1) t)
-                                   ((or `?$ `?@)
+                                   (?_ t)
+                                   (?. (forward-char -1) t)
+                                   ((or ?$ ?@)
                                     (forward-char -1)
                                     (and (eq (char-before) (char-after))
                                          (forward-char -1)))
-                                   (`?:
+                                   (?:
                                     (forward-char -1)
                                     (eq (char-before) :)))))
                    (if (looking-at ruby-block-end-re)
diff --git a/lisp/progmodes/sh-script.el b/lisp/progmodes/sh-script.el
index aaa86b5816..46c9e6ee65 100644
--- a/lisp/progmodes/sh-script.el
+++ b/lisp/progmodes/sh-script.el
@@ -959,8 +959,8 @@ sh--inside-noncommand-expression
            ;; ((...)) or $((...)) or $[...] or ${...}. Nested
            ;; parenthesis can occur inside the first of these forms, so
            ;; parse backward recursively.
-           (`?\( (eq ?\( (char-before)))
-           ((or `?\{ `?\[) (eq ?\$ (char-before))))
+           (?\( (eq ?\( (char-before)))
+           ((or ?\{ ?\[) (eq ?\$ (char-before))))
          (sh--inside-noncommand-expression (1- (point))))))))
 
 (defun sh-font-lock-open-heredoc (start string eol)
@@ -2038,7 +2038,7 @@ sh-smie-sh-rules
     (`(:elem . basic) sh-basic-offset)
     (`(:after . "case-)") (- (sh-var-value 'sh-indent-for-case-alt)
                              (sh-var-value 'sh-indent-for-case-label)))
-    (`(:before . ,(or `"(" `"{" `"[" "while" "if" "for" "case"))
+    (`(:before . ,(or "(" "{" "[" "while" "if" "for" "case"))
      (if (not (smie-rule-prev-p "&&" "||" "|"))
          (when (smie-rule-hanging-p)
            (smie-rule-parent))
@@ -2047,11 +2047,11 @@ sh-smie-sh-rules
 	 `(column . ,(smie-indent-virtual)))))
     ;; FIXME: Maybe this handling of ;; should be made into
     ;; a smie-rule-terminator function that takes the substitute ";" as arg.
-    (`(:before . ,(or `";;" `";&" `";;&"))
+    (`(:before . ,(or ";;" ";&" ";;&"))
      (if (and (smie-rule-bolp) (looking-at ";;?&?[ \t]*\\(#\\|$\\)"))
          (cons 'column (smie-indent-keyword ";"))
        (smie-rule-separator kind)))
-    (`(:after . ,(or `";;" `";&" `";;&"))
+    (`(:after . ,(or ";;" ";&" ";;&"))
      (with-demoted-errors
        (smie-backward-sexp token)
        (cons 'column
@@ -2062,7 +2062,7 @@ sh-smie-sh-rules
                             (smie-rule-bolp))))
                  (current-column)
                (smie-indent-calculate)))))
-    (`(:before . ,(or `"|" `"&&" `"||"))
+    (`(:before . ,(or "|" "&&" "||"))
      (unless (smie-rule-parent-p token)
        (smie-backward-sexp token)
        `(column . ,(+ (funcall smie-rules-function :elem 'basic)
@@ -2081,7 +2081,7 @@ sh-smie-sh-rules
     ;; sh-indent-after-done: aligned completely differently.
     (`(:after . "in") (sh-var-value 'sh-indent-for-case-label))
     ;; sh-indent-for-continuation: Line continuations are handled differently.
-    (`(:after . ,(or `"(" `"{" `"["))
+    (`(:after . ,(or "(" "{" "["))
      (if (not (looking-at ".[ \t]*[^\n \t#]"))
          (sh-var-value 'sh-indent-after-open)
        (goto-char (1- (match-end 0)))
@@ -2253,7 +2253,7 @@ sh-smie-rc-rules
      (save-excursion
        (when (sh-smie--rc-after-special-arg-p)
          `(column . ,(current-column)))))
-    (`(:before . ,(or `"(" `"{" `"["))
+    (`(:before . ,(or "(" "{" "["))
      (if (smie-rule-hanging-p) (smie-rule-parent)))
     ;; FIXME: SMIE parses "if (exp) cmd" as "(if ((exp) cmd))" so "cmd" is
     ;; treated as an arg to (exp) by default, which indents it all wrong.
@@ -2262,7 +2262,7 @@ sh-smie-rc-rules
     ;; rule we have is the :list-intro hack, which we use here to align "cmd"
     ;; with "(exp)", which is rarely the right thing to do, but is better
     ;; than nothing.
-    (`(:list-intro . ,(or `"for" `"if" `"while")) t)
+    (`(:list-intro . ,(or "for" "if" "while")) t)
     ;; sh-indent-after-switch: handled implicitly by the default { rule.
     ))
 
diff --git a/lisp/server.el b/lisp/server.el
index 50684a20aa..d0a8ca313e 100644
--- a/lisp/server.el
+++ b/lisp/server.el
@@ -1112,16 +1112,16 @@ server-execute-continuation
 	    (while args-left
               (pcase (pop args-left)
                 ;; -version CLIENT-VERSION: obsolete at birth.
-                (`"-version" (pop args-left))
+                ("-version" (pop args-left))
 
                 ;; -nowait:  Emacsclient won't wait for a result.
-                (`"-nowait" (setq nowait t))
+                ("-nowait" (setq nowait t))
 
                 ;; -current-frame:  Don't create frames.
-                (`"-current-frame" (setq use-current-frame t))
+                ("-current-frame" (setq use-current-frame t))
 
                 ;; -frame-parameters: Set frame parameters
-                (`"-frame-parameters"
+                ("-frame-parameters"
                  (let ((alist (pop args-left)))
                    (if coding-system
                        (setq alist (decode-coding-string alist coding-system)))
@@ -1129,24 +1129,24 @@ server-execute-continuation
 
                 ;; -display DISPLAY:
                 ;; Open X frames on the given display instead of the default.
-                (`"-display"
+                ("-display"
                  (setq display (pop args-left))
                  (if (zerop (length display)) (setq display nil)))
 
                 ;; -parent-id ID:
                 ;; Open X frame within window ID, via XEmbed.
-                (`"-parent-id"
+                ("-parent-id"
                  (setq parent-id (pop args-left))
                  (if (zerop (length parent-id)) (setq parent-id nil)))
 
                 ;; -window-system:  Open a new X frame.
-                (`"-window-system"
+                ("-window-system"
 		 (if (fboundp 'x-create-frame)
 		     (setq dontkill t
 			   tty-name 'window-system)))
 
                 ;; -resume:  Resume a suspended tty frame.
-                (`"-resume"
+                ("-resume"
                  (let ((terminal (process-get proc 'terminal)))
                    (setq dontkill t)
                    (push (lambda ()
@@ -1157,7 +1157,7 @@ server-execute-continuation
                 ;; -suspend:  Suspend the client's frame.  (In case we
                 ;; get out of sync, and a C-z sends a SIGTSTP to
                 ;; emacsclient.)
-                (`"-suspend"
+                ("-suspend"
                  (let ((terminal (process-get proc 'terminal)))
                    (setq dontkill t)
                    (push (lambda ()
@@ -1167,13 +1167,13 @@ server-execute-continuation
 
                 ;; -ignore COMMENT:  Noop; useful for debugging emacsclient.
                 ;; (The given comment appears in the server log.)
-                (`"-ignore"
+                ("-ignore"
                  (setq dontkill t)
                  (pop args-left))
 
 		;; -tty DEVICE-NAME TYPE:  Open a new tty frame.
 		;; (But if we see -window-system later, use that.)
-                (`"-tty"
+                ("-tty"
                  (setq tty-name (pop args-left)
                        tty-type (pop args-left)
                        dontkill (or dontkill
@@ -1192,7 +1192,7 @@ server-execute-continuation
 
                 ;; -position LINE[:COLUMN]:  Set point to the given
                 ;;  position in the next file.
-                (`"-position"
+                ("-position"
                  (if (not (string-match "\\+\\([0-9]+\\)\\(?::\\([0-9]+\\)\\)?"
                                         (car args-left)))
                      (error "Invalid -position command in client args"))
@@ -1203,7 +1203,7 @@ server-execute-continuation
                                                      ""))))))
 
                 ;; -file FILENAME:  Load the given file.
-                (`"-file"
+                ("-file"
                  (let ((file (pop args-left)))
                    (if coding-system
                        (setq file (decode-coding-string file coding-system)))
@@ -1221,7 +1221,7 @@ server-execute-continuation
                  (setq filepos nil))
 
                 ;; -eval EXPR:  Evaluate a Lisp expression.
-                (`"-eval"
+                ("-eval"
                  (if use-current-frame
                      (setq use-current-frame 'always))
                  (let ((expr (pop args-left)))
@@ -1232,14 +1232,14 @@ server-execute-continuation
                    (setq filepos nil)))
 
                 ;; -env NAME=VALUE:  An environment variable.
-                (`"-env"
+                ("-env"
                  (let ((var (pop args-left)))
                    ;; XXX Variables should be encoded as in getenv/setenv.
                    (process-put proc 'env
                                 (cons var (process-get proc 'env)))))
 
                 ;; -dir DIRNAME:  The cwd of the emacsclient process.
-                (`"-dir"
+                ("-dir"
                  (setq dir (pop args-left))
                  (if coding-system
                      (setq dir (decode-coding-string dir coding-system)))
diff --git a/lisp/subr.el b/lisp/subr.el
index 41dc9aa45f..aaf8909e0c 100644
--- a/lisp/subr.el
+++ b/lisp/subr.el
@@ -4815,7 +4815,7 @@ called-interactively-p
                           i frame nextframe)))
                (pcase skip
                  (`nil nil)
-                 (`0 t)
+                 (0 t)
                  (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
       ;; Now `frame' should be "the function from which we were called".
       (pcase (cons frame nextframe)
diff --git a/lisp/textmodes/css-mode.el b/lisp/textmodes/css-mode.el
index 31ce638b31..63c86317ee 100644
--- a/lisp/textmodes/css-mode.el
+++ b/lisp/textmodes/css-mode.el
@@ -1219,7 +1219,7 @@ css-smie-rules
     (`(:elem . basic) css-indent-offset)
     (`(:elem . arg) 0)
     ;; "" stands for BOB (bug#15467).
-    (`(:list-intro . ,(or `";" `"" `":-property")) t)
+    (`(:list-intro . ,(or ";" "" ":-property")) t)
     (`(:before . "{")
      (when (or (smie-rule-hanging-p) (smie-rule-bolp))
        (smie-backward-sexp ";")
diff --git a/test/lisp/emacs-lisp/pcase-tests.el b/test/lisp/emacs-lisp/pcase-tests.el
index 774a488255..c706c1051e 100644
--- a/test/lisp/emacs-lisp/pcase-tests.el
+++ b/test/lisp/emacs-lisp/pcase-tests.el
@@ -53,7 +53,7 @@ pcase-tests-grep
   (should (pcase-tests-grep
            'memq (macroexpand-all '(pcase x ((or 1 2 3) body)))))
   (should (pcase-tests-grep
-           'member (macroexpand-all '(pcase x ((or '"a" '2 '3) body)))))
+           'member (macroexpand-all '(pcase x ((or "a" 2 3) body)))))
   (should-not (pcase-tests-grep
                'memq (macroexpand-all '(pcase x ((or "a" 2 3) body)))))
   (let ((exp (macroexpand-all
-- 
2.19.1


[-- Attachment #3: Type: text/plain, Size: 23 bytes --]





Thanks,

Michael.


^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-27 15:19                                                                               ` Michael Heerdegen
@ 2018-10-27 16:56                                                                                 ` Garreau, Alexandre
  2018-10-27 22:37                                                                                 ` Dmitry Gutov
  2018-10-29  3:26                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  2 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-27 16:56 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, Stefan Monnier, emacs-devel

On 2018-10-27 at 17:19, Michael Heerdegen wrote:
> What's then left is the task to replace all pcase forms that can be
> trivially rewritten by using case or cond/assoc.  I must admit that
> I'm very skeptical about this now.  Not only that we would only
> replace exactly these pcase occurrences that are really trivial to
> read for anybody, which could be, at the end, counterproductive for
> those people who dislike pcase because the pcase forms left are the
> harder ones (Eli, I know you don't think like that).
>
> I also saw that people have very different likings, independent from
> pcase.  Say, we have one third of people who want to keep pcase in
> these cases, one third who want to replace it with cl-case, and one
> third who want cond or assoc instead.  We have a clear majority
> against pcase.  But we also have a clear majority against cl-case, and
> a majority against cond/assoc.

First of all, on a practical ground, I’m not sure anything has been that
democratic yet, or anybody has found a that-much democratic process to
be useful (at least it is complex to, well, process)…

But, as the question is raised, that recalls me a lot Arrow’s paradox:
normally this is the moment I notice you that each one of these thirds
may have a preference too about the two forms they dislike (or only like
less; for instance I might be a fan of case but prefer cond and assoc to
pcase (or the other way around)), so we might ask a list of preferences
rather than a single preference, and Arrow’s paradox says this issue
keep going as in the end the comparisons may be A > B > C > A.

Fyi, one solution of this paradox, is to allow multiple equalities (such
as giving preferences in the form A = B > C = D), and do a median rather
than a average/direct-superiority-count-compare, or, in a more
intuitive, developed and straightforward way: “in a ringle round, give a
notation mark to each preference, then for each preference, take their
median score, take the winner(s), and if several, the one who won by
this score by more voices” (very unlikely to get equalities).

More pretty interesting documentation on arrow paradox:
<https://en.wikipedia.org/wiki/Arrow%27s_paradox>



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25 14:47                                                                               ` Eli Zaretskii
  2018-10-25 15:32                                                                                 ` Stefan Monnier
@ 2018-10-27 17:48                                                                                 ` Garreau, Alexandre
  1 sibling, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-27 17:48 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

On 2018-10-25 at 17:47, Eli Zaretskii wrote:
>> From: Stefan Monnier <monnier@iro.umontreal.ca>
>> Date: Wed, 24 Oct 2018 16:52:23 -0400
>
>> To me, it's more verbose and more complex because you need to double
>> check that the same var is tested each time before you can know that it's
>> equivalent to a C-style `switch`.
>
> But it isn't equivalent to C-style 'switch': it doesn't compare like C
> does, and it doesn't dispatch like C does.

Is this about the fact you need “break” in C to get the same behavior?
Then a lot of programmers “as a good style” put it at the end of each
case, because they don’t even know they can do otherwise, and what does
that actually mean.

> (I find it generally not useful to think in C concepts when
> programming in Lisp, because it might cause confusion and mistakes.)

Maybe it’s more a matter of programming habits than of C concepts.  And
factorizing conditionals seems to be a pretty common thing.

> By contrast, with cond everything is explicit and self-explanatory.
> The programmer decides which equality to use.  Yes, that does come for
> a price, but copy-yanking is cheap and fast, as is "M-/", and also
> avoids typos.

People also have a habit of defining macros to factorize code so that to
match their thinking and expression of what they want to achieve: that’s
why I and many others end writing new personal conditional such as
case*.  But these not being standard, they’re way less explicit and
self-explanatory, as each re-definition will potentially loose unaware
people, be incompatible with others, and will be more of a burden for
readers of programs using them.  While encouraging mainline and standard
forms for common subexpressions elimination make people use them instead
of making up their own, and therefore make their software easier to
read.

>> We clearly have very different programming backgrounds: to me the "case
>> style" is much nicer and easier to read, closer to what I think in
>> my head, whereas the "cond+eq style" is like a "assembly-language"
>> version of the same.
>
> This isn't about style, this is about using macro facilities to
> significantly change the syntax of a language.
>
> E.g., what do you think about people who use cpp to define macros
> BEGIN and END that expand into braces?  One could argue that it is
> "closer to what one thinks in their head", or being "higher-level",
> and yet such practices are generally discouraged.

Because each one of these have real advantages as well as disadvantages,
and, more importantly, neither of them is more clearly expressible as a
composition of the other, compared to the other way around (eg. you can
translate BEGIN END to { } or the other way around, none of both is more
simple, natural or straightforward than the other).

While this is clearly the case for pcase, cl-case, and finally cond, as
each one of them can be more easily defined on top of, respectively,
case, cond, and if.  So the former are higher-level while the later are
lower-level.  Level is more a question of abstraction rather than
(subjective) thinking.

>> I prefer pcase to cl-case but I even much more strongly prefer cl-case
>> over cond+eq.
>
> The thing is, both cl-case and pcase are subtly different from the
> "boring" cond, and from each other.  E.g., cl-case uses eql to
> compare, so works with floats, but not with strings;

>> > (Quick: what's the difference between `require and 'require in this
>> > case?)
>> 
>> Same difference as between 'require and `require in normal Elisp code.
>> Why is that a problem in pcase and not in the rest of Elisp?
>
> Because people stumble on this and are likely to waste time trying to
> understand what kind of magic hides behind this.  Worse, they might
> copy this without understanding (as we already see in our sources),
> thus proliferating the obfuscation.
>
> Mind you: I'm not against pcase where its power is needed.  It is IMO
> needed where using the underlying core facilities would produce
> something that is hard to follow and even harder to understand.
> Simple comparisons against a collection of fixed values doesn't fit
> that bill, IMO.

cl-case does, imho.  I’d appreciate, as well as others, I think, an
official version with equal (case-equal, or casequal maybe?), or even a
more general version (with as second argument the test function to use):
either named case* (I recall having seen somewhere the convention of
appending a “*” for the general version (that asked for a test function)
of a comparision form, do anyone know where it might come from? as I’m
now unable to find it again), or maybe using a :test and :test-not
keywords.

Maybe even a version not quoting its keylists?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-27 15:19                                                                               ` Michael Heerdegen
  2018-10-27 16:56                                                                                 ` Garreau, Alexandre
@ 2018-10-27 22:37                                                                                 ` Dmitry Gutov
  2018-10-28  0:21                                                                                   ` Michael Heerdegen
  2018-10-29  3:26                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  2 siblings, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-27 22:37 UTC (permalink / raw)
  To: Michael Heerdegen, Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

On 27.10.2018 18:19, Michael Heerdegen wrote:
> Say, we have one third of people who want to keep pcase in these
> cases, one third who want to replace it with cl-case, and one third who
> want cond or assoc instead.  We have a clear majority against pcase.
> But we also have a clear majority against cl-case, and a majority
> against cond/assoc.

We could also assume that the silent majority is okay with the way 
things are. For example, I like pcase, even if more complex cases might 
look cryptic.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-27 22:37                                                                                 ` Dmitry Gutov
@ 2018-10-28  0:21                                                                                   ` Michael Heerdegen
  2018-10-28  2:07                                                                                     ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-28  0:21 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: Eli Zaretskii, Stefan Monnier, emacs-devel

Dmitry Gutov <dgutov@yandex.ru> writes:

> We could also assume that the silent majority is okay with the way
> things are. For example, I like pcase, even if more complex cases
> might look cryptic.

I also like it, and your assumption could be true.  Who knows.

Pcase was a big improvement to what can be expressed with Elisp.  And I
think its syntax and semantics are quite straightforward.  I doubt we
will find something more simplistic that has the same power.

Probably the main problem was that the documentation was originally
written in a quite terse academic style.  Also, the recursive nature of
` that makes it possible to combine it with all other patter types is
hard to get, but also very natural and powerful.  It's just consistent
that when backquote is used to construct complicated lists, it is also
used to build complex patterns to match such lists.  Nonetheless it
seems that ` is one of the main reasons for the bad feelings some people
have about pcase.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-28  0:21                                                                                   ` Michael Heerdegen
@ 2018-10-28  2:07                                                                                     ` Garreau, Alexandre
  2018-10-28  2:44                                                                                       ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-28  2:07 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, emacs-devel, Stefan Monnier, Dmitry Gutov

On 2018-10-28 at 02:21, Michael Heerdegen wrote:
> Dmitry Gutov <dgutov@yandex.ru> writes:
>
>> We could also assume that the silent majority is okay with the way
>> things are. For example, I like pcase, even if more complex cases
>> might look cryptic.
>
> I also like it, and your assumption could be true.  Who knows.
>
> Pcase was a big improvement to what can be expressed with Elisp.  And I
> think its syntax and semantics are quite straightforward.  I doubt we
> will find something more simplistic that has the same power.
>
> Probably the main problem was that the documentation was originally
> written in a quite terse academic style.  Also, the recursive nature of
> ` that makes it possible to combine it with all other patter types is
> hard to get, but also very natural and powerful.  It's just consistent
> that when backquote is used to construct complicated lists, it is also
> used to build complex patterns to match such lists.  Nonetheless it
> seems that ` is one of the main reasons for the bad feelings some people
> have about pcase.

Isn’t ` needed in just the same cases you could as well use guard or
predefined patterns?  when you need to eval things?  If there is some
redundance or covering between both, maybe ` could be avoided so it
confuses less?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-28  2:07                                                                                     ` Garreau, Alexandre
@ 2018-10-28  2:44                                                                                       ` Garreau, Alexandre
  2018-10-28  4:45                                                                                         ` How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]] Garreau, Alexandre
  2018-10-28 22:54                                                                                         ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-28  2:44 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

On 2018-10-28 at 03:07, Garreau, Alexandre wrote:
> On 2018-10-28 at 02:21, Michael Heerdegen wrote:
>> Dmitry Gutov <dgutov@yandex.ru> writes:
>>
>>> We could also assume that the silent majority is okay with the way
>>> things are. For example, I like pcase, even if more complex cases
>>> might look cryptic.
>>
>> I also like it, and your assumption could be true.  Who knows.
>>
>> Pcase was a big improvement to what can be expressed with Elisp.  And I
>> think its syntax and semantics are quite straightforward.  I doubt we
>> will find something more simplistic that has the same power.
>>
>> Probably the main problem was that the documentation was originally
>> written in a quite terse academic style.  Also, the recursive nature of
>> ` that makes it possible to combine it with all other patter types is
>> hard to get, but also very natural and powerful.  It's just consistent
>> that when backquote is used to construct complicated lists, it is also
>> used to build complex patterns to match such lists.  Nonetheless it
>> seems that ` is one of the main reasons for the bad feelings some people
>> have about pcase.
>
> Isn’t ` needed in just the same cases you could as well use guard or
> predefined patterns?  when you need to eval things?  If there is some
> redundance or covering between both, maybe ` could be avoided so it
> confuses less?

Nevermind, I just discovered that normally rar ` is mandatory for the
main use case of pcase, pattern matching, which I find weird.  So its
normal syntax is what case should be, and its ` syntax is what pcase
should be.

Initially I expected this would have worked the same:

#+BEGIN_SRC emacs-lisp
  (defun evaluate (exp env)
    (pcase exp
      (('add x y)       (+ (evaluate x env) (evaluate y env)))
      (('call fun arg)  (funcall (evaluate fun env) (evaluate arg env)))
      (('fn arg body)   (lambda (val)
                            (evaluate body (cons (cons arg val) env))))
      ((pred numberp)     exp)
      ((pred symbolp)     (cdr (assq exp env)))
      (_                  (error "Unknown expression %S" exp))))
#+END_SRC

because intuitively, I thought what would apply to a raw top-level atom,
would apply to it as a component of a sequence, but it seem I’m wrong.

Which indeed is unreasonable, as it is incompatible with pcase
non-pattern-matching own mini-language, which strangely seems to be more
important to pcase than pattern matching.

So know I understand why advocating for replacing case with pcase: pcase
is not about pattern matching, it is just a correctly working case,
except it only works for atoms, with an optional prevailing
mini-language, and even more optional, additive and not straightforward
pattern matching.

Maybe that would make more sense if ` (and '?) were not part of pcase’s
own mini-language, redefined by pcase, but if pcase actually truly
eval’d its pattern, defining pred, guard, etc. as real functions,
defined with a cl-letf, using lexical scoping so to prevailably define
all these + user-defined patterns.

But even then, “,” I feel like would barely make sense… it’s used the
same way, but doesn’t mean the same thing.  It doesn’t mean “eval”, as
the thing after “,”, if not a function call, might be something not
bound to a value, so it only means “undo the ‘`’, do like I didn’t do
it”, which is inconsistent with general use of “`”.

When seeing “,var”, I’m thinking “the actual value of var, or an error”,
so as I don’t see var defined anywere, I feel like an error is coming,
and as I know none is coming, I feel something is wrong.  I don’t see
how to eval ,var without getting an error, except by redefining how to
eval, or rather how to get a symbol value.

It even more feel wrong that, this, doesn’t work, for no reason (it
can’t be incompatible with the minilanguage):

#+BEGIN_SRC emacs-lisp
  (pcase [1 2]
    ([a b] (+ a b)))
#+END_SRC

Yet that’s the most intuitive and straightforward way of using pattern
matching.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]]
  2018-10-28  2:44                                                                                       ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
@ 2018-10-28  4:45                                                                                         ` Garreau, Alexandre
  2018-10-28 13:44                                                                                           ` Stefan Monnier
  2018-10-28 23:16                                                                                           ` Michael Heerdegen
  2018-10-28 22:54                                                                                         ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Michael Heerdegen
  1 sibling, 2 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-28  4:45 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, emacs-devel, Stefan Monnier, Dmitry Gutov

On 2018-10-28 at 03:44, Garreau, Alexandre wrote:
> Initially I expected this would have worked […]
>
> #+BEGIN_SRC emacs-lisp
>   (defun evaluate (exp env)
>     (pcase exp
>       (('add x y)       (+ (evaluate x env) (evaluate y env)))
>       (('call fun arg)  (funcall (evaluate fun env) (evaluate arg env)))
>       (('fn arg body)   (lambda (val)
>                             (evaluate body (cons (cons arg val) env))))
>       ((pred numberp)     exp)
>       ((pred symbolp)     (cdr (assq exp env)))
>       (_                  (error "Unknown expression %S" exp))))
> #+END_SRC
>
> […]
>
> It even more feel wrong that, this, doesn’t work, for no reason (it
> can’t be incompatible with the minilanguage):
>
> #+BEGIN_SRC emacs-lisp
>   (pcase [1 2]
>     ([a b] (+ a b)))
> #+END_SRC
>
> Yet that’s the most intuitive and straightforward way of using pattern
> matching.

Okay, so I went to search what is done in other pattern matching lisp
form.  The closer, yet quite straightforward, implementation of pattern
matching I found is the one found in Guile [0], claimed to be used in most
scheme implementation, which supports as well quasiquoting, but also raw
lists and vectors, because, according its manual:
>   The names ‘quote’, ‘quasiquote’, ‘unquote’, ‘unquote-splicing’, ‘?’,
> ‘_’, ‘$’, ‘and’, ‘or’, ‘not’, ‘set!’, ‘get!’, ‘...’, and ‘___’ cannot
> be used as pattern variables.

As you can see, it also supports `not', and some facilities for OOP.

I also found a cl library named cl-match [1], which also use its
minilanguage by default (but doesn’t support backquotes), so its
solution stays compatible: it uses sequences constructors such as
“cons”, “list”, “list*” (improper lists), or “array”/“vec” as patterns:

#+BEGIN_SRC lisp
  (match (list 1 2)
    ((list x y) (+ x y)))
#+END_SRC

It has several interesting forms pcase doesn’t seem to have (at least
not documented): such as “(as binding pattern)”, which matches
`pattern', and binds it to `binding' (so you can keep a binding though
binding subelement of it), or “(type type &optional pattern)” for
matching if it’s a given type, also more specific (hence semantic) and
shorter and simpler than “(and (pred typep) &optional pattern)”.

Then all other cl implementations I found (named either “match”, either
“unify”: the later is commutative, the former not) doesn’t do real
successive pattern matching, but simple destructuring (without `and',
`or', guards, or any minilanguage), yet unlike cl-destructuring-bind, in
a simpler way (without lambda-list-like arguments), and rather than
erroring out (making it unsuitable to successive tries of pattern
matching), they return either an environment, or something such as
'fail.  So it can be trivially used to make successive pattern-matching.

Going in this direction there’s first optima [2], which of course match
raw lists and such by default, but also have really interesting special
patterns, such as “(places symbol)”, that will bind to symbol, but using
symbol-macrolet, so that setf/cl-letf will work, or `(assoc 1
alist-pattern)' (so “(match '((1 . 2)) ((assoc 1 x) x))” returns 2), to
match content of an alist, or “property” for plists.

There are some others, generally a subset of what I described until
then, such as cl-unification [3].

One of these, the simpler I found, is one I found in an lisp files
archive annex [4] of a book that wasn’t freely available online /Lisp,
Third Edition/: it doesn’t appear to be free software, but it’s trivial
to understand: what it does is just match recursively plain conses
(hence lists), not even arrays or string, since it does eql on anything
else (just as case already wrongly do: what’s this fear of equal in
common lisp?), but it uses the special list (? symbol) to bind symbols.
Simply replacing “'?”  per “'var”, make it work in emacs-lisp, but as it
is not free there’s little interest in doing so.

In the end, I believe, before to even support arbitrary lists for when
the car is not a predefined pattern, it would be handy to support
constructors (hence simple new predefined patterns) such as “list” or
“vector”/“array”, that would make possible to remove all the confusing
backquotes.

However something such as (pcase-defmacro list (&rest args) ``(,@args))
(nor (pcase-defmacro list (&rest args) `(cons 'list args))) wouldn’t
work because multiple backquotes doesn’t seem to work.

[0] (info "(guile) Pattern Matching")
[1] https://common-lisp.net/project/cl-match/doc/clmatch-api.htm
[2] https://github.com/m2ym/optima
[3] https://common-lisp.net/project/cl-unification/
[4] http://people.csail.mit.edu/phw/Books/lisp.zip



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]]
  2018-10-28  4:45                                                                                         ` How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]] Garreau, Alexandre
@ 2018-10-28 13:44                                                                                           ` Stefan Monnier
  2018-10-28 17:57                                                                                             ` Garreau, Alexandre
  2018-10-28 23:16                                                                                           ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-28 13:44 UTC (permalink / raw)
  To: emacs-devel

> Okay, so I went to search what is done in other pattern matching lisp
> form.

You missed Racket's `match` (https://docs.racket-lang.org/reference/match.html)

Incidentally, I also missed it when I did the same search you did before
embarking on the design and implementation of pcase.  I later found
Racket's `match` which was pretty close to the original design of pcase,
but showed me how to add `pcase-defmacro` (mostly by adding the `app`
pattern), which led to the "new pcase" where ` is a macro (and where
' was added for that macro to have something to expand to).

The current `pcase` is pretty close to Racket's `match`.  The main
missing functionality is the negation, which Racket solves "easily"
because its underlying language handles lambda much more efficiently
(i.e. the code generated by `match` would work very poorly in Elisp
unless we significantly improved the byte-compiler's handling of
funcall).


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]]
  2018-10-28 13:44                                                                                           ` Stefan Monnier
@ 2018-10-28 17:57                                                                                             ` Garreau, Alexandre
  0 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-28 17:57 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-28 at 09:44, Stefan Monnier wrote:
>> Okay, so I went to search what is done in other pattern matching lisp
>> form.
>
> You missed Racket's `match` (https://docs.racket-lang.org/reference/match.html)

Indeed!  Thank you!  I missed it because when reading guile reference
(incidentelly already installed on my system, while I don’t even know if
racket’s is installable as info, pdf, man or even html here), I naively
thought if it said most schemes used the same, racket would too.

And indeed, it seems pretty compatible, beside being interestingly way
richer, having the `list', `vector', etc. patterns I found in cl-match…
and I’m very happy the `var' I made out of “Lisp, 3rd ed” book annex I
found happen to be just the same, compatible with racket: this easily
paliates for binding all constructs which aren’t bindable in guile’s
match (“((var list) foo)” to bind the symbol “list” as a first element).

> Incidentally, I also missed it when I did the same search you did before
> embarking on the design and implementation of pcase.  I later found
> Racket's `match` which was pretty close to the original design of pcase,
> but showed me how to add `pcase-defmacro` (mostly by adding the `app`
> pattern), which led to the "new pcase" where ` is a macro (and where
> ' was added for that macro to have something to expand to).

What was is initially? non-existing?

> The current `pcase` is pretty close to Racket's `match`.  The main
> missing functionality is the negation,

In terms of powerfulness, however, to come back to original discussion:
confusion.  The presence of type constructors (`list', `array'), the
fact lists and arrays, otherwise (if not matching a defined pattern)
work out of the box, and the `var' form, allow, if needed, to completely
avoid the “`” syntax.  And to me it’s like it appear that this syntax is
confusing quite some people (and I understand why, except when in ,(foo)
`foo' is a defined pattern, so it’s look like a function call).  So
avoiding this syntax in source code could be handy so to give a better
image to pcase, which would understood more easily.

> which Racket solves "easily" because its underlying language handles
> lambda much more efficiently (i.e. the code generated by `match` would
> work very poorly in Elisp unless we significantly improved the
> byte-compiler's handling of funcall).

From what I feel sometimes scheme’s byte-compiler are pretty handy,
maybe less than some cl compilers, but… well maybe it is only that elisp
byte-compiler doesn’t do that much, does it?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-25 23:53                                                                               ` Andy Moreton
  2018-10-26 14:59                                                                                 ` Stefan Monnier
@ 2018-10-28 21:44                                                                                 ` Stefan Monnier
  2018-10-29 13:01                                                                                   ` Alan Mackenzie
                                                                                                     ` (2 more replies)
  1 sibling, 3 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-28 21:44 UTC (permalink / raw)
  To: emacs-devel

> pcase-lambda, pcase-let, pcase-let*, and pcase-dolist still have no
> meaningful documentation,

Not sure what kind of documentation would be more meaningful, sorry.
Do you happen to have concrete questions about them which aren't answered
by their docstrings?

> Pattern matching is a useful facility, but pcase is woefully hard to use
> correctly, as the existing (mis-)usage shows.

I obviously can't judge fairly how hard it is to use, but I don't find
any of the examples posted here as evidence of problematic use and even
less misuse (they look perfectly correct to me).

Could you clarify what you find problematic in those uses?


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-28  2:44                                                                                       ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
  2018-10-28  4:45                                                                                         ` How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]] Garreau, Alexandre
@ 2018-10-28 22:54                                                                                         ` Michael Heerdegen
  2018-10-28 23:09                                                                                           ` Garreau, Alexandre
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-28 22:54 UTC (permalink / raw)
  To: Garreau, Alexandre
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:
> So know I understand why advocating for replacing case with pcase: pcase
> is not about pattern matching, it is just a correctly working case,
> except it only works for atoms, with an optional prevailing
> mini-language

If you look at the definition of the ``' pcase macro you see that it is
defined entirely in terms of the "things that only work for atoms" (it
uses `app' on car and cdr).

> Maybe that would make more sense if ` (and '?) were not part of pcase’s
> own mini-language, redefined by pcase, but if pcase actually truly
> eval’d its pattern, defining pred, guard, etc. as real functions,
> defined with a cl-letf, using lexical scoping so to prevailably define
> all these + user-defined patterns.

I think it would also be an interesting approach.  You would
additionally need some magical thing that binds variables for the scope
of the current clause, however.  That doesn't fit into that simple
approach.  But not less than into pcase itself.

I wonder if it could be similarly efficient as pcase.

> It even more feel wrong that, this, doesn’t work, for no reason

Well, there is a reason: it is wrong ;-)

> #+BEGIN_SRC emacs-lisp
>   (pcase [1 2]
>     ([a b] (+ a b)))
> #+END_SRC

That should be 

#+begin_src emacs-lisp
(pcase [1 2]
  (`[,a ,b] (+ a b)))
#+end_src

I'm sure you would have been able to find that after less than a minute
when reading the pcase docstring.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-28 22:54                                                                                         ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Michael Heerdegen
@ 2018-10-28 23:09                                                                                           ` Garreau, Alexandre
  2018-10-28 23:57                                                                                             ` Michael Heerdegen
  2018-10-29 17:26                                                                                             ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Clément Pit-Claudel
  0 siblings, 2 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-28 23:09 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

Le 28/10/2018 à 23h54, Michael Heerdegen a écrit :
> "Garreau, Alexandre" <galex-713@galex-713.eu> writes:
>> Maybe that would make more sense if ` (and '?) were not part of pcase’s
>> own mini-language, redefined by pcase, but if pcase actually truly
>> eval’d its pattern, defining pred, guard, etc. as real functions,
>> defined with a cl-letf, using lexical scoping so to prevailably define
>> all these + user-defined patterns.
>
> I think it would also be an interesting approach.  You would
> additionally need some magical thing that binds variables for the scope
> of the current clause, however.  That doesn't fit into that simple
> approach.  But not less than into pcase itself.

“(var name)”, as does racket and some common-lisp match/unify
implementations.  And so to integrate with “`”: “,(var name)” doesn’t
disturb me, it is okay: will bind “name” to something, pretty
straightforward.

> I wonder if it could be similarly efficient as pcase.

I’m almost sure it wouldn’t, or otherwise it would be awfully complex.
But, if there were something to replace ` while not being
counter-intuitive, I could live with ` not being efficient, but intuitive.

>> It even more feel wrong that, this, doesn’t work, for no reason
>
> Well, there is a reason: it is wrong ;-)
>
>> #+BEGIN_SRC emacs-lisp
>>   (pcase [1 2]
>>     ([a b] (+ a b)))
>> #+END_SRC
>
> That should be 
>
> #+begin_src emacs-lisp
> (pcase [1 2]
>   (`[,a ,b] (+ a b)))
> #+end_src
>
> I'm sure you would have been able to find that after less than a minute
> when reading the pcase docstring.

I found that before sending the mail.  But what I said I feel wrong, is
that this is wrong, after current pcase rules.  While it works for guile
and racket match, as well as several common lisp match, with only some
common-lisp match such as cl-match and optima as exceptions.

What is confusing is [] can’t serve for the pattern language, so it
feels wrong to disallow using it for pattern matching.  Beside lisp, all
pattern matching language make their feature serve one purpose: the
pattern look like what the data should be. adding “`” and “,” destroy
this feature, because the pattern no longer looks like what is matched.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]]
  2018-10-28  4:45                                                                                         ` How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]] Garreau, Alexandre
  2018-10-28 13:44                                                                                           ` Stefan Monnier
@ 2018-10-28 23:16                                                                                           ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-28 23:16 UTC (permalink / raw)
  To: Garreau, Alexandre
  Cc: Eli Zaretskii, emacs-devel, Stefan Monnier, Dmitry Gutov

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> As you can see, it also supports `not', and some facilities for OOP.

BTW, el-search supports `not'.  AFAIK it would be trivial to add `not'
to pcase, but Stefan wants to wait for an idea of how to do so
efficiently.

> or `(assoc 1 alist-pattern)' (so “(match '((1 . 2)) ((assoc 1 x) x))”
> returns 2), to match content of an alist, or “property” for plists.

Oh, there are some emacs libraries you need to load to get corresponding
pcase macros.  For example these:

-- (eieio &rest FIELDS)

Pcase patterns that match EIEIO object EXPVAL.

-- (seq &rest PATTERNS)

Build a `pcase' pattern that matches elements of SEQUENCE.

-- (rx &rest REGEXPS)

Build a `pcase' pattern matching `rx' REGEXPS in sexp form.

-- (cl-struct TYPE &rest FIELDS)

Pcase patterns that match cl-struct EXPVAL of type TYPE.

-- (radix-tree-leaf VPAT)

Build a `pcase' pattern that matches radix-tree leaf EXPVAL.
VPAT is a `pcase' pattern to extract the value.

-- (map &rest ARGS)

Build a `pcase' pattern matching map elements.


The last one supports matching alists conveniently.

> However something such as (pcase-defmacro list (&rest args) ``(,@args))

The normal backquote macro recursively handles also the backquotes and
unquotes that are meant for pcase, so you must avoid unwanted
processing.  I would write it as

#+begin_src emacs-lisp
(pcase-defmacro list (&rest args)
  `(,'\` ,(mapcar (lambda (thing) `(,'\, ,thing)) args)))
#+end_src

BTW, if you load "el-search-x.el", there is an `l' pattern defined, also
for matching lists, which also avoids ``' but has a completely different
semantics: it's more inspired by grep patterns, with the goal of
allowing to use very short input to find function definitions and such.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-28 23:09                                                                                           ` Garreau, Alexandre
@ 2018-10-28 23:57                                                                                             ` Michael Heerdegen
  2018-10-29 10:22                                                                                               ` Garreau, Alexandre
  2018-10-29 17:26                                                                                             ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Clément Pit-Claudel
  1 sibling, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-28 23:57 UTC (permalink / raw)
  To: Garreau, Alexandre
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> “(var name)”, as does racket and some common-lisp match/unify
> implementations.  And so to integrate with “`”: “,(var name)” doesn’t
> disturb me, it is okay: will bind “name” to something, pretty
> straightforward.

That would make totally sense to me.  I often found it confusing that
using a symbol which is already bound (outside of pcase) isn't turned
into an equality test.  Having an explicit `var' or `bind' for binding
variables would be nice.

> Beside lisp, all pattern matching language make their feature serve
> one purpose: the pattern look like what the data should be. adding “`”
> and “,” destroy this feature, because the pattern no longer looks like
> what is matched.

But with, for example, el-search, that suddenly looks very natural if
you can, for example, transpose the first two arguments of all `foo'
calls in your code with the rule.

   `(foo ,a ,b . ,rest) -> `(foo ,b ,a . ,rest)

The pattern exactly looks like the matched data!  Just with a different
point of view.  Using ``' is not what most people would naively use to
implement destructuring, but I don't find it unnatural or not intuitive,
no.

The above pattern would look different if we would have to write it as

  `(foo ,(var a) ,(var b) . ,(var rest))

so the implicit binding feature of symbols also makes patterns much more
readable in more complex cases, which is a big win.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-27 15:19                                                                               ` Michael Heerdegen
  2018-10-27 16:56                                                                                 ` Garreau, Alexandre
  2018-10-27 22:37                                                                                 ` Dmitry Gutov
@ 2018-10-29  3:26                                                                                 ` Eli Zaretskii
  2018-10-29 21:46                                                                                   ` Michael Heerdegen
  2 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-29  3:26 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Stefan Monnier <monnier@iro.umontreal.ca>,  emacs-devel@gnu.org
> Date: Sat, 27 Oct 2018 17:19:02 +0200
> 
> Is the commit message ok as it is?  Or should I list the changed files
> to say "All callers changed" every time?

I'd prefer this format:

  * lisp/char-fold.el:
  * lisp/dired.el:
  * lisp/emacs-lisp/derived.el:
  * lisp/emacs-lisp/easy-mmode.el: Don't quote self-quoting 'pcase'
  patterns.

IOW, a list of all changed files, with the description at the end.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-28 23:57                                                                                             ` Michael Heerdegen
@ 2018-10-29 10:22                                                                                               ` Garreau, Alexandre
  2018-10-29 21:33                                                                                                 ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-29 10:22 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

Le 29/10/2018 à 00h57, Michael Heerdegen a écrit :
> "Garreau, Alexandre" <galex-713@galex-713.eu> writes:
>
>> “(var name)”, as does racket and some common-lisp match/unify
>> implementations.  And so to integrate with “`”: “,(var name)” doesn’t
>> disturb me, it is okay: will bind “name” to something, pretty
>> straightforward.
>
> That would make totally sense to me.  I often found it confusing that
> using a symbol which is already bound (outside of pcase) isn't turned
> into an equality test.  Having an explicit `var' or `bind' for binding
> variables would be nice.

Mmmh, that’s what I thought initially, and why I regretted cl-case
didn’t eval its arguments, but in reality, neither pcase does, though it
gives this impression, since it requires quoting symbols for equality.

“var” is to make explicit bind variable bindings where it could not
being done so otherwise, so to me ,(var name) looks less confusing, and,
if lists and arrays out of the box matched lists and arrays, so that
“(pcase (list 1 2 3) ((1 2 3) t))” was true, it would allow to bind a
list first element when it’s also the name of a predefined pattern, like
“(pcase (list 1 2 3) (((var and) 2 3) and))” would give “1” (it looks
silly to use a such name for a variable, but we never know, and at least
it makes pcase not unable to match some patterns (without ` I mean),
like guile’s match).

Also, as to speak about common pattern matching facilities, and how they
make patterns look related to their match: all of them make normal,
unbound identifier, lead to binding, instead of evaluation and
replacement by their bound value.  I (strangely, I realize no), see no
facilities in pattern matching in non-lisp languages to match the value
of an already bound variable… or am I wrong? do they allow that?

Even in pcase I don’t see how to do that except manually using (and var
(guard (equal var val))), which exactely looks like a cond, but more
complex, embed in a, now uselessly complex pcase, which, then, defeat
its purpose.

And yet that’d been the behavior I’d imagine for ,var, in `, that’s why
it’s confusing.  However, I cannot suggest to change it to lead ,var to
be evaluated to its value bound outside of pcase, because the way pcase
bind ` seems to already be used by several other pattern matching
facilities, so that’d break compatibility and bring confusion, too,
sadly (maybe a definable pattern could change the default ` behavior, so
people could experiment this behavior at least? yet their code could
lead to confusion then).

>> Beside lisp, all pattern matching language make their feature serve
>> one purpose: the pattern look like what the data should be. adding “`”
>> and “,” destroy this feature, because the pattern no longer looks like
>> what is matched.
>
> But with, for example, el-search, that suddenly looks very natural if
> you can, for example, transpose the first two arguments of all `foo'
> calls in your code with the rule.
>
>    `(foo ,a ,b . ,rest) -> `(foo ,b ,a . ,rest)

No it doesn’t look natural: the transformation does, the reading is
straightforward, the result is, but making the first pattern isn’t,
because a and b aren’t bound to anything, so the “`” meaning is truly
different (at least partially) than normal.

> The pattern exactly looks like the matched data!  Just with a different
> point of view.  Using ``' is not what most people would naively use to
> implement destructuring, but I don't find it unnatural or not intuitive,
> no.

Afaik, the matched data, here, is “(foo <something> <something>
. <something>)”, like “(foo 1 2 . 3)” (unquoted), or, when quoted “('foo
1 2 . 3)” (or “'(foo 1 2 . 3)” if you want, but if you ever changed to
“`” here, you’d have to admit it doesn’t mean the same as in pcase, and,
obviously: the fact you maybe used it in the data you want to match,
doesn’t mean you need to use it in the pattern (because the reader
removes it) so the purpose is defeated), that’s not what I call “look
exactely like it”: “(foo 1 2 . 3)” is “exactely”, “('foo a b . rest)”
would be enough.  I find “`(foo ,(var a) ,(var b) . ,(var rest))” is
still understandable and not that confusing, but it *doesn’t* look like
the matched data, like it does in other languages, such as
ocaml/haskell/rust/etc.

> The above pattern would look different if we would have to write it as
>
>   `(foo ,(var a) ,(var b) . ,(var rest))
>
> so the implicit binding feature of symbols also makes patterns much more
> readable in more complex cases, which is a big win.

It is a big win only in terms of avoiding confusion (with “`”), and
allowing otherwise impossible stuff (without “`”), but I wasn’t
proposing it to make more readable, only more powerful and less
confusing.  What would make more readable are directly matching them
when they don’t correspound an already defined pattern (such as (1 2 3),
since no pattern is defined after a number, or absolutely all occurences
of [], since no pattern is defined after an array), like guile’s and
racket’s matches, and some common lisp matches, do, and, otherwise,
pattern named after type constructor such as `vector' or `list', as you
suggested in the other thread, to correct me:

#+begin_src emacs-lisp
(pcase-defmacro list (&rest args)
  `(,'\`  ,(mapcar (lambda (thing) `(,'\, ,thing)) args)))
#+end_src

I tried to adapt for arrays:

#+begin_src emacs-lisp
(pcase-defmacro array (&rest args)
  `[,'\` ,(mapcar (lambda (thing) `(,'\, ,thing)) args)])
#+end_src

But it doesn’t work x), that, plus my initial non-working
“(pcase-defmacro list (&rest args) ``(,@args))”, I must find “`”, is,
indeed, quite confusing (how is “,'” needed? how isn’t “,'\`” equivalent
to “\`”?), even in real life (or maybe here it is because of pcase it is
that complex?), when it get complex, like used directly recursively.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-28 21:44                                                                                 ` Stefan Monnier
@ 2018-10-29 13:01                                                                                   ` Alan Mackenzie
  2018-10-29 13:28                                                                                     ` Stefan Monnier
  2018-10-29 14:47                                                                                   ` Andy Moreton
  2018-10-30 23:34                                                                                   ` Replace trivial pcase occurrences in the Emacs sources Van L
  2 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-29 13:01 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Hello, Stefan.

On Sun, Oct 28, 2018 at 17:44:57 -0400, Stefan Monnier wrote:
> > pcase-lambda, pcase-let, pcase-let*, and pcase-dolist still have no
> > meaningful documentation,

> Not sure what kind of documentation would be more meaningful, sorry.

Doc strings which specify fully the arguments to these macros, including
their semantics, and say what the macros do.  The current doc strings
(at least some of them) for these macros don't do this.

Entries in the elisp manual.  These don't exist at all.  (Or, if they
do, they don't have index entries.)

> Do you happen to have concrete questions about them which aren't answered
> by their docstrings?

I've had such questions in the past, and had to answer them by time
consuming guessing, reading the source of pcase-..., and
experimentation.  Adequate documentation would have saved me a great
deal of time, frustration, and uncertainty.

[ .... ]

>         Stefan

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 13:01                                                                                   ` Alan Mackenzie
@ 2018-10-29 13:28                                                                                     ` Stefan Monnier
  2018-10-29 13:47                                                                                       ` Alan Mackenzie
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-29 13:28 UTC (permalink / raw)
  To: emacs-devel

> Doc strings which specify fully the arguments to these macros, including
> their semantics, and say what the macros do.  The current doc strings
> (at least some of them) for these macros don't do this.

I understand this in theory, but I don't know what it means in this
concrete case.

> I've had such questions in the past, and had to answer them by time
> consuming guessing, reading the source of pcase-..., and
> experimentation.

Do you remember them enough to describe the problems, so we can try and
improve the doc accordingly?

> Adequate documentation would have saved me a great deal of time,
> frustration, and uncertainty.

I don't doubt it.  But I'm sadly not able to guess what those problems
might be.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 13:28                                                                                     ` Stefan Monnier
@ 2018-10-29 13:47                                                                                       ` Alan Mackenzie
  2018-10-29 21:08                                                                                         ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-29 13:47 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Hello, Stefan.

On Mon, Oct 29, 2018 at 09:28:25 -0400, Stefan Monnier wrote:
> > Doc strings which specify fully the arguments to these macros, including
> > their semantics, and say what the macros do.  The current doc strings
> > (at least some of them) for these macros don't do this.

> I understand this in theory, but I don't know what it means in this
> concrete case.

Take a look at, for example, the doc string for pcase-dolist.  In its
entirety, it's this:

    pcase-dolist is an autoloaded Lisp macro in `pcase.el'.

    (pcase-dolist (PATTERN LIST) BODY...)

    Like `dolist' but where the binding can be a `pcase' pattern.

There is no clue here what PATTERN, LIST, and BODY mean.  It is unclear
what "the binding" is.  It is unclear, exactly, what a "`pcase' pattern"
is.

It is not explained what the code (generated by the macro) does.  Even
supposing the notion "`pcase' pattern" to be understood, there is no
explanation of how such a pattern is used.

There is no explanation of any compatibility constraints between the
arguments PATTERN, LIST, and BODY.

There are no examples to clarify the syntax and semantics.

Now it is possible that partial enlightenment will come from looking at
the referenced doc strings for dolist and pcase, but I remember,
vaguely, this not being very helpful.  Maybe it's better now, with the
improved documentation of pcase.

> > I've had such questions in the past, and had to answer them by time
> > consuming guessing, reading the source of pcase-..., and
> > experimentation.

> Do you remember them enough to describe the problems, so we can try and
> improve the doc accordingly?

See above.

> > Adequate documentation would have saved me a great deal of time,
> > frustration, and uncertainty.

> I don't doubt it.  But I'm sadly not able to guess what those problems
> might be.

Also see above.

>         Stefan

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-28 21:44                                                                                 ` Stefan Monnier
  2018-10-29 13:01                                                                                   ` Alan Mackenzie
@ 2018-10-29 14:47                                                                                   ` Andy Moreton
  2018-10-29 18:49                                                                                     ` pcase-lambda usage [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
  2018-10-30 23:34                                                                                   ` Replace trivial pcase occurrences in the Emacs sources Van L
  2 siblings, 1 reply; 375+ messages in thread
From: Andy Moreton @ 2018-10-29 14:47 UTC (permalink / raw)
  To: emacs-devel

On Sun 28 Oct 2018, Stefan Monnier wrote:

>> pcase-lambda, pcase-let, pcase-let*, and pcase-dolist still have no
>> meaningful documentation,
>
> Not sure what kind of documentation would be more meaningful, sorry.
> Do you happen to have concrete questions about them which aren't answered
> by their docstrings?

Here is the documentation for lambda - reasonably complete and
descriptive, and with links to other referenced symbols:

  (lambda ARGS [DOCSTRING] [INTERACTIVE] BODY)

  Return a lambda expression.
  A call of the form (lambda ARGS DOCSTRING INTERACTIVE BODY) is
  self-quoting; the result of evaluating the lambda expression is the
  expression itself.  The lambda expression may then be treated as a
  function, i.e., stored as the function value of a symbol, passed to
  ‘funcall’ or ‘mapcar’, etc.

  ARGS should take the same form as an argument list for a ‘defun’.
  DOCSTRING is an optional documentation string.
   If present, it should describe how to call the function.
   But documentation strings are usually not useful in nameless functions.
  INTERACTIVE should be a call to the function ‘interactive’, which see.
  It may also be omitted.
  BODY should be a list of Lisp expressions.

Contrast this with the `pcase-lambda' docstring:

  (pcase-lambda LAMBDA-LIST &rest BODY)

  Like ‘lambda’ but allow each argument to be a pattern.
  I.e. accepts the usual &optional and &rest keywords, but every
  formal argument can be any pattern accepted by ‘pcase’ (a mere
  variable name being but a special case of it).

This mentions "each argument", but the arguments shown have
`LAMBDA-LIST' (which is not described) and BODY - is this an argument
that can be pattern ? There is no discussion of how pattern match
failure is treated - what happens ? Please note that users can only read
what is in the docstring, not the unwritten intentions of the docstring
author.

The `pcase-let' docstring warns that it assumes patterns will match and
fails arbitrarily if that is not the case. This seems a strng indicator
that this macro is unsafe for use in any user code.

The `pcase-let*' docstring does not mention a similar pattern matching
assumption, so does it also behave randomly on pattern match failure ?

The `pcase-dolist' docstring is entirely uninformative. None of the
arguments are described, nor are the semantics of the macro. The
docstring needs complete replacement.

The pcase-exhaustive docstring mentions that an error is signalled if
pattern matching fails, but which error ? How are users supposed to
write code that determines that a pattern match failure has occurred
rather than any other error ? Which error is signalled should be part of
the interface contract here, and should be documented.

There are no entry in the manual for the pcase macros, and there are no
meaningful examples to show proper usage of each of the pcase match
pattern types.

> Could you clarify what you find problematic in those uses?

Given that the documentation is insufficient to describe the syntax and
semantics of these macros, how can ordinary users discern the meaning of
a pcase construct that they read in code ? How can they learn to write
code containing pcase macros which has the user's desired semantics ?

How can users learn when these constructs may be beneficial and when
they should be avoided ?

    AndyM




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-28 23:09                                                                                           ` Garreau, Alexandre
  2018-10-28 23:57                                                                                             ` Michael Heerdegen
@ 2018-10-29 17:26                                                                                             ` Clément Pit-Claudel
  2018-10-30  0:27                                                                                               ` pcase ` meaning Garreau, Alexandre
  1 sibling, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-29 17:26 UTC (permalink / raw)
  To: emacs-devel

On 28/10/2018 19.09, Garreau, Alexandre wrote:
> the pattern look like what the data should be. adding “`” and “,”
> destroy this feature, because the pattern no longer looks like what
> is matched.

Maybe it's a matter of perspective? Adding "`" and "," is precisely what makes the pattern look like the data: the invariant is that if you have a match, repeating the pattern produces the original data.

Here's a concrete example: (pcase '(1 2 3 4) (`(,x ,y . ,z) `(,x ,y . ,z))) is a no-op.
In other words, q-patterns are equations with multiple unknown variables (holes).  When you write a q-pattern, you're asking "what values should the variables in this pattern take so that evaluating the pattern would return the matched data?"

Clément.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* pcase-lambda usage [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-29 14:47                                                                                   ` Andy Moreton
@ 2018-10-29 18:49                                                                                     ` Garreau, Alexandre
  0 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-29 18:49 UTC (permalink / raw)
  To: Andy Moreton; +Cc: emacs-devel

From what I learnt from pcase-lambda (I wished there were a simple
`match' implemented over `cl-destructuring-bind', similar to
one-matching cl implementations, on which would be based pcase (which
match several alternatively), and pcase-*), here a docstring that seems
better to me, probably not ideal, if anybody can improve, tell it:

#+BEGIN_SRC elisp
  "Like `lambda' but destructure each PATTERN with `pcase'.
It is not self-quoting: the result of `pcase-lambda' is a lambda
expression like returned by `lambda'.  Only then, the lambda expression
may be stored as a function value of a symbol with `fset', passed to
`funcall' or `mapcar', etc.  The first argument, of the form
(PATTERN...) also accepts the usual &optional and &rest keywords
accepted in lambda expressions arglist, but every formal element can be
any pattern accepted by `pcase' (a mere variable name being but a
special case of it).

PATTERN should take the same form as a `pcase' pattern.
  A given subpattern inside PATTERN might not match values (equality) or
  even types, except for each of its subsequences, which *have* to
  exist, have the right type, and be in the right place.
DOCSTRING is an optional documentation string just as in `lambda'.
  Note that each PATTERN that is a special `pcase' pattern will get an
  automatically assigned name: you may want to put
  \\(fn YOUR ARGLIST (AS YOU INTENDED)) so to reflect your patterns.
INTERACTIVE, should as well be a call to the function `interactive'.
It may be omitted.
BODY should be the usual list of Lisp expressions `lambda' takes as
lasts arguments.

\(fn (PATTERN...) [DOCSTRING] [INTERACTIVE] BODY)"
#+END_SRC

As I never saw pcase-lambda before and this was the first time I see
anything about it, here a sample of the process I went trough:

C-h f pcase-lambda RET => (pcase-lambda LAMBDA-LIST &rest BODY)

Okay, so there’s only one pattern, so it’s not pattern matching (as its
name might wrongly suggest), like in OCaml “function” operator, it’s
simple destructuring, exactely like `cl-destructuring-bind', but richer.

Also: no “docstring”? no “interactive”? really? doesn’t `pcase-lambda'
happen to work by translating to a lambda? does it override docstrings
(that might make sense, so to replace the arglist in help by the pcase
pattern) and interactiveness (that doesn’t make sense at all: so we
can’t define after pcase-lambda a pcase-defun and pcase-defmacro (wait,
this one is already occupied… it should have been a different name then:
this has gone too far)?)?

let’s try:
#+BEGIN_SRC emacs-lisp
  (global-set-key (kbd "C-c c c c")
     (pcase-lambda (a `(,b ,c))
       "test"
       (interactive)
       (insert ?2)))
#+END_SRC

Then “C-c c c c”, actually inserts 2.

C-h k C-c c c c => the docstring is “test”.

So these must be implicitly considered as inside “body”… that doesn’t
make really sense: even `lambda' explictly tells about them, while not
recommanding against not using docstring in anonymous function.

Docstring:
> Like ‘lambda’ but allow each argument to be a pattern.
> I.e. accepts the usual &optional and &rest keywords, but every
> formal argument can be any pattern accepted by ‘pcase’ (a mere
> variable name being but a special case of it).

Oh, does that mean I can, like cl-destructuring-bind, put &optional and
&rest wherever I want in any subpattern?  So then pcase is strictly a
superset of cl-destructuring-bind: how sad one is not implemented upon
the other, then (cl-destructuring-bind ought to have a no-error function
so that to be usable to build something upon it).

#+BEGIN_SRC emacs-lisp
  (pcase-lambda (a (b c)) c)
  ;; => pcase--macroexpand: Unknown a pattern: (a (b c))
  
  (pcase (list 1 (list 2 3)) ((a (b c)) c))
  ;; => pcase--macroexpand: Unknown a pattern: (a (b c))
  
  ;; Oh, I recall, pcase behaves differently than normal
  ;; pattern-matching, I must quote everything!
  
  (pcase-lambda '(a (b c)) c)
  ;; => pcase--macroexpand: Unknown a pattern: (a (b c))
  
  ;; Uh, isn’t ' a pattern in pcase? It errs out just the same!
  
  (pcase '(1 (2 3)) ('(a (b c)) t)) ; => nil ; But… why aren’t they
                                             ; behaving the same? Why
                                             ; don’t I get an error?
  
  ;; Oh I recall! I must use “`”:
  (pcase '(1 (2 3)) (`(,a (,b ,c)) t)) ; => t (It Works!™)
  
  So:
  (pcase-lambda `(,a (,b ,c)) c) ; => Wrong type argument: symbolp, (\, a)
  ;; Uh, isn’t that the correct way to use pcase?
  
  ;; Let’s go back before, when it unexpectedly didn’t err, wasn’t I
  ;; right?
  (pcase '(a (b c)) ('(a (b c)) t)) ; => t (so indeed, I was right)
  
  (pcase 'a ('a t)) ; => t (indeed, when you quote you compare symbols,
                    ;       not values (nor bind anything))
  
  ;; So let’s try the simplest case:
  (pcase-lambda 'a a) ; => (lambda (quote a) a)
  
  ;; Oh, if I’m right, that “quote” isn’t a quotation, but an argument
  
  ((lambda (quote a) a) 1 2) ; => 2 (it seems so)
  
  ((lambda (quote a) a) 'a)
  ;; => Wrong number of arguments: (lambda (quote a) a), 1
  ;; it *is* so
  
  ;; Then, if I’m right, the correct usage is:
  
  (pcase-lambda (a) a) ; => (lambda (a) a) ; okay it returns clean
                                           ; lambdas if possible
  
  (pcase-lambda (a (2 3)) a)
  ;; => (lambda (a arg0) (let nil a))
  ;; ah, I was wrong, nevermind (why this useless `let nil'?).  Btw, may I
  ;; suggest an argument name such as `list' instead of `arg0' that would
  ;; indicate type, as it is traditional in lisp (and only number list0,
  ;; list1, etc. if there are several of them)
  
  ((pcase-lambda (a '(2 3)) a) 1 (list 2 3))
  ;; => Invalid function: (pcase-lambda (a (quote (2 3)) a))
  
  ;; oh, there must be a special elisp-related reason why even if it does
  ;; return a lambda it can’t be used right away (maybe because it’s a
  ;; lisp-2?).  Since `lambda' doc says it’s “self-quoting” and “may be
  ;; used as a function”, and that’s not true the same way here, it should
  ;; be said.
  
  (funcall (pcase-lambda (a '(2 3)) a) 1 (list 2 3))
  => 1
  
  ;; Okay so since `lambda' docstring takes the time to say it works with
  ;; `funcall' and `mapcar', then probably `pcase-lambda' should too, so
  ;; an example of how to properly use it comes immediatly to mind.
  
  (funcall (pcase-lambda (a '(2 3)) a) 1 (list 1 1))
  
  ;; Okay it’s not normal, it should give an error, or returns nil, I think.

  (funcall (pcase-lambda (a '(b c)) c) 1 '(2 3)) ; let’s see what’s wrong
  ;; => Symbol’s value as variable is void: c
  ;; c isn’t bound?
  
  ;; Maybe quoting, again?
  (funcall (pcase-lambda (a `(,b ,c)) c) 1 '(2 3)) ; => 3 (yes, quoting)
  
  ;; Let’s try again not to match:
  (funcall (pcase-lambda (`(1 ,b 3)) a) 2)
  ;; => let*: Wrong type argument: listp, 2
  ;; Cool! *Now* it gives errors!

  (funcall (pcase-lambda (`(1 ,b 3)) b) '(2))
  ;; => nil (okay… I don’t understand)

  (funcall (pcase-lambda (`(1 ,b 3)) b) '(1 2 4))
  ;; => 2 (mmmh… seems lazy on arity and eq-uality… but picky on types)

  (mapcar (pcase-lambda (`(1 (2 ,c 4 . 5))) c)
    '((1 (2 3 4 . 5))
      (1 (2))
      (1 (2 3 4 5 6 . 7))))
  ;; => (2 nil) (indeed, it doesn’t give a fuck about arity)

  (funcall (pcase-lambda (`(1 (2 ,c 4 . 5))) c) '(1 (2 . 3)))
  ;; => let*: Wrong type argument: listp, 3
  ;; But it want sequences to be the right type
  
  (funcall (pcase-lambda (`(1 (2 ,c 4 . 5))) c) '(1 (2 3 . 4)))
  ;; => let*: Wrong type argument: listp, 4
  ;; Even when it doesn’t need to, apparently, so it’s not even laziness

  (funcall (pcase-lambda (`(1 (2 ,c (4 5)))) c) '(1 (2 3))) ; => 3
  (funcall (pcase-lambda (`(1 (2 ,c (4 5)))) c) '(1 (2 3 [4 5])))
  ;; => let*: Wrong type argument: listp, [4 5]
  ;; Yeah, sequences types, only that (it should have used “elt”, so it
  ;; would have always worked (you then only need to have the same
  ;; sequences tree structure)
  
  ;; let’s try out how that acts on arglist features
  (funcall (pcase-lambda (a `(&rest ,rest)) rest) 1 2 3)
  ;; => Wrong number of arguments: (lambda (a arg0) (let* ((x (car
  ;;    arg0)) (x (cdr arg0)) (x (car x)) (x (cdr x))) (let ((rest x))
  ;;    rest))), 3
  
  ;; Ah indeed, to do that it would be:
  (funcall (pcase-lambda (a &rest rest) rest) 1 2 3) ; => (2 3)
  ;; yes &rest works
  
  ;; So, I want, with correct args:
  (funcall (pcase-lambda (a `(&rest ,rest)) rest) 1 '(2 3)) ; => 3
  ;; UH???
  
  (funcall (pcase-lambda (a `(,b ,c &rest ,rest)) rest) 1 '(2 3 4 5 6 7))
  ;; => 5 (okay something strange is going)
  
  (funcall (pcase-lambda (a `(,b ,c &optional ,opt)) opt) 1 '(2 3 4))
  (funcall (pcase-lambda (a `(,b ,c &optional ,opt)) opt) 1 '(2 3))
  ;; => nil => nil (what?)
  
  (funcall (pcase-lambda (a `(,b ,c &optional ,opt)) opt) 1 '(2 3 4 5))
  ;; => 5 (there’s one argument too much)
  
  ;; Don’t say me &optional is matched as an argument?
  (funcall (pcase-lambda (a `(,b ,c &optional ,opt)) (list b c opt))
           1 '(2 3 4 5))                           ; => (2 3 5)
  ;; Is seems to >< so in the end it doesn’t work?
  
  (funcall (pcase-lambda (a &optional ,opt) (cons a opt))
           1 '(2 3 4 5))
  ;; => pcase--macroexpand: Unknown , pattern: (\, opt)
  
  (funcall (pcase-lambda (a &optional opt) (cons a opt))
           1 2)                                    ; => (1 . 2)
  (funcall (pcase-lambda (a &optional opt) (cons a opt))
           1)                                      ; => (1)
  
  ;; Isn’t behavior not supposed to change depending on nesting?
  
  (apply (pcase-lambda (a (b (c))) (cons a c)) '(a (b (c))))
  ;; => pcase--macroexpand: Unknown b pattern: (b (c))
  
  ;; It seems it becomes real `pcase' only from second level:
  (apply (pcase-lambda (a `(,b (,c))) (cons a c)) '(a (b (c))))
  ;; => (a . c)
  
  ;; So first level is what normal lambda (or destructuring-bind) does,
  ;; that looks like real pattern matching that look like the matched
  ;; data, like in ocaml, haskell, etc. and second level is pcase syntax…
#+END_SRC



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 13:47                                                                                       ` Alan Mackenzie
@ 2018-10-29 21:08                                                                                         ` Stefan Monnier
  2018-10-29 21:53                                                                                           ` Michael Heerdegen
                                                                                                             ` (4 more replies)
  0 siblings, 5 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-29 21:08 UTC (permalink / raw)
  To: emacs-devel

>> > Doc strings which specify fully the arguments to these macros, including
>> > their semantics, and say what the macros do.  The current doc strings
>> > (at least some of them) for these macros don't do this.
>> I understand this in theory, but I don't know what it means in this
>> concrete case.
> Take a look at, for example, the doc string for pcase-dolist.  In its
> entirety, it's this:

Thanks.  What do you think of the patch below?

I'd rather keep it defined in terms of its differences w.r.t `dolist`,
but if really needed, we could change the doc so it doesn't rely on
`dolist`s own doc at all.

We do have to keep the reference to `pcase` because we don't want to
repeat the definition of what a pcase pattern can look like.


        Stefan


diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
index 57c2d6c3cb..861c900b21 100644
--- a/lisp/emacs-lisp/pcase.el
+++ b/lisp/emacs-lisp/pcase.el
@@ -281,7 +281,7 @@ pcase-let*
 (defmacro pcase-let (bindings &rest body)
   "Like `let' but where you can use `pcase' patterns for bindings.
 BODY should be a list of expressions, and BINDINGS should be a list of bindings
-of the form (PAT EXP).
+of the form (PATTERN EXP).
 The macro is expanded and optimized under the assumption that those
 patterns *will* match, so a mismatch may go undetected or may cause
 any kind of error."
@@ -302,7 +302,12 @@ pcase-let
 
 ;;;###autoload
 (defmacro pcase-dolist (spec &rest body)
-  "Like `dolist' but where the binding can be a `pcase' pattern.
+  "Superset of `dolist' where the VAR binding can be a `pcase' PATTERN.
+More specifically `dolist's VAR binding is replaced by a PATTERN
+against which each element of the list is matched.
+As in the case of `pcase-let', PATTERN is matched under the assumption
+that it *will* match.
+
 \n(fn (PATTERN LIST) BODY...)"
   (declare (indent 1) (debug ((pcase-PAT form) body)))
   (if (pcase--trivial-upat-p (car spec))




^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-29 10:22                                                                                               ` Garreau, Alexandre
@ 2018-10-29 21:33                                                                                                 ` Michael Heerdegen
  2018-10-29 23:00                                                                                                   ` pcase ` meaning Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-29 21:33 UTC (permalink / raw)
  To: Garreau, Alexandre
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> Even in pcase I don’t see how to do that except manually using (and var
> (guard (equal var val))),

You mean like (pred (equal val))?


> #+begin_src emacs-lisp
> (pcase-defmacro list (&rest args)
>   `(,'\`  ,(mapcar (lambda (thing) `(,'\, ,thing)) args)))
> #+end_src
>
> I tried to adapt for arrays:
>
> #+begin_src emacs-lisp
> (pcase-defmacro array (&rest args)
>   `[,'\` ,(mapcar (lambda (thing) `(,'\, ,thing)) args)])
> #+end_src

> But it doesn’t work x), that, plus my initial non-working
> “(pcase-defmacro list (&rest args) ``(,@args))”, I must find “`”, is,
> indeed, quite confusing (how is “,'” needed? how isn’t “,'\`” equivalent
> to “\`”?),

You want , to survive til after the macro expansion.  Backquote can't
know that it should ignore a , because you want it to be literally in
the expansion.  ,'\` let's backquote insert a literal , into the
expansion, which is what you want.  The underlying problem is that you
want to use (of course you don't have to!) backquote to construct a
backquote expression.  That happens here and there when writing Lisp,
it's not something special to pcase.

For understanding the definition above note that ``' (synonymous for
`backquote') is a (very normal) macro accepting one argument STRUCTURE,
whereby we also have an abbreviating reader syntax
`STRUCTURE == (` STRUCTURE).  We also have the reader syntax
,THING == (, THING).

Your pcase macro `array' could be defined like

#+begin_src emacs-lisp
(pcase-defmacro array (&rest args)
  `(,'\` [,@(mapcar (lambda (thing) `(,'\, ,thing)) args)]))
#+end_src

You could also write that without backquote (and also without the []
reader syntax).


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29  3:26                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
@ 2018-10-29 21:46                                                                                   ` Michael Heerdegen
  2018-10-30  0:36                                                                                     ` What `case' have done you? [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
  2018-10-30  6:31                                                                                     ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-29 21:46 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

[-- Attachment #1: Type: text/plain, Size: 430 bytes --]

Eli Zaretskii <eliz@gnu.org> writes:

> I'd prefer this format:
>
>   * lisp/char-fold.el:
>   * lisp/dired.el:
>   * lisp/emacs-lisp/derived.el:
>   * lisp/emacs-lisp/easy-mmode.el: Don't quote self-quoting 'pcase'
>   patterns.
>
> IOW, a list of all changed files, with the description at the end.

Ok, done.  I kept the description as commit message however, since I
need one.  Ok to install (the patch itself is unchanged)?


[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0001-Don-t-quote-self-quoting-pcase-patterns.patch --]
[-- Type: text/x-diff, Size: 39685 bytes --]

From 656f77b1233388ef713ca84904c1ffbddf49c002 Mon Sep 17 00:00:00 2001
From: Michael Heerdegen <michael_heerdegen@web.de>
Date: Sat, 27 Oct 2018 01:48:35 +0200
Subject: [PATCH] Don't quote self-quoting pcase patterns

* admin/bzrmerge.el:
* lisp/char-fold.el:
* lisp/dired.el:
* lisp/emacs-lisp/derived.el:
* lisp/emacs-lisp/easy-mmode.el:
* lisp/emacs-lisp/easymenu.el:
* lisp/emacs-lisp/eieio-core.el:
* lisp/emacs-lisp/package.el:
* lisp/emacs-lisp/smie.el:
* lisp/faces.el:
* lisp/filesets.el:
* lisp/progmodes/modula2.el:
* lisp/progmodes/octave.el:
* lisp/progmodes/opascal.el:
* lisp/progmodes/perl-mode.el:
* lisp/progmodes/prolog.el:
* lisp/progmodes/ruby-mode.el:
* lisp/progmodes/sh-script.el:
* lisp/server.el:
* lisp/subr.el:
* lisp/textmodes/css-mode.el:
* test/lisp/emacs-lisp/pcase-tests.el: Don't quote self-quoting
'pcase' patterns.
---
 admin/bzrmerge.el                   |  6 +--
 lisp/char-fold.el                   |  2 +-
 lisp/dired.el                       |  8 ++--
 lisp/emacs-lisp/derived.el          |  8 ++--
 lisp/emacs-lisp/easy-mmode.el       | 62 ++++++++++++++---------------
 lisp/emacs-lisp/easymenu.el         | 28 ++++++-------
 lisp/emacs-lisp/eieio-core.el       |  6 +--
 lisp/emacs-lisp/package.el          | 22 +++++-----
 lisp/emacs-lisp/smie.el             |  4 +-
 lisp/faces.el                       | 22 +++++-----
 lisp/filesets.el                    |  2 +-
 lisp/progmodes/modula2.el           | 22 +++++-----
 lisp/progmodes/octave.el            | 36 ++++++++---------
 lisp/progmodes/opascal.el           | 14 +++----
 lisp/progmodes/perl-mode.el         |  4 +-
 lisp/progmodes/prolog.el            | 14 +++----
 lisp/progmodes/ruby-mode.el         | 18 ++++-----
 lisp/progmodes/sh-script.el         | 18 ++++-----
 lisp/server.el                      | 32 +++++++--------
 lisp/subr.el                        |  2 +-
 lisp/textmodes/css-mode.el          |  2 +-
 test/lisp/emacs-lisp/pcase-tests.el |  2 +-
 22 files changed, 167 insertions(+), 167 deletions(-)

diff --git a/admin/bzrmerge.el b/admin/bzrmerge.el
index cedb625fb0..d54ba330f9 100644
--- a/admin/bzrmerge.el
+++ b/admin/bzrmerge.el
@@ -150,12 +150,12 @@ bzrmerge-missing
                              (format "%s: Skip (y/n/N/q/%s)? " str
                                      (key-description (vector help-char)))
                              '(?y ?n ?N ?q)))
-                      (`?y (setq skip t))
-                      (`?q (keyboard-quit))
+                      (?y (setq skip t))
+                      (?q (keyboard-quit))
                       ;; A single log entry can match skip-regexp multiple
                       ;; times.  If you are sure you don't want to skip it,
                       ;; you don't want to be asked multiple times.
-                      (`?N (setq skip 'no))))))
+                      (?N (setq skip 'no))))))
               (if (eq skip t)
                   (push revno skipped)
                 (push revno revnos)))))
diff --git a/lisp/char-fold.el b/lisp/char-fold.el
index 86bd6038e3..907d49e4f2 100644
--- a/lisp/char-fold.el
+++ b/lisp/char-fold.el
@@ -170,7 +170,7 @@ char-fold-to-regexp
     ;; need to keep them grouped together like this: "\\(  \\|[ ...][ ...]\\)".
     (while (< i end)
       (pcase (aref string i)
-        (`?\s (setq spaces (1+ spaces)))
+        (?\s (setq spaces (1+ spaces)))
         (c (when (> spaces 0)
              (push (char-fold--make-space-string spaces) out)
              (setq spaces 0))
diff --git a/lisp/dired.el b/lisp/dired.el
index 5c7bb9599c..f2f2b76eb7 100644
--- a/lisp/dired.el
+++ b/lisp/dired.el
@@ -3046,10 +3046,10 @@ dired-delete-file
                              ("no"   ?n "skip to next")
                              ("all"  ?! "delete all remaining directories with no more questions")
                              ("quit" ?q "exit")))
-                     ('"all" (setq recursive 'always dired-recursive-deletes recursive))
-                     ('"yes" (if (eq recursive 'top) (setq recursive 'always)))
-                     ('"no" (setq recursive nil))
-                     ('"quit" (keyboard-quit))
+                     ("all" (setq recursive 'always dired-recursive-deletes recursive))
+                     ("yes" (if (eq recursive 'top) (setq recursive 'always)))
+                     ("no" (setq recursive nil))
+                     ("quit" (keyboard-quit))
                      (_ (keyboard-quit))))) ; catch all unknown answers
              (setq recursive nil)) ; Empty dir or recursive is nil.
            (delete-directory file recursive trash))))
diff --git a/lisp/emacs-lisp/derived.el b/lisp/emacs-lisp/derived.el
index 6b47ffea07..483d6fbfa4 100644
--- a/lisp/emacs-lisp/derived.el
+++ b/lisp/emacs-lisp/derived.el
@@ -193,10 +193,10 @@ define-derived-mode
     ;; Process the keyword args.
     (while (keywordp (car body))
       (pcase (pop body)
-	(`:group (setq group (pop body)))
-	(`:abbrev-table (setq abbrev (pop body)) (setq declare-abbrev nil))
-	(`:syntax-table (setq syntax (pop body)) (setq declare-syntax nil))
-        (`:after-hook (setq after-hook (pop body)))
+	(:group (setq group (pop body)))
+	(:abbrev-table (setq abbrev (pop body)) (setq declare-abbrev nil))
+	(:syntax-table (setq syntax (pop body)) (setq declare-syntax nil))
+        (:after-hook (setq after-hook (pop body)))
 	(_ (pop body))))
 
     (setq docstring (derived-mode-make-docstring
diff --git a/lisp/emacs-lisp/easy-mmode.el b/lisp/emacs-lisp/easy-mmode.el
index 4d8a502026..d74c3ddb97 100644
--- a/lisp/emacs-lisp/easy-mmode.el
+++ b/lisp/emacs-lisp/easy-mmode.el
@@ -217,30 +217,30 @@ define-minor-mode
     (while (keywordp (setq keyw (car body)))
       (setq body (cdr body))
       (pcase keyw
-	(`:init-value (setq init-value (pop body)))
-	(`:lighter (setq lighter (purecopy (pop body))))
-	(`:global (setq globalp (pop body))
-         (when (and globalp (symbolp mode))
-           (setq setter `(setq-default ,mode))
-           (setq getter `(default-value ',mode))))
-	(`:extra-args (setq extra-args (pop body)))
-	(`:set (setq set (list :set (pop body))))
-	(`:initialize (setq initialize (list :initialize (pop body))))
-	(`:group (setq group (nconc group (list :group (pop body)))))
-	(`:type (setq type (list :type (pop body))))
-	(`:require (setq require (pop body)))
-	(`:keymap (setq keymap (pop body)))
-        (`:variable (setq variable (pop body))
-         (if (not (and (setq tmp (cdr-safe variable))
-                       (or (symbolp tmp)
-                           (functionp tmp))))
-             ;; PLACE is not of the form (GET . SET).
-             (progn
-               (setq setter `(setf ,variable))
-               (setq getter variable))
-           (setq getter (car variable))
-           (setq setter `(funcall #',(cdr variable)))))
-	(`:after-hook (setq after-hook (pop body)))
+	(:init-value (setq init-value (pop body)))
+	(:lighter (setq lighter (purecopy (pop body))))
+	(:global (setq globalp (pop body))
+                 (when (and globalp (symbolp mode))
+                   (setq setter `(setq-default ,mode))
+                   (setq getter `(default-value ',mode))))
+	(:extra-args (setq extra-args (pop body)))
+	(:set (setq set (list :set (pop body))))
+	(:initialize (setq initialize (list :initialize (pop body))))
+	(:group (setq group (nconc group (list :group (pop body)))))
+	(:type (setq type (list :type (pop body))))
+	(:require (setq require (pop body)))
+	(:keymap (setq keymap (pop body)))
+        (:variable (setq variable (pop body))
+                   (if (not (and (setq tmp (cdr-safe variable))
+                                 (or (symbolp tmp)
+                                     (functionp tmp))))
+                       ;; PLACE is not of the form (GET . SET).
+                       (progn
+                         (setq setter `(setf ,variable))
+                         (setq getter variable))
+                     (setq getter (car variable))
+                     (setq setter `(funcall #',(cdr variable)))))
+	(:after-hook (setq after-hook (pop body)))
 	(_ (push keyw extra-keywords) (push (pop body) extra-keywords))))
 
     (setq keymap-sym (if (and keymap (symbolp keymap)) keymap
@@ -407,8 +407,8 @@ define-globalized-minor-mode
     (while (keywordp (setq keyw (car keys)))
       (setq keys (cdr keys))
       (pcase keyw
-	(`:group (setq group (nconc group (list :group (pop keys)))))
-	(`:global (setq keys (cdr keys)))
+	(:group (setq group (nconc group (list :group (pop keys)))))
+	(:global (setq keys (cdr keys)))
 	(_ (push keyw extra-keywords) (push (pop keys) extra-keywords))))
 
     (unless group
@@ -533,11 +533,11 @@ easy-mmode-define-keymap
       (let ((key (pop args))
 	    (val (pop args)))
 	(pcase key
-	 (`:name (setq name val))
-	 (`:dense (setq dense val))
-	 (`:inherit (setq inherit val))
-	 (`:suppress (setq suppress val))
-	 (`:group)
+	  (:name (setq name val))
+	  (:dense (setq dense val))
+	  (:inherit (setq inherit val))
+	  (:suppress (setq suppress val))
+	  (:group)
 	 (_ (message "Unknown argument %s in defmap" key)))))
     (unless (keymapp m)
       (setq bs (append m bs))
diff --git a/lisp/emacs-lisp/easymenu.el b/lisp/emacs-lisp/easymenu.el
index 94d035f374..403829ac46 100644
--- a/lisp/emacs-lisp/easymenu.el
+++ b/lisp/emacs-lisp/easymenu.el
@@ -226,14 +226,14 @@ easy-menu-create-menu
       (let ((arg (cadr menu-items)))
         (setq menu-items (cddr menu-items))
         (pcase keyword
-          (`:filter
+          (:filter
            (setq filter (lambda (menu)
                           (easy-menu-filter-return (funcall arg menu)
                                                    menu-name))))
-          ((or `:enable `:active) (setq enable (or arg ''nil)))
-          (`:label (setq label arg))
-          (`:help (setq help arg))
-          ((or `:included `:visible) (setq visible (or arg ''nil))))))
+          ((or :enable :active) (setq enable (or arg ''nil)))
+          (:label (setq label arg))
+          (:help (setq help arg))
+          ((or :included :visible) (setq visible (or arg ''nil))))))
     (if (equal visible ''nil)
 	nil				; Invisible menu entry, return nil.
       (if (and visible (not (easy-menu-always-true-p visible)))
@@ -325,15 +325,15 @@ easy-menu-convert-item-1
 		(setq arg (aref item (1+ count)))
 		(setq count (+ 2 count))
 		(pcase keyword
-                  ((or `:included `:visible) (setq visible (or arg ''nil)))
-                  (`:key-sequence (setq cache arg cache-specified t))
-                  (`:keys (setq keys arg no-name nil))
-                  (`:label (setq label arg))
-                  ((or `:active `:enable) (setq active (or arg ''nil)))
-                  (`:help (setq prop (cons :help (cons arg prop))))
-                  (`:suffix (setq suffix arg))
-                  (`:style (setq style arg))
-                  (`:selected (setq selected (or arg ''nil)))))
+                  ((or :included :visible) (setq visible (or arg ''nil)))
+                  (:key-sequence (setq cache arg cache-specified t))
+                  (:keys (setq keys arg no-name nil))
+                  (:label (setq label arg))
+                  ((or :active :enable) (setq active (or arg ''nil)))
+                  (:help (setq prop (cons :help (cons arg prop))))
+                  (:suffix (setq suffix arg))
+                  (:style (setq style arg))
+                  (:selected (setq selected (or arg ''nil)))))
 	      (if suffix
 		  (setq label
 			(if (stringp suffix)
diff --git a/lisp/emacs-lisp/eieio-core.el b/lisp/emacs-lisp/eieio-core.el
index e5ea33c003..e5c4f198f5 100644
--- a/lisp/emacs-lisp/eieio-core.el
+++ b/lisp/emacs-lisp/eieio-core.el
@@ -388,9 +388,9 @@ eieio-defclass-internal
 	;; Clean up the meaning of protection.
         (setq prot
               (pcase prot
-                ((or 'nil 'public ':public) nil)
-                ((or 'protected ':protected) 'protected)
-                ((or 'private ':private) 'private)
+                ((or 'nil 'public :public) nil)
+                ((or 'protected :protected) 'protected)
+                ((or 'private :private) 'private)
                 (_ (signal 'invalid-slot-type (list :protection prot)))))
 
 	;; The default type specifier is supposed to be t, meaning anything.
diff --git a/lisp/emacs-lisp/package.el b/lisp/emacs-lisp/package.el
index 9c4c3e9fe7..f2ffef8da7 100644
--- a/lisp/emacs-lisp/package.el
+++ b/lisp/emacs-lisp/package.el
@@ -2911,17 +2911,17 @@ package-menu--print-info-simple
 Return (PKG-DESC [NAME VERSION STATUS DOC])."
   (let* ((status  (package-desc-status pkg))
          (face (pcase status
-                 (`"built-in"  'package-status-built-in)
-                 (`"external"  'package-status-external)
-                 (`"available" 'package-status-available)
-                 (`"avail-obso" 'package-status-avail-obso)
-                 (`"new"       'package-status-new)
-                 (`"held"      'package-status-held)
-                 (`"disabled"  'package-status-disabled)
-                 (`"installed" 'package-status-installed)
-                 (`"dependency" 'package-status-dependency)
-                 (`"unsigned"  'package-status-unsigned)
-                 (`"incompat"  'package-status-incompat)
+                 ("built-in"  'package-status-built-in)
+                 ("external"  'package-status-external)
+                 ("available" 'package-status-available)
+                 ("avail-obso" 'package-status-avail-obso)
+                 ("new"       'package-status-new)
+                 ("held"      'package-status-held)
+                 ("disabled"  'package-status-disabled)
+                 ("installed" 'package-status-installed)
+                 ("dependency" 'package-status-dependency)
+                 ("unsigned"  'package-status-unsigned)
+                 ("incompat"  'package-status-incompat)
                  (_            'font-lock-warning-face)))) ; obsolete.
     (list pkg
           `[(,(symbol-name (package-desc-name pkg))
diff --git a/lisp/emacs-lisp/smie.el b/lisp/emacs-lisp/smie.el
index c01a40172b..4b82172984 100644
--- a/lisp/emacs-lisp/smie.el
+++ b/lisp/emacs-lisp/smie.el
@@ -1856,9 +1856,9 @@ smie-setup
     (let ((k (pop keywords))
           (v (pop keywords)))
       (pcase k
-        (`:forward-token
+        (:forward-token
          (set (make-local-variable 'smie-forward-token-function) v))
-        (`:backward-token
+        (:backward-token
          (set (make-local-variable 'smie-backward-token-function) v))
         (_ (message "smie-setup: ignoring unknown keyword %s" k)))))
   (let ((ca (cdr (assq :smie-closer-alist grammar))))
diff --git a/lisp/faces.el b/lisp/faces.el
index 18b821a0b6..a8c1546d5a 100644
--- a/lisp/faces.el
+++ b/lisp/faces.el
@@ -1084,27 +1084,27 @@ face-valid-attribute-values
 an integer value."
   (let ((valid
          (pcase attribute
-           (`:family
+           (:family
             (if (window-system frame)
                 (mapcar (lambda (x) (cons x x))
                         (font-family-list))
 	      ;; Only one font on TTYs.
 	      (list (cons "default" "default"))))
-           (`:foundry
+           (:foundry
 	    (list nil))
-	   (`:width
+	   (:width
 	    (mapcar #'(lambda (x) (cons (symbol-name (aref x 1)) (aref x 1)))
 		    font-width-table))
-           (`:weight
+           (:weight
 	    (mapcar #'(lambda (x) (cons (symbol-name (aref x 1)) (aref x 1)))
 		    font-weight-table))
-	   (`:slant
+	   (:slant
 	    (mapcar #'(lambda (x) (cons (symbol-name (aref x 1)) (aref x 1)))
 		    font-slant-table))
-	   (`:inverse-video
+	   (:inverse-video
 	    (mapcar #'(lambda (x) (cons (symbol-name x) x))
 		    (internal-lisp-face-attribute-values attribute)))
-           ((or `:underline `:overline `:strike-through `:box)
+           ((or :underline :overline :strike-through :box)
             (if (window-system frame)
                 (nconc (mapcar #'(lambda (x) (cons (symbol-name x) x))
                                (internal-lisp-face-attribute-values attribute))
@@ -1112,12 +1112,12 @@ face-valid-attribute-values
                                (defined-colors frame)))
 	      (mapcar #'(lambda (x) (cons (symbol-name x) x))
 		      (internal-lisp-face-attribute-values attribute))))
-           ((or `:foreground `:background)
+           ((or :foreground :background)
             (mapcar #'(lambda (c) (cons c c))
                     (defined-colors frame)))
-           (`:height
+           (:height
             'integerp)
-           (`:stipple
+           (:stipple
             (and (memq (window-system frame) '(x ns)) ; No stipple on w32
                  (mapcar #'list
                          (apply #'nconc
@@ -1126,7 +1126,7 @@ face-valid-attribute-values
                                                (file-directory-p dir)
                                                (directory-files dir)))
                                         x-bitmap-file-path)))))
-           (`:inherit
+           (:inherit
             (cons '("none" . nil)
                   (mapcar #'(lambda (c) (cons (symbol-name c) c))
                           (face-list))))
diff --git a/lisp/filesets.el b/lisp/filesets.el
index c1e6ef10d5..8ccfa570e3 100644
--- a/lisp/filesets.el
+++ b/lisp/filesets.el
@@ -1559,7 +1559,7 @@ filesets-file-close
 (defun filesets-get-fileset-from-name (name &optional mode)
   "Get fileset definition for NAME."
   (pcase mode
-    ((or `:ingroup `:tree) name)
+    ((or :ingroup :tree) name)
     (_ (assoc name filesets-data))))
 
 
diff --git a/lisp/progmodes/modula2.el b/lisp/progmodes/modula2.el
index 582e495a2b..ef12352457 100644
--- a/lisp/progmodes/modula2.el
+++ b/lisp/progmodes/modula2.el
@@ -232,11 +232,11 @@ m2-smie-refine-semi
 ;; FIXME: "^." are two tokens, not one.
 (defun m2-smie-forward-token ()
   (pcase (smie-default-forward-token)
-    (`"VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
-    (`"CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
-    (`";" (save-excursion (m2-smie-refine-semi)))
-    (`"OF" (save-excursion (forward-char -2) (m2-smie-refine-of)))
-    (`":" (save-excursion (forward-char -1) (m2-smie-refine-colon)))
+    ("VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
+    ("CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
+    (";" (save-excursion (m2-smie-refine-semi)))
+    ("OF" (save-excursion (forward-char -2) (m2-smie-refine-of)))
+    (":" (save-excursion (forward-char -1) (m2-smie-refine-colon)))
     ;; (`"END" (if (and (looking-at "[ \t\n]*\\(\\(?:\\sw\\|\\s_\\)+\\)")
     ;;                  (not (assoc (match-string 1) m2-smie-grammar)))
     ;;             "END-proc" "END"))
@@ -244,11 +244,11 @@ m2-smie-forward-token
 
 (defun m2-smie-backward-token ()
   (pcase (smie-default-backward-token)
-    (`"VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
-    (`"CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
-    (`";" (save-excursion (forward-char 1) (m2-smie-refine-semi)))
-    (`"OF" (save-excursion (m2-smie-refine-of)))
-    (`":" (save-excursion (m2-smie-refine-colon)))
+    ("VAR" (if (zerop (car (syntax-ppss))) "VAR" "VAR-arg"))
+    ("CONST" (if (zerop (car (syntax-ppss))) "CONST" "CONST-arg"))
+    (";" (save-excursion (forward-char 1) (m2-smie-refine-semi)))
+    ("OF" (save-excursion (m2-smie-refine-of)))
+    (":" (save-excursion (m2-smie-refine-colon)))
     ;; (`"END" (if (and (looking-at "\\sw+[ \t\n]+\\(\\(?:\\sw\\|\\s_\\)+\\)")
     ;;                  (not (assoc (match-string 1) m2-smie-grammar)))
     ;;             "END-proc" "END"))
@@ -272,7 +272,7 @@ m2-smie-rules
   (pcase (cons kind token)
     (`(:elem . basic) m2-indent)
     (`(:after . ":=") (or m2-indent smie-indent-basic))
-    (`(:after . ,(or `"CONST" `"VAR" `"TYPE"))
+    (`(:after . ,(or "CONST" "VAR" "TYPE"))
      (or m2-indent smie-indent-basic))
     ;; (`(:before . ,(or `"VAR" `"TYPE" `"CONST"))
     ;;  (if (smie-rule-parent-p "PROCEDURE") 0))
diff --git a/lisp/progmodes/octave.el b/lisp/progmodes/octave.el
index 13510eef80..cce5e17e79 100644
--- a/lisp/progmodes/octave.el
+++ b/lisp/progmodes/octave.el
@@ -1065,8 +1065,8 @@ octave-goto-function-definition
              (unless found (goto-char orig))
              found))))
     (pcase (and buffer-file-name (file-name-extension buffer-file-name))
-      (`"cc" (funcall search
-                      "\\_<DEFUN\\(?:_DLD\\)?\\s-*(\\s-*\\(\\(?:\\sw\\|\\s_\\)+\\)" 1))
+      ("cc" (funcall search
+                     "\\_<DEFUN\\(?:_DLD\\)?\\s-*(\\s-*\\(\\(?:\\sw\\|\\s_\\)+\\)" 1))
       (_ (funcall search octave-function-header-regexp 3)))))
 
 (defun octave-function-file-p ()
@@ -1135,19 +1135,19 @@ octave-sync-function-file-names
                       (read-char-choice
                        "Which name to use? (a/b/q) " '(?a ?b ?q))))))
           (pcase c
-            (`?a (let ((newname (expand-file-name
-                                 (concat func (file-name-extension
-                                               buffer-file-name t)))))
-                   (when (or (not (file-exists-p newname))
-                             (yes-or-no-p
-                              (format "Target file %s exists; proceed? " newname)))
-                     (when (file-exists-p buffer-file-name)
-                       (rename-file buffer-file-name newname t))
-                     (set-visited-file-name newname))))
-            (`?b (save-excursion
-                   (goto-char name-start)
-                   (delete-region name-start name-end)
-                   (insert file)))))))))
+            (?a (let ((newname (expand-file-name
+                                (concat func (file-name-extension
+                                              buffer-file-name t)))))
+                  (when (or (not (file-exists-p newname))
+                            (yes-or-no-p
+                             (format "Target file %s exists; proceed? " newname)))
+                    (when (file-exists-p buffer-file-name)
+                      (rename-file buffer-file-name newname t))
+                    (set-visited-file-name newname))))
+            (?b (save-excursion
+                  (goto-char name-start)
+                  (delete-region name-start name-end)
+                  (insert file)))))))))
 
 (defun octave-update-function-file-comment (beg end)
   "Query replace function names in function file comment."
@@ -1801,19 +1801,19 @@ octave-find-definition-filename-function
 (defun octave-find-definition-default-filename (name)
   "Default value for `octave-find-definition-filename-function'."
   (pcase (file-name-extension name)
-    (`"oct"
+    ("oct"
      (octave-find-definition-default-filename
       (concat "libinterp/dldfcn/"
               (file-name-sans-extension (file-name-nondirectory name))
               ".cc")))
-    (`"cc"
+    ("cc"
      (let ((file (or (locate-file name (octave-source-directories))
                      (locate-file (file-name-nondirectory name)
                                   (octave-source-directories)))))
        (or (and file (file-exists-p file))
            (error "File `%s' not found" name))
        file))
-    (`"mex"
+    ("mex"
      (if (yes-or-no-p (format-message "File `%s' may be binary; open? "
 				      (file-name-nondirectory name)))
          name
diff --git a/lisp/progmodes/opascal.el b/lisp/progmodes/opascal.el
index 4606621951..7d055b735d 100644
--- a/lisp/progmodes/opascal.el
+++ b/lisp/progmodes/opascal.el
@@ -393,17 +393,17 @@ opascal-literal-kind
         (if (null (nth 8 ppss))
             (when (looking-at opascal--literal-start-re)
               (pcase (char-after)
-                (`?/  'comment-single-line)
-                (`?\{ 'comment-multi-line-1)
-                (`?\( 'comment-multi-line-2)
-                (`?\' 'string)
-                (`?\" 'double-quoted-string)))
+                (?/  'comment-single-line)
+                (?\{ 'comment-multi-line-1)
+                (?\( 'comment-multi-line-2)
+                (?\' 'string)
+                (?\" 'double-quoted-string)))
           (if (nth 3 ppss)   ;String.
               (if (eq (nth 3 ppss) ?\")
                   'double-quoted-string 'string)
             (pcase (nth 7 ppss)
-              (`2 'comment-single-line)
-              (`1 'comment-multi-line-2)
+              (2 'comment-single-line)
+              (1 'comment-multi-line-2)
               (_  'comment-multi-line-1))))))))
 
 (defun opascal-literal-start-pattern (literal-kind)
diff --git a/lisp/progmodes/perl-mode.el b/lisp/progmodes/perl-mode.el
index b96aad7a6e..a61d1adcb7 100644
--- a/lisp/progmodes/perl-mode.el
+++ b/lisp/progmodes/perl-mode.el
@@ -323,8 +323,8 @@ perl-syntax-propertize-function
               (cons (car (string-to-syntax "< c"))
                     ;; Remember the names of heredocs found on this line.
                     (cons (cons (pcase (aref name 0)
-                                  (`?\\ (substring name 1))
-                                  ((or `?\" `?\' `?\`) (substring name 1 -1))
+                                  (?\\ (substring name 1))
+                                  ((or ?\" ?\' ?\`) (substring name 1 -1))
                                   (_ name))
                                 indented)
                           (cdr st)))))))
diff --git a/lisp/progmodes/prolog.el b/lisp/progmodes/prolog.el
index 3bcc9bebcd..b530c61f97 100644
--- a/lisp/progmodes/prolog.el
+++ b/lisp/progmodes/prolog.el
@@ -954,9 +954,9 @@ prolog-smie-rules
     ;;    ->  thenrule
     ;;    ;   elserule
     ;;    )
-    (`(:before . ,(or `"->" `";"))
+    (`(:before . ,(or "->" ";"))
      (and (smie-rule-bolp) (smie-rule-parent-p "(") (smie-rule-parent 0)))
-    (`(:after . ,(or `"->" `"*->"))
+    (`(:after . ,(or "->" "*->"))
      ;; We distinguish
      ;;
      ;;     (a ->
@@ -3247,11 +3247,11 @@ prolog-electric--underscore
 
 (defun prolog-post-self-insert ()
   (pcase last-command-event
-    (`?_ (prolog-electric--underscore))
-    (`?- (prolog-electric--dash))
-    (`?: (prolog-electric--colon))
-    ((or `?\( `?\; `?>) (prolog-electric--if-then-else))
-    (`?. (prolog-electric--dot))))
+    (?_ (prolog-electric--underscore))
+    (?- (prolog-electric--dash))
+    (?: (prolog-electric--colon))
+    ((or ?\( ?\; ?>) (prolog-electric--if-then-else))
+    (?. (prolog-electric--dot))))
 
 (defun prolog-find-term (functor arity &optional prefix)
   "Go to the position at the start of the next occurrence of a term.
diff --git a/lisp/progmodes/ruby-mode.el b/lisp/progmodes/ruby-mode.el
index fad7bc1fb8..32130cee8e 100644
--- a/lisp/progmodes/ruby-mode.el
+++ b/lisp/progmodes/ruby-mode.el
@@ -612,7 +612,7 @@ ruby-smie-rules
       ;; For (invalid) code between switch and case.
       ;; (if (smie-parent-p "switch") 4)
       ))
-    (`(:before . ,(or `"(" `"[" `"{"))
+    (`(:before . ,(or "(" "[" "{"))
      (cond
       ((and (equal token "{")
             (not (smie-rule-prev-p "(" "{" "[" "," "=>" "=" "return" ";"))
@@ -639,7 +639,7 @@ ruby-smie-rules
            (forward-char -1))
          (smie-indent-virtual))
         (t (smie-rule-parent))))))
-    (`(:after . ,(or `"(" "[" "{"))
+    (`(:after . ,(or "(" "[" "{"))
      ;; FIXME: Shouldn't this be the default behavior of
      ;; `smie-indent-after-keyword'?
      (save-excursion
@@ -660,7 +660,7 @@ ruby-smie-rules
        (smie-backward-sexp ".")
        (cons 'column (+ (current-column)
                         ruby-indent-level))))
-    (`(:before . ,(or `"else" `"then" `"elsif" `"rescue" `"ensure"))
+    (`(:before . ,(or "else" "then" "elsif" "rescue" "ensure"))
      (smie-rule-parent))
     (`(:before . "when")
      ;; Align to the previous `when', but look up the virtual
@@ -1544,8 +1544,8 @@ ruby-backward-sexp
             (cond ((looking-at "\\s)")
                    (goto-char (scan-sexps (1+ (point)) -1))
                    (pcase (char-before)
-                     (`?% (forward-char -1))
-                     ((or `?q `?Q `?w `?W `?r `?x)
+                     (?% (forward-char -1))
+                     ((or ?q ?Q ?w ?W ?r ?x)
                       (if (eq (char-before (1- (point))) ?%)
                           (forward-char -2))))
                    nil)
@@ -1562,13 +1562,13 @@ ruby-backward-sexp
                    (forward-char 1)
                    (while (progn (forward-word-strictly -1)
                                  (pcase (char-before)
-                                   (`?_ t)
-                                   (`?. (forward-char -1) t)
-                                   ((or `?$ `?@)
+                                   (?_ t)
+                                   (?. (forward-char -1) t)
+                                   ((or ?$ ?@)
                                     (forward-char -1)
                                     (and (eq (char-before) (char-after))
                                          (forward-char -1)))
-                                   (`?:
+                                   (?:
                                     (forward-char -1)
                                     (eq (char-before) :)))))
                    (if (looking-at ruby-block-end-re)
diff --git a/lisp/progmodes/sh-script.el b/lisp/progmodes/sh-script.el
index aaa86b5816..46c9e6ee65 100644
--- a/lisp/progmodes/sh-script.el
+++ b/lisp/progmodes/sh-script.el
@@ -959,8 +959,8 @@ sh--inside-noncommand-expression
            ;; ((...)) or $((...)) or $[...] or ${...}. Nested
            ;; parenthesis can occur inside the first of these forms, so
            ;; parse backward recursively.
-           (`?\( (eq ?\( (char-before)))
-           ((or `?\{ `?\[) (eq ?\$ (char-before))))
+           (?\( (eq ?\( (char-before)))
+           ((or ?\{ ?\[) (eq ?\$ (char-before))))
          (sh--inside-noncommand-expression (1- (point))))))))
 
 (defun sh-font-lock-open-heredoc (start string eol)
@@ -2038,7 +2038,7 @@ sh-smie-sh-rules
     (`(:elem . basic) sh-basic-offset)
     (`(:after . "case-)") (- (sh-var-value 'sh-indent-for-case-alt)
                              (sh-var-value 'sh-indent-for-case-label)))
-    (`(:before . ,(or `"(" `"{" `"[" "while" "if" "for" "case"))
+    (`(:before . ,(or "(" "{" "[" "while" "if" "for" "case"))
      (if (not (smie-rule-prev-p "&&" "||" "|"))
          (when (smie-rule-hanging-p)
            (smie-rule-parent))
@@ -2047,11 +2047,11 @@ sh-smie-sh-rules
 	 `(column . ,(smie-indent-virtual)))))
     ;; FIXME: Maybe this handling of ;; should be made into
     ;; a smie-rule-terminator function that takes the substitute ";" as arg.
-    (`(:before . ,(or `";;" `";&" `";;&"))
+    (`(:before . ,(or ";;" ";&" ";;&"))
      (if (and (smie-rule-bolp) (looking-at ";;?&?[ \t]*\\(#\\|$\\)"))
          (cons 'column (smie-indent-keyword ";"))
        (smie-rule-separator kind)))
-    (`(:after . ,(or `";;" `";&" `";;&"))
+    (`(:after . ,(or ";;" ";&" ";;&"))
      (with-demoted-errors
        (smie-backward-sexp token)
        (cons 'column
@@ -2062,7 +2062,7 @@ sh-smie-sh-rules
                             (smie-rule-bolp))))
                  (current-column)
                (smie-indent-calculate)))))
-    (`(:before . ,(or `"|" `"&&" `"||"))
+    (`(:before . ,(or "|" "&&" "||"))
      (unless (smie-rule-parent-p token)
        (smie-backward-sexp token)
        `(column . ,(+ (funcall smie-rules-function :elem 'basic)
@@ -2081,7 +2081,7 @@ sh-smie-sh-rules
     ;; sh-indent-after-done: aligned completely differently.
     (`(:after . "in") (sh-var-value 'sh-indent-for-case-label))
     ;; sh-indent-for-continuation: Line continuations are handled differently.
-    (`(:after . ,(or `"(" `"{" `"["))
+    (`(:after . ,(or "(" "{" "["))
      (if (not (looking-at ".[ \t]*[^\n \t#]"))
          (sh-var-value 'sh-indent-after-open)
        (goto-char (1- (match-end 0)))
@@ -2253,7 +2253,7 @@ sh-smie-rc-rules
      (save-excursion
        (when (sh-smie--rc-after-special-arg-p)
          `(column . ,(current-column)))))
-    (`(:before . ,(or `"(" `"{" `"["))
+    (`(:before . ,(or "(" "{" "["))
      (if (smie-rule-hanging-p) (smie-rule-parent)))
     ;; FIXME: SMIE parses "if (exp) cmd" as "(if ((exp) cmd))" so "cmd" is
     ;; treated as an arg to (exp) by default, which indents it all wrong.
@@ -2262,7 +2262,7 @@ sh-smie-rc-rules
     ;; rule we have is the :list-intro hack, which we use here to align "cmd"
     ;; with "(exp)", which is rarely the right thing to do, but is better
     ;; than nothing.
-    (`(:list-intro . ,(or `"for" `"if" `"while")) t)
+    (`(:list-intro . ,(or "for" "if" "while")) t)
     ;; sh-indent-after-switch: handled implicitly by the default { rule.
     ))
 
diff --git a/lisp/server.el b/lisp/server.el
index 50684a20aa..d0a8ca313e 100644
--- a/lisp/server.el
+++ b/lisp/server.el
@@ -1112,16 +1112,16 @@ server-execute-continuation
 	    (while args-left
               (pcase (pop args-left)
                 ;; -version CLIENT-VERSION: obsolete at birth.
-                (`"-version" (pop args-left))
+                ("-version" (pop args-left))
 
                 ;; -nowait:  Emacsclient won't wait for a result.
-                (`"-nowait" (setq nowait t))
+                ("-nowait" (setq nowait t))
 
                 ;; -current-frame:  Don't create frames.
-                (`"-current-frame" (setq use-current-frame t))
+                ("-current-frame" (setq use-current-frame t))
 
                 ;; -frame-parameters: Set frame parameters
-                (`"-frame-parameters"
+                ("-frame-parameters"
                  (let ((alist (pop args-left)))
                    (if coding-system
                        (setq alist (decode-coding-string alist coding-system)))
@@ -1129,24 +1129,24 @@ server-execute-continuation
 
                 ;; -display DISPLAY:
                 ;; Open X frames on the given display instead of the default.
-                (`"-display"
+                ("-display"
                  (setq display (pop args-left))
                  (if (zerop (length display)) (setq display nil)))
 
                 ;; -parent-id ID:
                 ;; Open X frame within window ID, via XEmbed.
-                (`"-parent-id"
+                ("-parent-id"
                  (setq parent-id (pop args-left))
                  (if (zerop (length parent-id)) (setq parent-id nil)))
 
                 ;; -window-system:  Open a new X frame.
-                (`"-window-system"
+                ("-window-system"
 		 (if (fboundp 'x-create-frame)
 		     (setq dontkill t
 			   tty-name 'window-system)))
 
                 ;; -resume:  Resume a suspended tty frame.
-                (`"-resume"
+                ("-resume"
                  (let ((terminal (process-get proc 'terminal)))
                    (setq dontkill t)
                    (push (lambda ()
@@ -1157,7 +1157,7 @@ server-execute-continuation
                 ;; -suspend:  Suspend the client's frame.  (In case we
                 ;; get out of sync, and a C-z sends a SIGTSTP to
                 ;; emacsclient.)
-                (`"-suspend"
+                ("-suspend"
                  (let ((terminal (process-get proc 'terminal)))
                    (setq dontkill t)
                    (push (lambda ()
@@ -1167,13 +1167,13 @@ server-execute-continuation
 
                 ;; -ignore COMMENT:  Noop; useful for debugging emacsclient.
                 ;; (The given comment appears in the server log.)
-                (`"-ignore"
+                ("-ignore"
                  (setq dontkill t)
                  (pop args-left))
 
 		;; -tty DEVICE-NAME TYPE:  Open a new tty frame.
 		;; (But if we see -window-system later, use that.)
-                (`"-tty"
+                ("-tty"
                  (setq tty-name (pop args-left)
                        tty-type (pop args-left)
                        dontkill (or dontkill
@@ -1192,7 +1192,7 @@ server-execute-continuation
 
                 ;; -position LINE[:COLUMN]:  Set point to the given
                 ;;  position in the next file.
-                (`"-position"
+                ("-position"
                  (if (not (string-match "\\+\\([0-9]+\\)\\(?::\\([0-9]+\\)\\)?"
                                         (car args-left)))
                      (error "Invalid -position command in client args"))
@@ -1203,7 +1203,7 @@ server-execute-continuation
                                                      ""))))))
 
                 ;; -file FILENAME:  Load the given file.
-                (`"-file"
+                ("-file"
                  (let ((file (pop args-left)))
                    (if coding-system
                        (setq file (decode-coding-string file coding-system)))
@@ -1221,7 +1221,7 @@ server-execute-continuation
                  (setq filepos nil))
 
                 ;; -eval EXPR:  Evaluate a Lisp expression.
-                (`"-eval"
+                ("-eval"
                  (if use-current-frame
                      (setq use-current-frame 'always))
                  (let ((expr (pop args-left)))
@@ -1232,14 +1232,14 @@ server-execute-continuation
                    (setq filepos nil)))
 
                 ;; -env NAME=VALUE:  An environment variable.
-                (`"-env"
+                ("-env"
                  (let ((var (pop args-left)))
                    ;; XXX Variables should be encoded as in getenv/setenv.
                    (process-put proc 'env
                                 (cons var (process-get proc 'env)))))
 
                 ;; -dir DIRNAME:  The cwd of the emacsclient process.
-                (`"-dir"
+                ("-dir"
                  (setq dir (pop args-left))
                  (if coding-system
                      (setq dir (decode-coding-string dir coding-system)))
diff --git a/lisp/subr.el b/lisp/subr.el
index 41dc9aa45f..aaf8909e0c 100644
--- a/lisp/subr.el
+++ b/lisp/subr.el
@@ -4815,7 +4815,7 @@ called-interactively-p
                           i frame nextframe)))
                (pcase skip
                  (`nil nil)
-                 (`0 t)
+                 (0 t)
                  (_ (setq i (+ i skip -1)) (funcall get-next-frame)))))))
       ;; Now `frame' should be "the function from which we were called".
       (pcase (cons frame nextframe)
diff --git a/lisp/textmodes/css-mode.el b/lisp/textmodes/css-mode.el
index 31ce638b31..63c86317ee 100644
--- a/lisp/textmodes/css-mode.el
+++ b/lisp/textmodes/css-mode.el
@@ -1219,7 +1219,7 @@ css-smie-rules
     (`(:elem . basic) css-indent-offset)
     (`(:elem . arg) 0)
     ;; "" stands for BOB (bug#15467).
-    (`(:list-intro . ,(or `";" `"" `":-property")) t)
+    (`(:list-intro . ,(or ";" "" ":-property")) t)
     (`(:before . "{")
      (when (or (smie-rule-hanging-p) (smie-rule-bolp))
        (smie-backward-sexp ";")
diff --git a/test/lisp/emacs-lisp/pcase-tests.el b/test/lisp/emacs-lisp/pcase-tests.el
index 774a488255..c706c1051e 100644
--- a/test/lisp/emacs-lisp/pcase-tests.el
+++ b/test/lisp/emacs-lisp/pcase-tests.el
@@ -53,7 +53,7 @@ pcase-tests-grep
   (should (pcase-tests-grep
            'memq (macroexpand-all '(pcase x ((or 1 2 3) body)))))
   (should (pcase-tests-grep
-           'member (macroexpand-all '(pcase x ((or '"a" '2 '3) body)))))
+           'member (macroexpand-all '(pcase x ((or "a" 2 3) body)))))
   (should-not (pcase-tests-grep
                'memq (macroexpand-all '(pcase x ((or "a" 2 3) body)))))
   (let ((exp (macroexpand-all
-- 
2.19.1


[-- Attachment #3: Type: text/plain, Size: 20 bytes --]



Thanks,

Michael.

^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:08                                                                                         ` Stefan Monnier
@ 2018-10-29 21:53                                                                                           ` Michael Heerdegen
  2018-10-29 23:12                                                                                             ` Eric Abrahamsen
  2018-10-30  1:15                                                                                           ` Garreau, Alexandre
                                                                                                             ` (3 subsequent siblings)
  4 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-29 21:53 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Stefan Monnier <monnier@iro.umontreal.ca> writes:

> I'd rather keep it defined in terms of its differences w.r.t `dolist`,
> but if really needed, we could change the doc so it doesn't rely on
> `dolist`s own doc at all.

I also don't think that would be an improvement.

> +As in the case of `pcase-let', PATTERN is matched under the
> assumption +that it *will* match.

What this leaves a bit unclear: It sounds like matching itself happens
differently (user visibly).  Or does it just mean "if PATTERN doesn't
match, the behavior [of pcase-dolist] is undefined/ this is not
allowed".


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-29 21:33                                                                                                 ` Michael Heerdegen
@ 2018-10-29 23:00                                                                                                   ` Garreau, Alexandre
  2018-10-29 23:57                                                                                                     ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-29 23:00 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

Le 29/10/2018 à 22h33, Michael Heerdegen a écrit :
> "Garreau, Alexandre" <galex-713@galex-713.eu> writes:
>
>> Even in pcase I don’t see how to do that except manually using (and var
>> (guard (equal var val))),
>
> You mean like (pred (equal val))?

Oh indeed!  Still that defeat the purpose of pattern matching by
requiring non-pattern matching stuff.

>> #+begin_src emacs-lisp
>> (pcase-defmacro list (&rest args)
>>   `(,'\`  ,(mapcar (lambda (thing) `(,'\, ,thing)) args)))
>> #+end_src
>>
>> I tried to adapt for arrays:
>>
>> #+begin_src emacs-lisp
>> (pcase-defmacro array (&rest args)
>>   `[,'\` ,(mapcar (lambda (thing) `(,'\, ,thing)) args)])
>> #+end_src
>
>> But it doesn’t work x), that, plus my initial non-working
>> “(pcase-defmacro list (&rest args) ``(,@args))”, I must find “`”, is,
>> indeed, quite confusing (how is “,'” needed? how isn’t “,'\`” equivalent
>> to “\`”?),
>
> You want , to survive til after the macro expansion.  Backquote can't
> know that it should ignore a , because you want it to be literally in
> the expansion.  ,'\` let's backquote insert a literal , into the
> expansion, which is what you want.  The underlying problem is that you
> want to use (of course you don't have to!) backquote to construct a
> backquote expression.  That happens here and there when writing Lisp,
> it's not something special to pcase.

Yes I know, what I meant is `, in lisp, can generally lead to confusion
unexperimented programmer.  That’s one of the selling points of hygienic
macros (standard and default in scheme).

The fact pcase is not strictly treating ` as standard lisp’s reader does
is only *adding* the the already existing confusion normal and standard
` introduces in lisp.

> For understanding the definition above note that ``' (synonymous for
> `backquote') is a (very normal) macro accepting one argument STRUCTURE,
> whereby we also have an abbreviating reader syntax
> `STRUCTURE == (` STRUCTURE).  We also have the reader syntax
> ,THING == (, THING).

Indeed you’re right, but that doesn’t automagically explain to me how
does exactely work the “,” macro, as it stays context dependant, not
trivial, and to me, “,” meant either “eval” or “undo ‘`’” (the later is
nearer to the meaning used in pcase btw).

> Your pcase macro `array' could be defined like
>
> #+begin_src emacs-lisp
> (pcase-defmacro array (&rest args)
>   `(,'\` [,@(mapcar (lambda (thing) `(,'\, ,thing)) args)]))
> #+end_src
>
> You could also write that without backquote (and also without the []
> reader syntax).

Ah okkkk!  Backquotes may be difficult or confusing to master fully, but
at least they’re consistent and simple enough to stay readable, I find,
more easily than easily writable.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:53                                                                                           ` Michael Heerdegen
@ 2018-10-29 23:12                                                                                             ` Eric Abrahamsen
  2018-10-29 23:18                                                                                               ` Eric Abrahamsen
  2018-10-30 12:30                                                                                               ` Stefan Monnier
  0 siblings, 2 replies; 375+ messages in thread
From: Eric Abrahamsen @ 2018-10-29 23:12 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Stefan Monnier, emacs-devel

Michael Heerdegen <michael_heerdegen@web.de> writes:

> Stefan Monnier <monnier@iro.umontreal.ca> writes:
>
>> I'd rather keep it defined in terms of its differences w.r.t `dolist`,
>> but if really needed, we could change the doc so it doesn't rely on
>> `dolist`s own doc at all.
>
> I also don't think that would be an improvement.
>
>> +As in the case of `pcase-let', PATTERN is matched under the
>> assumption +that it *will* match.
>
> What this leaves a bit unclear: It sounds like matching itself happens
> differently (user visibly).  Or does it just mean "if PATTERN doesn't
> match, the behavior [of pcase-dolist] is undefined/ this is not
> allowed".

I wonder if the manual shouldn't have a section somewhere making
explicit the difference between `pcase' -- where a single value is
matched against many patterns, and may fail to match altogether, and
destructuring is only one of the use-cases -- and the other
pcase-derived forms, where many values are matched against a single
pattern, which *must* match (or error), and destructuring is kind of the
whole point. Conceptually, they're pretty different.

BTW I just looked at the new manual section for pcase -- that's much
better!

Eric



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 23:12                                                                                             ` Eric Abrahamsen
@ 2018-10-29 23:18                                                                                               ` Eric Abrahamsen
  2018-10-30  0:50                                                                                                 ` `pcase'/`case' implementation [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
  2018-10-30 13:07                                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
  2018-10-30 12:30                                                                                               ` Stefan Monnier
  1 sibling, 2 replies; 375+ messages in thread
From: Eric Abrahamsen @ 2018-10-29 23:18 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Stefan Monnier, emacs-devel

Eric Abrahamsen <eric@ericabrahamsen.net> writes:

> Michael Heerdegen <michael_heerdegen@web.de> writes:
>
>> Stefan Monnier <monnier@iro.umontreal.ca> writes:
>>
>>> I'd rather keep it defined in terms of its differences w.r.t `dolist`,
>>> but if really needed, we could change the doc so it doesn't rely on
>>> `dolist`s own doc at all.
>>
>> I also don't think that would be an improvement.
>>
>>> +As in the case of `pcase-let', PATTERN is matched under the
>>> assumption +that it *will* match.
>>
>> What this leaves a bit unclear: It sounds like matching itself happens
>> differently (user visibly).  Or does it just mean "if PATTERN doesn't
>> match, the behavior [of pcase-dolist] is undefined/ this is not
>> allowed".
>
> I wonder if the manual shouldn't have a section somewhere making
> explicit the difference between `pcase' -- where a single value is
> matched against many patterns, and may fail to match altogether, and
> destructuring is only one of the use-cases -- and the other
> pcase-derived forms, where many values are matched against a single
> pattern, which *must* match (or error), and destructuring is kind of the
> whole point. Conceptually, they're pretty different.

In fact, when you think about it, the "case" nature of pcase is pretty
orthogonal to the "match/destructure" nature of pcase. If anything
fairly fundamental were to be done to refactor pcase, I wonder if it
shouldn't be to separate these two concerns. In a sense, we already have
`cl-case', why would we need another case-like structure? All we really
need are new _matching forms_, which could be used within `cl-case',
`dolist', `lambda'...



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-29 23:00                                                                                                   ` pcase ` meaning Garreau, Alexandre
@ 2018-10-29 23:57                                                                                                     ` Michael Heerdegen
  2018-10-30  0:17                                                                                                       ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-29 23:57 UTC (permalink / raw)
  To: Garreau, Alexandre
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> > You mean like (pred (equal val))?
>
> Oh indeed!  Still that defeat the purpose of pattern matching by
> requiring non-pattern matching stuff.

What in that pattern is non-pattern matching stuff?

> The fact pcase is not strictly treating ` as standard lisp’s reader does
> is only *adding* the the already existing confusion normal and standard
> ` introduces in lisp.

` is a normal macro, it has nothing to do with the reader.  Apart from
the ` reader macro, which pcase doesn't touch at all.

What it does is to give ` different semantics inside patterns.  Like
your `list' pattern gives new semantics to the symbol `list'.  Oh my.

> > For understanding the definition above note that ``' (synonymous for
> > `backquote') is a (very normal) macro accepting one argument STRUCTURE,
> > whereby we also have an abbreviating reader syntax
> > `STRUCTURE == (` STRUCTURE).  We also have the reader syntax
> > ,THING == (, THING).
>
> Indeed you’re right, but that doesn’t automagically explain to me how
> does exactely work the “,” macro, as it stays context dependant, not
> trivial, and to me, “,” meant either “eval” or “undo ‘`’” (the later is
> nearer to the meaning used in pcase btw).

(, is not a macro, btw)  Well, in pcase patterns it "means" something
different.  As `and' means something different in `rx'.

You very often say that you expected something different.  I dunno what
I first expected, I read the docs to learn pcase, and it took 5 minutes.

I think we can agree that we disagree - I just don't share your
opinion.  The thing is designed in a way that it matches how some, but
not all people, like to think about pattern matching.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-29 23:57                                                                                                     ` Michael Heerdegen
@ 2018-10-30  0:17                                                                                                       ` Garreau, Alexandre
  2018-10-30  1:40                                                                                                         ` Michael Heerdegen
  2018-10-30 16:05                                                                                                         ` Yuri Khan
  0 siblings, 2 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-30  0:17 UTC (permalink / raw)
  To: Michael Heerdegen
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

On 2018/10/30 at 00:57, Michael Heerdegen wrote:
> "Garreau, Alexandre" <galex-713@galex-713.eu> writes:
>
>> > You mean like (pred (equal val))?
>>
>> Oh indeed!  Still that defeat the purpose of pattern matching by
>> requiring non-pattern matching stuff.
>
> What in that pattern is non-pattern matching stuff?

guards, pred, etc. are “pattern” in pcase parlance, but aren’t
pattern-matching in general sense: they are only a (handy) extra way to
specify arbitrary conditions in the middle of a pattern matching, in
addition to matching the *pattern*, that is a structure that mimick what
we want to match.

>> The fact pcase is not strictly treating ` as standard lisp’s reader does
>> is only *adding* the the already existing confusion normal and standard
>> ` introduces in lisp.
>
> ` is a normal macro, it has nothing to do with the reader.  Apart from
> the ` reader macro, which pcase doesn't touch at all.

They share a name, that’s enough.  And to me it seems that this name
sharing is here to (incompletely / incorrectly) borrow some of the
semantics of the ` reader macro.

> What it does is to give ` different semantics inside patterns.  Like
> your `list' pattern gives new semantics to the symbol `list'.  Oh my.

It’s not arbitrary random semantics, it base on the knowledge people
might have of “`”, and of its use along with “,”.  List, at the
opposite, is pure pattern matching, since it is used as a list
constructor, look:

(pcase (list 1 2 3) ((list 1 2 3) t))

It just looks *exactely* the same.

(pcase (list 1 2 3) ((list a b c) (+ a b c)))

And here it’s *almost* the same, beside identifiers, to be bound.

While:

(pcase `(1 2 3) (`(1 2 3) t))

look the same, as well as:

(pcase `(a b c) (`(a b c) t))

But not:

(pcase `(1 2 3) (`(,a ,b ,c) (+ a b c)))

>> > For understanding the definition above note that ``' (synonymous for
>> > `backquote') is a (very normal) macro accepting one argument STRUCTURE,
>> > whereby we also have an abbreviating reader syntax
>> > `STRUCTURE == (` STRUCTURE).  We also have the reader syntax
>> > ,THING == (, THING).
>>
>> Indeed you’re right, but that doesn’t automagically explain to me how
>> does exactely work the “,” macro, as it stays context dependant, not
>> trivial, and to me, “,” meant either “eval” or “undo ‘`’” (the later is
>> nearer to the meaning used in pcase btw).
>
> (, is not a macro, btw)  Well, in pcase patterns it "means" something
> different.  As `and' means something different in `rx'.

Yes.  A different meaning for `and', is acceptable, and the first time I
saw a complain about it I also immediatly thought to `rx'.  But if `and'
meaning change is acceptable it’s because “and” is already a word of
english with an abstract, independant, general meaning per se.  While
“`” is almost never used as in lisp, except as *real* quotes, that
match, as in `' in TeX (or docstrings), or `` in shellscript.

> You very often say that you expected something different.  I dunno what
> I first expected, I read the docs to learn pcase, and it took 5 minutes.

I sometimes exagerate in reguard to pcase understandability: I find its
syntax confusive because it is actually inconsistent with
outside-pcase-world, and I’m a perfectionist (that’s a defect that can
be workaround, still).

I do that because, though I’m not fond of pattern matching, I do think
sometimes it’s handy, useful or even necessary, and then I’d like pcase
to be the most easily understandable by the most possible people.

> I think we can agree that we disagree - I just don't share your
> opinion.  The thing is designed in a way that it matches how some, but
> not all people, like to think about pattern matching.

Not that much I believe: you were enthusiast as well about the `var'
pattern, and I’m pretty sure (and guess I’m not the only one) than
borrowing some patterns from other lisps pattern matching facilities may
allow less confusing pcase usages, as you initially wanted.

The one I’d push the harder, and find the most important, is (a b c)
(not quoted) to match a list, when no `a' pattern is defined, as it is
done in schemes’ match, and the most naive and simple common-lisp match.
Here I know pcase, currently, refuse it, but I didn’t yet hear people
talk against it, but I may expect to be a minority to want this, or at
least not to be a majority wanting it, or to have some people (Stefan?)
against it.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-29 17:26                                                                                             ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Clément Pit-Claudel
@ 2018-10-30  0:27                                                                                               ` Garreau, Alexandre
  2018-10-30 13:14                                                                                                 ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-30  0:27 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

On 2018-10-29 at 13:26, Clément Pit-Claudel wrote:
> On 28/10/2018 19.09, Garreau, Alexandre wrote:
>> the pattern look like what the data should be. adding “`” and “,”
>> destroy this feature, because the pattern no longer looks like what
>> is matched.
>
> Maybe it's a matter of perspective? Adding "`" and "," is precisely
> what makes the pattern look like the data: the invariant is that if
> you have a match, repeating the pattern produces the original data.

Oh, you mean “repeating *in the body*”?  Didn’t notice that.  Indeed,
this is something I didn’t notice: that’s making me way more comfortable
with “`” (as it is used this way in all schemes too, so its meaning
couldn’t and won’t be changed).

But normally, even if, as a side effect, pattern matching match in
appearance what it’d be if you wanted to repeat the pattern, repeated,
like here:

#+BEGIN_SRC emacs-lisp
  (pcase `(1 2 3) (`(,a ,b ,c) `(,a ,b ,c)))
#+END_SRC

(or may appear also as '(1 2 3), or (list 1 2 3))

#+BEGIN_SRC ocaml
  match [1;2;3] with [a;b;c] -> [a;b;c]
#+END_SRC

But this is a non-primordial side effect.  Notice how in the later case
the matched data *always* look the same as the pattern (beside replacing
a number per an identifier): *that’s* the purpose of pattern matching.
While in the lisp case you got those extra “,”.

Of course, these might not cause problem if, incidentally, you were to
use them in matched data too (but it’d be odd):

#+BEGIN_SRC emacs-lisp
  (pcase `(,x ,y ,z) (`(,a ,b ,c) `(,a ,b ,c)))
#+END_SRC

But that will rarely happen, as it is somewhat redundant.

> Here's a concrete example: (pcase '(1 2 3 4) (`(,x ,y . ,z) `(,x ,y
> . ,z))) is a no-op.  In other words, q-patterns are equations with
> multiple unknown variables (holes).  When you write a q-pattern,
> you're asking "what values should the variables in this pattern take
> so that evaluating the pattern would return the matched data?"

Normally, the pattern isn’t made related to the reuse of its var, but
related to the matched data, to look like it.  Only then, by
implication, you got it to look like what you would do to reconstruct it
in the body.

But that is a really interesting perspective I missed.  Thank you for
sharing it.  This is the kind of implicit “logical” intuitive ideas that
make designs meaningful that are kept unwritten, while they should, I
believe, be advertised so to explain why a specific design is handy or
natural (if ever newcomers found it unnatural).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* What `case' have done you? [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-29 21:46                                                                                   ` Michael Heerdegen
@ 2018-10-30  0:36                                                                                     ` Garreau, Alexandre
  2018-10-30  1:45                                                                                       ` Michael Heerdegen
  2018-10-30  6:31                                                                                     ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-30  0:36 UTC (permalink / raw)
  To: monnier, Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

On 2018-10-29 at 22:46, Michael Heerdegen wrote:
> +                      (?y (setq skip t))
> +                      (?q (keyboard-quit))

> +                      (?N (setq skip 'no))))))

> +	(:group (setq group (pop body)))
> +	(:abbrev-table (setq abbrev (pop body)) (setq declare-abbrev nil))
> +	(:syntax-table (setq syntax (pop body)) (setq declare-syntax nil))

> +                ((or 'nil 'public :public) nil)
> +                ((or 'protected :protected) 'protected)
> +                ((or 'private :private) 'private)

There are quite some (long) cases where only matching characters or
symbols: is it really that problematic to use `case' (though, in such
common functions body, I wouldn’t find cond+assoc natural either)?  I’m
uncomfortable to make elisp, like ocaml, the kind of language where if
you want the equivalent of a switch, etc. you’d need the pattern
matching facility.  That’s excessive promotion of pattern matching I
find.  And `case' wasn’t invented for no purpose: it already existed in
common lisp and many lisps, and would perfectly fit there, why
invisibilizing it so much, even for cases it works?  Why is everybody
banning so much that hard `case' from elisp common usage?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* `pcase'/`case' implementation [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-29 23:18                                                                                               ` Eric Abrahamsen
@ 2018-10-30  0:50                                                                                                 ` Garreau, Alexandre
  2018-10-30 13:07                                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
  1 sibling, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-30  0:50 UTC (permalink / raw)
  To: Eric Abrahamsen; +Cc: Michael Heerdegen, Stefan Monnier, emacs-devel

On 2018-10-29 at 16:18, Eric Abrahamsen wrote:
> Eric Abrahamsen <eric@ericabrahamsen.net> writes:
>> I wonder if the manual shouldn't have a section somewhere making
>> explicit the difference between `pcase' -- where a single value is
>> matched against many patterns, and may fail to match altogether, and
>> destructuring is only one of the use-cases -- and the other
>> pcase-derived forms, where many values are matched against a single
>> pattern, which *must* match (or error), and destructuring is kind of the
>> whole point. Conceptually, they're pretty different.
>
> In fact, when you think about it, the "case" nature of pcase is pretty
> orthogonal to the "match/destructure" nature of pcase. If anything
> fairly fundamental were to be done to refactor pcase, I wonder if it
> shouldn't be to separate these two concerns. In a sense, we already have
> `cl-case', why would we need another case-like structure? All we really
> need are new _matching forms_, which could be used within `cl-case',
> `dolist', `lambda'...

I also believe this.  We should, on one side, have a `match' function,
that would do more advanced destructuring than `cl-destructuring-bind'
(and, potentially, be based on it (so it could seeminglessly be used in
`pcase-lambda' on whole argument list), or the other way around, so
match returns an env (like other one-clause `match'), without having to
execute body, so to be more composable, and only then it would be used
in `cl-destructuring-bind' (which would then be accordingly more
powerful (but potentially incompatible in some corner cases (or more
than corner cases, if we don’t implement unquoted “(a . b)” where “a”
isn’t a predefined pattern, to match a cons)))), preferably based on it
(and potentially with an `unify' based on it).

Then, on another, I strongly believe we need a `case' struct that takes
a test function as an argument.  That test function might be `equal', so
that to make `case' generally more useful, but also `match', so now we
got a neat composition of two orthogonal and separate functions to make
a more complex one.  Then, we might tweak `case' so that to take the
result of the test function as an environment to be used for each BODY:
most test functions returns t, and in emacs, that’s already the void
environment referring to the global dynamical one, and `match' would
return what it bound.

Then `pcase' would simply be “case :test #'match” (like (setf pcase
(apply-partially #'case :test #'match)), but with its defun, docstring,
et al), get a simpler implementation, neat internal interfaces, and ends
that sort of sterile and useless implicit fight between `case' and
`pcase' (as they’re only two different levels).

I like minimalism, composition and reductionnism.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:08                                                                                         ` Stefan Monnier
  2018-10-29 21:53                                                                                           ` Michael Heerdegen
@ 2018-10-30  1:15                                                                                           ` Garreau, Alexandre
  2018-10-30  6:17                                                                                           ` Eli Zaretskii
                                                                                                             ` (2 subsequent siblings)
  4 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-30  1:15 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-29 at 17:08, Stefan Monnier wrote:
>>> > Doc strings which specify fully the arguments to these macros, including
>>> > their semantics, and say what the macros do.  The current doc strings
>>> > (at least some of them) for these macros don't do this.
>>> I understand this in theory, but I don't know what it means in this
>>> concrete case.
>> Take a look at, for example, the doc string for pcase-dolist.  In its
>> entirety, it's this:
>
> Thanks.  What do you think of the patch below?
>
> I'd rather keep it defined in terms of its differences w.r.t `dolist`,
> but if really needed, we could change the doc so it doesn't rely on
> `dolist`s own doc at all.

You can do that while being more explicit on how arguments relate.  A
little redundancy might be welcome, but I believe the standard minimum
(that, for instance, would satisfy checkdoc) would only to cite each
argument name in upcase and say it is like in `dolist', only if this is
*exactely the case*.  It is not for “PATTERN” so usage ought to be more
detailed: instead of describing what is done, you’d better explain what
it is for.  So in “More specifically `dolist's VAR binding is replaced
by a PATTERN against which each element of the list is matched.” you’re
simply describing your macro implementation, which readers doesn’t want
(otherwise they would be reading function’s source), you’d better say
“PATTERN allow to bind several variables at once through a `pcase'
pattern, instead of only one var as in simple `dolist'”.  This is way
clearer (I really ought to learn how to make up patches ><).

> We do have to keep the reference to `pcase` because we don't want to
> repeat the definition of what a pcase pattern can look like.

Of course.  But you want to precise how exactely does it relate to
`pcase'.

>  (defmacro pcase-let (bindings &rest body)
>    "Like `let' but where you can use `pcase' patterns for bindings.
>  BODY should be a list of expressions, and BINDINGS should be a list of bindings
> -of the form (PAT EXP).
> +of the form (PATTERN EXP).

So `pcase-let' doesn’t support single variable names bound to `nil' (not
that sad, I (sadly) never use that anyway, that’s only for lexical
locality tweaking)?  I checked, in fact it indeed doesn’t: knowing the
other `pcase-' functions docstrings tendency to omit optional behavior,
if I didn’t checked, I’d have bet it were supporting it.

Then, contrarily to `let' you might make your docstring more readable by
changing the arglist spec: "\(fn ((PATTERN EXP)...) BODY...)"

or you may be more formal, so it’d become more readable: “BINDINGS is a
list of the form (BINDING...), with each BINDING is (PATTERN EXP), where
PATTERN is a `pcase' pattern, and EXP the expression it must match.”

>  ;;;###autoload
>  (defmacro pcase-dolist (spec &rest body)
> -  "Like `dolist' but where the binding can be a `pcase' pattern.
> +  "Superset of `dolist' where the VAR binding can be a `pcase' PATTERN.
> +More specifically `dolist's VAR binding is replaced by a PATTERN
> +against which each element of the list is matched.
> +As in the case of `pcase-let', PATTERN is matched under the assumption
> +that it *will* match.

First I don’t believe it is a good idea to talk about `pcase-let' in the
docstring of another function, or then you should cite the whole family
(including `pcase-lambda', etc.), except if they’re tightly tied, but
then you should also cite `pcase-dolist' in `pcase-let' docstring, so to
make a followable dual-link.

>  The macro is expanded and optimized under the assumption that those
>  patterns *will* match, so a mismatch may go undetected or may cause
>  any kind of error."

That’s not explicit enough on the result if not doing so: what kind of
error?

From what I see there:

#+BEGIN_SRC emacs-lisp
(pcase-let ((`(,a ,b ,c) (list 1 2))) (list a b c)) ; => (1 2 nil)

(pcase-let ((`(,a ,b (2 3)) (list 1 2 3))) (list a b))
;; => (wrong-type-argument listp 3)

(pcase-let ((`(,a ,b (2 3)) (list 1 2 (list 4 5)))) (list a b))
;; => (1 2)
#+END_SRC

It seems to be like `pcase-lambda': it binds nil, and doesn’t err
anything, as long as the structures are in the same places and the same
types.

This behavior ought to be documented, or changed.

In my message about `pcase-lambda', I wrote:
> A given subpattern inside PATTERN might not match values (equality) or
> even types, except for each of its subsequences, which *have* to
> exist, have the right type, and be in the right place.

>  \n(fn (PATTERN LIST) BODY...)"
>    (declare (indent 1) (debug ((pcase-PAT form) body)))
>    (if (pcase--trivial-upat-p (car spec))

So `pcase-dolist' doesn’t support `dolist'’s `result'?  I bet it does
(if it doesn’t it’s sad), and like in `pcase-lambda' you again omitted
optional arguments from your docstring: this is confusing, as you might
as well have implemented it so that to remove or override these.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-30  0:17                                                                                                       ` Garreau, Alexandre
@ 2018-10-30  1:40                                                                                                         ` Michael Heerdegen
  2018-10-30 16:05                                                                                                         ` Yuri Khan
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-30  1:40 UTC (permalink / raw)
  To: Garreau, Alexandre
  Cc: Eli Zaretskii, Dmitry Gutov, Stefan Monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> > I think we can agree that we disagree - I just don't share your
> > opinion.  The thing is designed in a way that it matches how some, but
> > not all people, like to think about pattern matching.
>
> Not that much I believe: you were enthusiast as well about the `var'
> pattern

Yeah, but only to see some lines later that what we have is better.  The
concept and implementation of pcase are more thought over than you
think.

Ok, I think I have said all I wanted, more than once: I like pcase, it
is a very good solution of the task of pattern matching in my eyes.  I
like its use of backquote, etc...I think this thread has enough of my
opinion so far, so I'll stop here until I have something really new to
say.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: What `case' have done you? [Was: Re: Replace trivial pcase occurrences in the Emacs sources]
  2018-10-30  0:36                                                                                     ` What `case' have done you? [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
@ 2018-10-30  1:45                                                                                       ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-30  1:45 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: Eli Zaretskii, monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> There are quite some (long) cases where only matching characters or
> symbols: is it really that problematic to use `case' (though, in such
> common functions body, I wouldn’t find cond+assoc natural either)?

That's what we discuss here.  However, the suggested patch isn't meant
to answer this question.  I only want to clear up some pcase
occurrences.  If developers later decide to replace such occurrences
with case or whatever, I can still do it.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:08                                                                                         ` Stefan Monnier
  2018-10-29 21:53                                                                                           ` Michael Heerdegen
  2018-10-30  1:15                                                                                           ` Garreau, Alexandre
@ 2018-10-30  6:17                                                                                           ` Eli Zaretskii
  2018-10-30 12:15                                                                                             ` Stefan Monnier
  2018-10-30 17:22                                                                                           ` Michael Heerdegen
  2018-10-30 18:09                                                                                           ` Alan Mackenzie
  4 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30  6:17 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Mon, 29 Oct 2018 17:08:38 -0400
> 
> Thanks.  What do you think of the patch below?

Thanks for doing this.

> I'd rather keep it defined in terms of its differences w.r.t `dolist`,
> but if really needed, we could change the doc so it doesn't rely on
> `dolist`s own doc at all.

I think the doc string should be (more) independent, at least in the
pcase-dolist case, because the semantics of executing BODY with
PATTERN matched against a LIST element is significantly different from
that of executing the dolist BODY with a VAR binding.  And the
description of that semantics is missing from the doc string you
propose.

> We do have to keep the reference to `pcase` because we don't want to
> repeat the definition of what a pcase pattern can look like.

I see no problem to say something like

  See `pcase' for the description of possible forms of PATTERN.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:46                                                                                   ` Michael Heerdegen
  2018-10-30  0:36                                                                                     ` What `case' have done you? [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
@ 2018-10-30  6:31                                                                                     ` Eli Zaretskii
  2018-10-30 15:47                                                                                       ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30  6:31 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Mon, 29 Oct 2018 22:46:54 +0100
> 
> > IOW, a list of all changed files, with the description at the end.
> 
> Ok, done.  I kept the description as commit message however, since I
> need one.

I never meant to say you should discard one.

> Ok to install (the patch itself is unchanged)?

Fine with me, thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30  6:17                                                                                           ` Eli Zaretskii
@ 2018-10-30 12:15                                                                                             ` Stefan Monnier
  2018-10-30 12:38                                                                                               ` Eli Zaretskii
  2018-10-30 14:16                                                                                               ` Andy Moreton
  0 siblings, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 12:15 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

> I think the doc string should be (more) independent, at least in the
> pcase-dolist case, because the semantics of executing BODY with
> PATTERN matched against a LIST element is significantly different from
> that of executing the dolist BODY with a VAR binding.

Hmm... I really don't see what difference you're thinking of.

Maybe a simpler way to document it is to show its definition:

    (dolist (x LIST) (pcase-let ((PATTERN x)) BODY))


-- Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 23:12                                                                                             ` Eric Abrahamsen
  2018-10-29 23:18                                                                                               ` Eric Abrahamsen
@ 2018-10-30 12:30                                                                                               ` Stefan Monnier
  2018-10-30 17:16                                                                                                 ` Stefan Monnier
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 12:30 UTC (permalink / raw)
  To: Eric Abrahamsen; +Cc: Michael Heerdegen, emacs-devel

> I wonder if the manual shouldn't have a section somewhere making
> explicit the difference between `pcase' -- where a single value is
> matched against many patterns, and may fail to match altogether, and
> destructuring is only one of the use-cases -- and the other

Yes, I'll send a patch for that,


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 12:15                                                                                             ` Stefan Monnier
@ 2018-10-30 12:38                                                                                               ` Eli Zaretskii
  2018-10-30 15:00                                                                                                 ` Stefan Monnier
  2018-10-30 14:16                                                                                               ` Andy Moreton
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 12:38 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Cc: emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 08:15:31 -0400
> 
> > I think the doc string should be (more) independent, at least in the
> > pcase-dolist case, because the semantics of executing BODY with
> > PATTERN matched against a LIST element is significantly different from
> > that of executing the dolist BODY with a VAR binding.
> 
> Hmm... I really don't see what difference you're thinking of.

I thought it was clear: matching doesn't assign any values to anything
directly related to BODY, so the mechanism by which it affects
execution of BODY needs to be described.

> Maybe a simpler way to document it is to show its definition:
> 
>     (dolist (x LIST) (pcase-let ((PATTERN x)) BODY))

You aren't saying that showing the code removes the need for any
documentation of what it does, do you? ;-)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 23:18                                                                                               ` Eric Abrahamsen
  2018-10-30  0:50                                                                                                 ` `pcase'/`case' implementation [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
@ 2018-10-30 13:07                                                                                                 ` Stefan Monnier
  2018-10-30 23:30                                                                                                   ` Eric Abrahamsen
  2018-11-01  0:16                                                                                                   ` Garreau, Alexandre
  1 sibling, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 13:07 UTC (permalink / raw)
  To: emacs-devel

> In fact, when you think about it, the "case" nature of pcase is pretty
> orthogonal to the "match/destructure" nature of pcase. If anything

How do you suggest to split the two in cases like:

    (defun cconv-convert (form env extend)
      (pcase form
        (`(,(and letsym (or `let* `let)) ,binders . ,body)
         ...)
    
        (`(,(and `(lambda . ,_) fun) . ,args)
         ...)
        
        (`(cond . ,cond-forms)
         ...)
    
        (`(function (lambda ,args . ,body) . ,_)
         ...)
    
        (`(internal-make-closure . ,_)
         ...)
    
        (`(quote . ,_) form)
        (`(function . ,_) form)
    
        (`(,(and sym (or `defconst `defvar)) ,definedsymbol . ,forms)
         ...)
    
        ((and `(condition-case ,var ,protected-form . ,handlers)
              (guard byte-compile--use-old-handlers))
         ...)
    
        (`(condition-case ,var ,protected-form . ,handlers)
         ...)
    
        (`(,(and head (or (and `catch (guard byte-compile--use-old-handlers))
                          `unwind-protect))
           ,form . ,body)
         ...)
    
        (`(setq . ,forms)
         ...)
    
        (`(,(and (or `funcall `apply) callsym) ,fun . ,args)
         ...)
    
        (`(interactive . ,forms)
         ...)

        (`(declare . ,_) form)

        (`(,func . ,forms)
         ...)

        (_
         ...)))

That kind of use is the main motivation behind the design of pcase.

Once you have this, you also trivially cover the `cl-case` uses and you
can easily make it handle the "destructuring" uses.
Splitting the two will just require more code to get less flexibility.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-30  0:27                                                                                               ` pcase ` meaning Garreau, Alexandre
@ 2018-10-30 13:14                                                                                                 ` Stefan Monnier
  2018-10-31 23:13                                                                                                   ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 13:14 UTC (permalink / raw)
  To: emacs-devel

> #+BEGIN_SRC ocaml
>   match [1;2;3] with [a;b;c] -> [a;b;c]
> #+END_SRC
>
> But this is a non-primordial side effect.  Notice how in the later case
> the matched data *always* look the same as the pattern (beside replacing
> a number per an identifier): *that’s* the purpose of pattern matching.
> While in the lisp case you got those extra “,”.

That's for a very simple reason: OCaml doesn't have Lisp's symbols, so
its [a;b;c] can't mean "a list containing the symbols a, b, and c".
OCaml still has to distinguish between variables and data constructors,
but instead of using a "," to distinguish the two cases, they force
constructors to be capitalized.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 12:15                                                                                             ` Stefan Monnier
  2018-10-30 12:38                                                                                               ` Eli Zaretskii
@ 2018-10-30 14:16                                                                                               ` Andy Moreton
  2018-10-30 15:05                                                                                                 ` Clément Pit-Claudel
  1 sibling, 1 reply; 375+ messages in thread
From: Andy Moreton @ 2018-10-30 14:16 UTC (permalink / raw)
  To: emacs-devel

On Tue 30 Oct 2018, Stefan Monnier wrote:

>> I think the doc string should be (more) independent, at least in the
>> pcase-dolist case, because the semantics of executing BODY with
>> PATTERN matched against a LIST element is significantly different from
>> that of executing the dolist BODY with a VAR binding.
>
> Hmm... I really don't see what difference you're thinking of.
>
> Maybe a simpler way to document it is to show its definition:
>
>     (dolist (x LIST) (pcase-let ((PATTERN x)) BODY))

So this also fails randomly if the pattern does not match, like
`pcase-let', and this should be documented.

How are users meant to write reliable code using such constructs ? Why
are there not versions of these constructs that have deterministic
behaviour on pattern match failure ?

    AndyM




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 12:38                                                                                               ` Eli Zaretskii
@ 2018-10-30 15:00                                                                                                 ` Stefan Monnier
  2018-10-30 17:00                                                                                                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 15:00 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

>>     (dolist (x LIST) (pcase-let ((PATTERN x)) BODY))
> You aren't saying that showing the code removes the need for any
> documentation of what it does, do you? ;-)

I think I am, yes.  In cases like these where the definition is really
just a trivial combination of two less trivial elements, it might be
a better option for the docstring, since it is both more concise and
more precise than whatever wording we can come up with to try and repeat
what dolist and pcase-let do.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 14:16                                                                                               ` Andy Moreton
@ 2018-10-30 15:05                                                                                                 ` Clément Pit-Claudel
  2018-10-30 18:14                                                                                                   ` Alan Mackenzie
  0 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-30 15:05 UTC (permalink / raw)
  To: emacs-devel

On 30/10/2018 10.16, Andy Moreton wrote:
> How are users meant to write reliable code using such constructs ?

Ensure that the pattern actually matches :)
IOW, only use these constructs when it's an invariant of your program that the pattern will match the data.
For cases in which the pattern might not match, use pcase instead of pcase-dolist.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30  6:31                                                                                     ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
@ 2018-10-30 15:47                                                                                       ` Michael Heerdegen
  2018-10-30 17:29                                                                                         ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-30 15:47 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > Ok to install (the patch itself is unchanged)?
>
> Fine with me, thanks.

Installed as 049bd5d2 "Don't quote self-quoting pcase patterns".

Shall I now work on the `DOESNT-UNQUOTE -> 'DOESNT-UNQUOTE patch?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-30  0:17                                                                                                       ` Garreau, Alexandre
  2018-10-30  1:40                                                                                                         ` Michael Heerdegen
@ 2018-10-30 16:05                                                                                                         ` Yuri Khan
  1 sibling, 0 replies; 375+ messages in thread
From: Yuri Khan @ 2018-10-30 16:05 UTC (permalink / raw)
  To: galex-713
  Cc: Michael Heerdegen, Eli Zaretskii, Emacs developers,
	Stefan Monnier, Dmitry Gutov

On Tue, Oct 30, 2018 at 7:18 AM Garreau, Alexandre
<galex-713@galex-713.eu> wrote:

> (pcase `(1 2 3) (`(1 2 3) t))
>
> look the same, as well as:
>
> (pcase `(a b c) (`(a b c) t))
>
> But not:
>
> (pcase `(1 2 3) (`(,a ,b ,c) (+ a b c)))

IMO you’re giving too much attention to “looking the same”.

You use identifiers a, b, and c in a pattern. The pattern matcher
needs to know which of these you meant as placeholders to bind, and
which as literal symbols to match against.

    (let ((c 42))
      (pcase `(a x 42) (`(a ,b ,(pred (equal c))) t)))

In an alternate world, you would color the parentheses, the spaces,
and the literal symbol “a” yellow, and say these are the things to
match literally. You would then color “b” and “c” white, and say these
are placeholders. You might even color something green and say these
are expressions whose values should be taken and matched.

In that same world, you could draw nested boxes instead of these
nested parentheses that make newbies so nervous about Lisp.

However, in this world, we only encode Unicode characters in our
source files, and add color only as an aid to understanding. So we use
various funny characters such as parentheses to denote nesting, and `
and , to denote color.

(Upthread, the idea of “holes” was mentioned. That is a very good
analogy, both for pcase and for quoting/antiquoting in general.)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 15:00                                                                                                 ` Stefan Monnier
@ 2018-10-30 17:00                                                                                                   ` Eli Zaretskii
  2018-10-30 17:27                                                                                                     ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 17:00 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Cc: emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 11:00:47 -0400
> 
> >>     (dolist (x LIST) (pcase-let ((PATTERN x)) BODY))
> > You aren't saying that showing the code removes the need for any
> > documentation of what it does, do you? ;-)
> 
> I think I am, yes.

Seriously?  This cannot fly: for starters, the user could be using an
Emacs where *.el files are not accessible.  More generally, it sounds
like a defeat to say that we are unable to describe the behavior, and
ask users to read the code instead.

> In cases like these where the definition is really just a trivial
> combination of two less trivial elements, it might be a better
> option for the docstring, since it is both more concise and more
> precise than whatever wording we can come up with to try and repeat
> what dolist and pcase-let do.

Tell you what: how about if you try explaining this, and I will then
make a better doc string out of that?  Deal?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 12:30                                                                                               ` Stefan Monnier
@ 2018-10-30 17:16                                                                                                 ` Stefan Monnier
  2018-10-30 19:03                                                                                                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 17:16 UTC (permalink / raw)
  To: Eric Abrahamsen; +Cc: Michael Heerdegen, emacs-devel

>> I wonder if the manual shouldn't have a section somewhere making
>> explicit the difference between `pcase' -- where a single value is
>> matched against many patterns, and may fail to match altogether, and
>> destructuring is only one of the use-cases -- and the other
> Yes, I'll send a patch for that,

How 'bout...


        Stefan


diff --git a/doc/lispref/control.texi b/doc/lispref/control.texi
index 5be4b298b4..819f486f4e 100644
--- a/doc/lispref/control.texi
+++ b/doc/lispref/control.texi
@@ -477,6 +477,7 @@ Pattern-Matching Conditional
 * The @code{pcase} macro: pcase Macro.  Plus examples and caveats.
 * Extending @code{pcase}: Extending pcase.  Define new kinds of patterns.
 * Backquote-Style Patterns: Backquote Patterns.  Structural matching.
+* Destructuring patterns:: Using pcase patterns to extract subfields.
 @end menu
 
 @node pcase Macro
@@ -1168,6 +1169,81 @@ Backquote Patterns
 (evaluate '(sub 1 2) nil)                 @result{} error
 @end example
 
+@node Destructuring patterns
+@subsection Destructuring Patterns
+@cindex Destructuring patterns
+
+Pcase patterns not only express a condition on the form of the objects
+they can match but they can also extract sub-fields of those objects.
+Say we have a list and want to extract 2 elements from it with the
+following code:
+
+@example
+  (pcase l
+    (`(add ,x ,y)  (message "Contains %S and %S" x y)))
+@end example
+
+This will not only extract @code{x} and @code{y} but will additionally
+test that @code{l} is a list containing exactly 3 elements and whose
+first element is the symbol @code{add}.  If any of those tests fail,
+@code{pcase} will directly return @code{nil} without calling
+@code{message}.
+
+The macros described in this section use @emph{destructuring}
+patterns, which are normal Pcase patterns used in a context where we
+presume that the object does match the pattern, and we only want
+to extract some subfields.  For example:
+
+@example
+  (pcase-let ((`(add ,x ,y) l))
+    (message "Contains %S and %S" x y))
+@end example
+
+Does the same as the previous example, except that it directly tries
+to extract @code{x} and @code{y} from @code{l} without first verifying
+if @code{l} is a list which has the right number of elements and has
+@code{add} as its first element.
+The precise behavior when the object does not actually match the
+pattern is undefined, although the body will not be silently skipped:
+either an error is signaled or the body is run with some of the
+variables potentially bound to arbitrary values like @code{nil}.
+
+@defmac pcase-let bindings body@dots{}
+Bind variables according to @var{bindings} and then eval @var{body}.
+
+@var{bindings} is a list of bindings of the form @code{(@var{pattern}
+@var{exp})}, where @var{exp} is an expression to evaluate and
+@var{pattern} is a destructuring pattern.
+
+All @var{exp}s are evaluated first after which they are matched
+against their respective @var{pattern}, introducing new variable
+bindings which can then be used inside @var{body}.
+@end defmac
+
+@defmac pcase-let* bindings body@dots{}
+Bind variables according to @var{bindings} and then eval @var{body}.
+
+@var{bindings} is a list of bindings of the form @code{(@var{pattern}
+@var{exp})}, where @var{exp} is an expression to evaluate and
+@var{pattern} is a destructuring pattern.
+
+Unlike @code{pcase-let}, but like @code{let*}, each @var{exp} is
+matched against its corresponding @var{pattern} before passing to the
+next element of @var{bindings}, so the variables introduced in each
+binding are available in the @var{exp}s that follow it, additionally
+to being available in @var{body}.
+@end defmac
+
+@findex dolist
+@defmac pcase-dolist (pattern list) body@dots{}
+This construct executes @var{body} once for each element of
+@var{list}, in a context where the destructuring pattern
+@var{pattern} was matched against the element.
+When @var{pattern} is a simple variable, this ends up being equivalent
+to @code{dolist}.
+@end defmac
+
+
 @node Iteration
 @section Iteration
 @cindex iteration



^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:08                                                                                         ` Stefan Monnier
                                                                                                             ` (2 preceding siblings ...)
  2018-10-30  6:17                                                                                           ` Eli Zaretskii
@ 2018-10-30 17:22                                                                                           ` Michael Heerdegen
  2018-10-30 17:31                                                                                             ` Stefan Monnier
  2018-10-30 18:09                                                                                           ` Alan Mackenzie
  4 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-30 17:22 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

[-- Attachment #1: Type: text/plain, Size: 227 bytes --]

Stefan,

we also wanted to say something more about side effects.  Since the
restoration of the pcase docstring this is completely missing.

Maybe you also can take care about this?  I would suggest maybe
something like this:


[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0001-WIP-pcase-pattern-side-effects.patch --]
[-- Type: text/x-diff, Size: 771 bytes --]

From 499e715e2f31fc7f9e50dfb553532aedaba1dd3f Mon Sep 17 00:00:00 2001
From: Michael Heerdegen <michael_heerdegen@web.de>
Date: Sun, 28 Oct 2018 23:30:49 +0100
Subject: [PATCH] WIP: pcase pattern side effects

---
 lisp/emacs-lisp/pcase.el | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
index 57c2d6c3cb..ff59d2c3a0 100644
--- a/lisp/emacs-lisp/pcase.el
+++ b/lisp/emacs-lisp/pcase.el
@@ -139,6 +139,9 @@ pcase
   (F ARG1 .. ARGn)
      call F with ARG1..ARGn and EXPVAL as n+1'th argument
 
+Evaluating a FUN, BOOLEXP or EXPR as described above should not have
+any side effects.
+
 FUN, BOOLEXP, EXPR, and subsequent PAT can refer to variables
 bound earlier in the pattern by a SYMBOL pattern.
 
-- 
2.19.1


[-- Attachment #3: Type: text/plain, Size: 20 bytes --]



Thanks,

Michael.

^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:00                                                                                                   ` Eli Zaretskii
@ 2018-10-30 17:27                                                                                                     ` Stefan Monnier
  2018-10-30 17:36                                                                                                       ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 17:27 UTC (permalink / raw)
  To: emacs-devel

> Seriously?  This cannot fly: for starters, the user could be using an
> Emacs where *.el files are not accessible.

I didn't mean for the docstring to say "read the code"; I meant the
patch below.

> Tell you what: how about if you try explaining this,

I already did.


        Stefan


diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
index 57c2d6c3cb..7781d0d424 100644
--- a/lisp/emacs-lisp/pcase.el
+++ b/lisp/emacs-lisp/pcase.el
@@ -302,7 +302,10 @@ pcase-let
 
 ;;;###autoload
 (defmacro pcase-dolist (spec &rest body)
-  "Like `dolist' but where the binding can be a `pcase' pattern.
+  "Superset of `dolist' where the VAR binding can be a `pcase' PATTERN.
+More specifically, this is just a shorthand for
+
+    (dolist (x LIST) (pcase-let ((PATTERN x)) BODY...))
 \n(fn (PATTERN LIST) BODY...)"
   (declare (indent 1) (debug ((pcase-PAT form) body)))
   (if (pcase--trivial-upat-p (car spec))




^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 15:47                                                                                       ` Michael Heerdegen
@ 2018-10-30 17:29                                                                                         ` Eli Zaretskii
  2018-10-30 22:09                                                                                           ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 17:29 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 16:47:45 +0100
> 
> Shall I now work on the `DOESNT-UNQUOTE -> 'DOESNT-UNQUOTE patch?

Yes, I think so.

TIA



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:22                                                                                           ` Michael Heerdegen
@ 2018-10-30 17:31                                                                                             ` Stefan Monnier
  2018-10-30 23:08                                                                                               ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 17:31 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

> +Evaluating a FUN, BOOLEXP or EXPR as described above should not have
> +any side effects.

LGTM, thanks.  We could maybe give a hint about why, e.g. saying that
there are no guarantees about the order and number of times they are run.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:27                                                                                                     ` Stefan Monnier
@ 2018-10-30 17:36                                                                                                       ` Eli Zaretskii
  2018-10-30 18:09                                                                                                         ` Stefan Monnier
  2018-10-30 18:24                                                                                                         ` Alan Mackenzie
  0 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 17:36 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Tue, 30 Oct 2018 13:27:43 -0400
> 
> > Seriously?  This cannot fly: for starters, the user could be using an
> > Emacs where *.el files are not accessible.
> 
> I didn't mean for the docstring to say "read the code"; I meant the
> patch below.
> 
> > Tell you what: how about if you try explaining this,
> 
> I already did.

And I already read that, and hoped for some more details.  Should I
give up?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:36                                                                                                       ` Eli Zaretskii
@ 2018-10-30 18:09                                                                                                         ` Stefan Monnier
  2018-10-30 18:42                                                                                                           ` Eli Zaretskii
  2018-10-30 18:24                                                                                                         ` Alan Mackenzie
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 18:09 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

> And I already read that, and hoped for some more details.  Should I
> give up?

As I said, I'm not interested in a docstring that repeats what
dolist does; I want it to explain the difference between dolist and
pcase-dolist (because that's how pcase-dolist is defined both in terms
of design and in terms of implementation).


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-29 21:08                                                                                         ` Stefan Monnier
                                                                                                             ` (3 preceding siblings ...)
  2018-10-30 17:22                                                                                           ` Michael Heerdegen
@ 2018-10-30 18:09                                                                                           ` Alan Mackenzie
  2018-10-30 18:17                                                                                             ` Stefan Monnier
  4 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-30 18:09 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Hello, Stefan.

On Mon, Oct 29, 2018 at 17:08:38 -0400, Stefan Monnier wrote:
> >> > Doc strings which specify fully the arguments to these macros, including
> >> > their semantics, and say what the macros do.  The current doc strings
> >> > (at least some of them) for these macros don't do this.
> >> I understand this in theory, but I don't know what it means in this
> >> concrete case.
> > Take a look at, for example, the doc string for pcase-dolist.  In its
> > entirety, it's this:

> Thanks.  What do you think of the patch below?

I don't think it's enough.

> I'd rather keep it defined in terms of its differences w.r.t `dolist`,
> but if really needed, we could change the doc so it doesn't rely on
> `dolist`s own doc at all.

That's a bad idea if it means not saying what the macro does.  Not
everybody is familiar with dolist by any means.  Is dolist's doc string
of sufficiently high quality to act as this basis?

> We do have to keep the reference to `pcase` because we don't want to
> repeat the definition of what a pcase pattern can look like.

Yes, I think that's right.

Things I believe MUST appear explicitly in the doc string for
pcase-dolist: 
1. It is a loop over the elements of LIST, which must be a list.
2. It attempts to match the current list element with the supplied
PATTERN, which must be a valid pcase style pattern.
3. The BODY forms are evaluated for each element of the list.
4. The purpose of the matching is to create bindings for symbols, and
these bindings are in force when the BODY forms are evaluated.
5. When a pattern match fails, ..... (This needs to be stated).

>         Stefan


> diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
> index 57c2d6c3cb..861c900b21 100644
> --- a/lisp/emacs-lisp/pcase.el
> +++ b/lisp/emacs-lisp/pcase.el
> @@ -281,7 +281,7 @@ pcase-let*
>  (defmacro pcase-let (bindings &rest body)
>    "Like `let' but where you can use `pcase' patterns for bindings.
>  BODY should be a list of expressions, and BINDINGS should be a list of bindings
> -of the form (PAT EXP).
> +of the form (PATTERN EXP).
>  The macro is expanded and optimized under the assumption that those
>  patterns *will* match, so a mismatch may go undetected or may cause
>  any kind of error."
> @@ -302,7 +302,12 @@ pcase-let
 
>  ;;;###autoload
>  (defmacro pcase-dolist (spec &rest body)
> -  "Like `dolist' but where the binding can be a `pcase' pattern.
> +  "Superset of `dolist' where the VAR binding can be a `pcase' PATTERN.
> +More specifically `dolist's VAR binding is replaced by a PATTERN
> +against which each element of the list is matched.
> +As in the case of `pcase-let', PATTERN is matched under the assumption
> +that it *will* match.
> +
>  \n(fn (PATTERN LIST) BODY...)"
>    (declare (indent 1) (debug ((pcase-PAT form) body)))
>    (if (pcase--trivial-upat-p (car spec))

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 15:05                                                                                                 ` Clément Pit-Claudel
@ 2018-10-30 18:14                                                                                                   ` Alan Mackenzie
  2018-10-30 19:56                                                                                                     ` Clément Pit-Claudel
  0 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-30 18:14 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

Hello, Clément.

On Tue, Oct 30, 2018 at 11:05:55 -0400, Clément Pit-Claudel wrote:
> On 30/10/2018 10.16, Andy Moreton wrote:
> > How are users meant to write reliable code using such constructs ?

> Ensure that the pattern actually matches :)

You mean, unless you can be 100% sure that the pattern will match, you
mustn't use pcase-... constructs.  That sounds equivalent to saying you
shouldn't use these constructs at all.

> IOW, only use these constructs when it's an invariant of your program
> that the pattern will match the data.  For cases in which the pattern
> might not match, use pcase instead of pcase-dolist.

pcase is not a looping construct.  pcase-dolist is.  They're not
replacements for eachother.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:09                                                                                           ` Alan Mackenzie
@ 2018-10-30 18:17                                                                                             ` Stefan Monnier
  2018-10-30 19:00                                                                                               ` Alan Mackenzie
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 18:17 UTC (permalink / raw)
  To: emacs-devel

> Not everybody is familiar with dolist by any means.  Is dolist's doc
> string of sufficiently high quality to act as this basis?

If dolist's docstring is not good enough, then I don't think it's
pcase-dolist's job to fix it.

>> We do have to keep the reference to `pcase` because we don't want to
>> repeat the definition of what a pcase pattern can look like.
>
> Yes, I think that's right.
>
> Things I believe MUST appear explicitly in the doc string for
> pcase-dolist: 
> 1. It is a loop over the elements of LIST, which must be a list.
> 2. It attempts to match the current list element with the supplied
> PATTERN, which must be a valid pcase style pattern.
> 3. The BODY forms are evaluated for each element of the list.
> 4. The purpose of the matching is to create bindings for symbols, and
> these bindings are in force when the BODY forms are evaluated.
> 5. When a pattern match fails, ..... (This needs to be stated).

This is highly redundant w.r.t pcase-let and dolist.  Fine for the
manual, but not for docstrings.  You can click on the link to the
docstring of `dolist` and `pcase` (tho, I now see the link should go to
`pcase-let` instead).


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:36                                                                                                       ` Eli Zaretskii
  2018-10-30 18:09                                                                                                         ` Stefan Monnier
@ 2018-10-30 18:24                                                                                                         ` Alan Mackenzie
  1 sibling, 0 replies; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-30 18:24 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

Hello, Eli.

On Tue, Oct 30, 2018 at 19:36:04 +0200, Eli Zaretskii wrote:
> > From: Stefan Monnier <monnier@iro.umontreal.ca>
> > Date: Tue, 30 Oct 2018 13:27:43 -0400

> > > Seriously?  This cannot fly: for starters, the user could be using an
> > > Emacs where *.el files are not accessible.

> > I didn't mean for the docstring to say "read the code"; I meant the
> > patch below.

> > > Tell you what: how about if you try explaining this,

> > I already did.

> And I already read that, and hoped for some more details.  Should I
> give up?

No, please don't.

Two things: I explained what I think is the semantics of pcase-dolist in
a post I posted ~20 minutes ago in reply to Stefan's opening of this sub
thread.  I can't be sure I've got all the details right, but I believe
I'm not far off.

If we can't get quality doc strings for pcase-dolist and friends, I say
we should remove them from Emacs.  There are only around 30 occurrences
of pcase-dolist.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:09                                                                                                         ` Stefan Monnier
@ 2018-10-30 18:42                                                                                                           ` Eli Zaretskii
  2018-10-30 18:58                                                                                                             ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 18:42 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Cc: emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 14:09:18 -0400
> 
> > And I already read that, and hoped for some more details.  Should I
> > give up?
> 
> As I said, I'm not interested in a docstring that repeats what
> dolist does; I want it to explain the difference between dolist and
> pcase-dolist (because that's how pcase-dolist is defined both in terms
> of design and in terms of implementation).

I didn't say we should repeat what dolist does, so our interests don't
necessarily conflict yet.  I tried to explain earlier what I thought
was missing, here it is again:

> matching doesn't assign any values to anything directly related to
> BODY, so the mechanism by which it affects execution of BODY needs
> to be described.

Could you please fill that void?  This isn't a repetition of what
dolist does.

TIA



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:42                                                                                                           ` Eli Zaretskii
@ 2018-10-30 18:58                                                                                                             ` Stefan Monnier
  2018-10-31 12:08                                                                                                               ` Alan Mackenzie
  2018-11-03 13:13                                                                                                               ` Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 18:58 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

>> matching doesn't assign any values to anything directly related to
>> BODY, so the mechanism by which it affects execution of BODY needs
>> to be described.
>
> Could you please fill that void?  This isn't a repetition of what
> dolist does.

I don't know how to say it any better than with the patch I just
installed into emacs-26.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:17                                                                                             ` Stefan Monnier
@ 2018-10-30 19:00                                                                                               ` Alan Mackenzie
  2018-10-31  0:21                                                                                                 ` Andy Moreton
  0 siblings, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-30 19:00 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Hello, Stefan.

On Tue, Oct 30, 2018 at 14:17:10 -0400, Stefan Monnier wrote:
> > Not everybody is familiar with dolist by any means.  Is dolist's doc
> > string of sufficiently high quality to act as this basis?

> If dolist's docstring is not good enough, then I don't think it's
> pcase-dolist's job to fix it.

I think everybody would agree with this point.

> >> We do have to keep the reference to `pcase` because we don't want to
> >> repeat the definition of what a pcase pattern can look like.

> > Yes, I think that's right.

> > Things I believe MUST appear explicitly in the doc string for
> > pcase-dolist: 
> > 1. It is a loop over the elements of LIST, which must be a list.
> > 2. It attempts to match the current list element with the supplied
> > PATTERN, which must be a valid pcase style pattern.
> > 3. The BODY forms are evaluated for each element of the list.
> > 4. The purpose of the matching is to create bindings for symbols, and
> > these bindings are in force when the BODY forms are evaluated.
> > 5. When a pattern match fails, ..... (This needs to be stated).

> This is highly redundant w.r.t pcase-let and dolist.

Maybe, but so what?

Doc strings should be as far as is reasonable self contained.  Have a
look at the doc strings for let and let*.  They have a great deal in
common, but each is self contained.

> Fine for the manual, but not for docstrings.

You seem to be arguing that doc strings needn't say what
de{fun,macro,var}s do and are, as long as the meaning can be acquired
through the traversal of a directed acyclic graph of linked doc strings.
Maybe you find this a good way of acquiring information, but I certainly
don't.  I just get angry and frustrated, and I'm sure I'm not the only
one.

> You can click on the link to the docstring of `dolist` and `pcase`
> (tho, I now see the link should go to `pcase-let` instead).

I can, but I'd much rather find the information in a coherent form in a
single place.  That's what doc strings are for.

>         Stefan

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:16                                                                                                 ` Stefan Monnier
@ 2018-10-30 19:03                                                                                                   ` Eli Zaretskii
  2018-10-30 19:21                                                                                                     ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 19:03 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: eric, michael_heerdegen, emacs-devel

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Date: Tue, 30 Oct 2018 13:16:33 -0400
> Cc: Michael Heerdegen <michael_heerdegen@web.de>, emacs-devel@gnu.org
> 
> >> I wonder if the manual shouldn't have a section somewhere making
> >> explicit the difference between `pcase' -- where a single value is
> >> matched against many patterns, and may fail to match altogether, and
> >> destructuring is only one of the use-cases -- and the other
> > Yes, I'll send a patch for that,
> 
> How 'bout...

Thanks.  I have a few comments:

> +* Destructuring patterns:: Using pcase patterns to extract subfields.

We never used "pcase patterns" in the manual before, so I wonder
whether we should start now.  If we want to do that, this should be
defined before it is used.

> +@node Destructuring patterns
> +@subsection Destructuring Patterns
> +@cindex Destructuring patterns

By convention, index entries should start with a lower-case letter.

> +The macros described in this section use @emph{destructuring}
> +patterns, which are normal Pcase patterns used in a context where we
> +presume that the object does match the pattern, and we only want
> +to extract some subfields.

I think we need to define "destructuring" here (or elsewhere in the
manual, and have a cross-reference there in this section).  Readers
that aren't familiar with that term will not be able to understand why
this word is used here.  We need to start this with something like

  @dfn{Destructuring} means ...

It would also help to tell what exactly makes a pattern a
destructuring one.

> +@example
> +  (pcase-let ((`(add ,x ,y) l))
> +    (message "Contains %S and %S" x y))
> +@end example
> +
> +Does the same as the previous example, except that it directly tries

You want the text after the example to start like this:

  @noindent
  does the same as ...

Otherwise, this sentence sounds awkward, and will also be indented.

> +@var{bindings} is a list of bindings of the form @code{(@var{pattern}
> +@var{exp})}

Please use @w{..} around this form, so that it doesn't get broken
between two lines.

> +All @var{exp}s are evaluated first after which they are matched
> +against their respective @var{pattern}, introducing new variable
> +bindings which can then be used inside @var{body}.

AFAIU, this means only some of the pcase patterns make sense in this
context.  If that is true, I'd suggest ti somehow tell which are (or
which aren't, if that's easier).

> +@defmac pcase-dolist (pattern list) body@dots{}
> +This construct executes @var{body} once for each element of
> +@var{list}, in a context where the destructuring pattern
> +@var{pattern} was matched against the element.

I don't think I understand what "in a context where the pattern was
matched" means here.  Is any aspect of the match except destructuring
bindings relevant to execution of the body?  If so, what other aspects
are relevant?

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:03                                                                                                   ` Eli Zaretskii
@ 2018-10-30 19:21                                                                                                     ` Stefan Monnier
  2018-10-30 19:54                                                                                                       ` Eli Zaretskii
  2018-10-30 20:04                                                                                                       ` Dmitry Gutov
  0 siblings, 2 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 19:21 UTC (permalink / raw)
  To: emacs-devel

>> +* Destructuring patterns:: Using pcase patterns to extract subfields.
> We never used "pcase patterns" in the manual before, so I wonder
> whether we should start now.  If we want to do that, this should be
> defined before it is used.

I'm uncomfortable using "pattern" to refer to "pcase pattern" unless the
context makes it clear.  I'm not completely sure where best to define
pcase patterns.

>> +@node Destructuring patterns
>> +@subsection Destructuring Patterns
>> +@cindex Destructuring patterns
>
> By convention, index entries should start with a lower-case letter.

Fixed.

>> +The macros described in this section use @emph{destructuring}
>> +patterns, which are normal Pcase patterns used in a context where we
>> +presume that the object does match the pattern, and we only want
>> +to extract some subfields.
>
> I think we need to define "destructuring" here (or elsewhere in the
> manual, and have a cross-reference there in this section).

The paragraph you quoted is exactly what I consider the definition of
"destructuring pattern" (I don't see a need to define "destructuring"
separately: the word placed in front of "pattern" is here treated as
a kind of "proper name", just chosen so that it will help some if they
already know the term from elsewhere, such as cl-destructuring-bind).

> Readers that aren't familiar with that term will not be able to
> understand why this word is used here.  We need to start this with
> something like
>
>   @dfn{Destructuring} means ...

I'd rather rename those to "Monnier patterns" and avoid the problem, if
that's what it takes.

> It would also help to tell what exactly makes a pattern a
> destructuring one.

As the paragraph says: it's the context in which it's used.

> You want the text after the example to start like this:
>
>   @noindent
>   does the same as ...
>
> Otherwise, this sentence sounds awkward, and will also be indented.

Thanks.

>> +@var{bindings} is a list of bindings of the form @code{(@var{pattern}
>> +@var{exp})}
>
> Please use @w{..} around this form, so that it doesn't get broken
> between two lines.

Done.

>> +All @var{exp}s are evaluated first after which they are matched
>> +against their respective @var{pattern}, introducing new variable
>> +bindings which can then be used inside @var{body}.
> AFAIU, this means only some of the pcase patterns make sense in this
> context.  If that is true, I'd suggest ti somehow tell which are (or
> which aren't, if that's easier).

Not sure what you're thinking of.

>> +@defmac pcase-dolist (pattern list) body@dots{}
>> +This construct executes @var{body} once for each element of
>> +@var{list}, in a context where the destructuring pattern
>> +@var{pattern} was matched against the element.
>
> I don't think I understand what "in a context where the pattern was
> matched" means here.  Is any aspect of the match except destructuring
> bindings relevant to execution of the body?

No.  But those extra bindings are exactly the context I'm referring to.
In my work, "context" and "environment" are the usual words used to
refer to the map that links identifiers to their corresponding
information (typically, type or value depending on the
...ahem... context).


        Stefan


diff --git a/doc/lispref/control.texi b/doc/lispref/control.texi
index 5be4b298b4..da6a240ddc 100644
--- a/doc/lispref/control.texi
+++ b/doc/lispref/control.texi
@@ -477,6 +477,7 @@ Pattern-Matching Conditional
 * The @code{pcase} macro: pcase Macro.  Plus examples and caveats.
 * Extending @code{pcase}: Extending pcase.  Define new kinds of patterns.
 * Backquote-Style Patterns: Backquote Patterns.  Structural matching.
+* Destructuring patterns:: Using pcase patterns to extract subfields.
 @end menu
 
 @node pcase Macro
@@ -497,6 +498,10 @@ pcase Macro
 Otherwise, @code{pcase} evaluates to @code{nil}.
 @end defmac
 
+Each @var{pattern} has to be a @dfn{pcase pattern}, which can either
+use one of the core patterns defined below, or use one of the patterns
+defined via @code{pcase-defmacro}.
+
 The rest of this subsection
 describes different forms of core patterns,
 presents some examples,
@@ -1168,6 +1173,82 @@ Backquote Patterns
 (evaluate '(sub 1 2) nil)                 @result{} error
 @end example
 
+@node Destructuring patterns
+@subsection Destructuring Patterns
+@cindex destructuring patterns
+
+Pcase patterns not only express a condition on the form of the objects
+they can match but they can also extract sub-fields of those objects.
+Say we have a list and want to extract 2 elements from it with the
+following code:
+
+@example
+  (pcase l
+    (`(add ,x ,y)  (message "Contains %S and %S" x y)))
+@end example
+
+This will not only extract @code{x} and @code{y} but will additionally
+test that @code{l} is a list containing exactly 3 elements and whose
+first element is the symbol @code{add}.  If any of those tests fail,
+@code{pcase} will directly return @code{nil} without calling
+@code{message}.
+
+The macros described in this section use @dfn{destructuring
+patterns}, which are normal Pcase patterns used in a context where we
+presume that the object does match the pattern, and we only want
+to extract some subfields.  For example:
+
+@example
+  (pcase-let ((`(add ,x ,y) l))
+    (message "Contains %S and %S" x y))
+@end example
+
+@noindent
+does the same as the previous example, except that it directly tries
+to extract @code{x} and @code{y} from @code{l} without first verifying
+if @code{l} is a list which has the right number of elements and has
+@code{add} as its first element.
+The precise behavior when the object does not actually match the
+pattern is undefined, although the body will not be silently skipped:
+either an error is signaled or the body is run with some of the
+variables potentially bound to arbitrary values like @code{nil}.
+
+@defmac pcase-let bindings body@dots{}
+Bind variables according to @var{bindings} and then eval @var{body}.
+
+@var{bindings} is a list of bindings of the form @w{@code{(@var{pattern}
+@var{exp})}}, where @var{exp} is an expression to evaluate and
+@var{pattern} is a destructuring pattern.
+
+All @var{exp}s are evaluated first after which they are matched
+against their respective @var{pattern}, introducing new variable
+bindings which can then be used inside @var{body}.
+@end defmac
+
+@defmac pcase-let* bindings body@dots{}
+Bind variables according to @var{bindings} and then eval @var{body}.
+
+@var{bindings} is a list of bindings of the form @code{(@var{pattern}
+@var{exp})}, where @var{exp} is an expression to evaluate and
+@var{pattern} is a destructuring pattern.
+
+Unlike @code{pcase-let}, but like @code{let*}, each @var{exp} is
+matched against its corresponding @var{pattern} before passing to the
+next element of @var{bindings}, so the variables introduced in each
+binding are available in the @var{exp}s that follow it, additionally
+to being available in @var{body}.
+@end defmac
+
+@findex dolist
+@defmac pcase-dolist (pattern list) body@dots{}
+This construct executes @var{body} once for each element of
+@var{list}, in a context where the destructuring pattern
+@var{pattern} was matched against the element.
+When @var{pattern} is a simple variable, this ends up being equivalent
+to @code{dolist}.
+@end defmac
+
+
 @node Iteration
 @section Iteration
 @cindex iteration




^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:21                                                                                                     ` Stefan Monnier
@ 2018-10-30 19:54                                                                                                       ` Eli Zaretskii
  2018-10-30 20:44                                                                                                         ` Stefan Monnier
  2018-11-01  1:40                                                                                                         ` Garreau, Alexandre
  2018-10-30 20:04                                                                                                       ` Dmitry Gutov
  1 sibling, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-30 19:54 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Tue, 30 Oct 2018 15:21:52 -0400
> 
> >> +* Destructuring patterns:: Using pcase patterns to extract subfields.
> > We never used "pcase patterns" in the manual before, so I wonder
> > whether we should start now.  If we want to do that, this should be
> > defined before it is used.
> 
> I'm uncomfortable using "pattern" to refer to "pcase pattern" unless the
> context makes it clear.  I'm not completely sure where best to define
> pcase patterns.

I think the best place of defining them is where we first describe
them, i.e. in the section about pcase itself.

> >> +The macros described in this section use @emph{destructuring}
> >> +patterns, which are normal Pcase patterns used in a context where we
> >> +presume that the object does match the pattern, and we only want
> >> +to extract some subfields.
> >
> > I think we need to define "destructuring" here (or elsewhere in the
> > manual, and have a cross-reference there in this section).
> 
> The paragraph you quoted is exactly what I consider the definition of
> "destructuring pattern" (I don't see a need to define "destructuring"
> separately: the word placed in front of "pattern" is here treated as
> a kind of "proper name", just chosen so that it will help some if they
> already know the term from elsewhere, such as cl-destructuring-bind).

The "destructuring" part needs to make sense, or at least we should
strive that it does.  It isn't a random word.

> > Readers that aren't familiar with that term will not be able to
> > understand why this word is used here.  We need to start this with
> > something like
> >
> >   @dfn{Destructuring} means ...
> 
> I'd rather rename those to "Monnier patterns" and avoid the problem, if
> that's what it takes.

No, I think "destructuring" is about right.  How about this text:

  @dfn{Destructuring} of an object is an operation that extracts
  multiple values stored in the object, e.g., the 2nd and the 3rd
  element of a list or a vector.  @dfn{Destructuring binding} is
  similar to a local binding (@pxref{Local Variables}), but it gives
  values to multiple elements of a variable by extracting those values
  from an object of compatible structure.

> > It would also help to tell what exactly makes a pattern a
> > destructuring one.
> 
> As the paragraph says: it's the context in which it's used.

I'm not sure I understand.  AFAIU, not every pattern described in
"pcase Macro" can be a destructuring one.  Right?

> >> +All @var{exp}s are evaluated first after which they are matched
> >> +against their respective @var{pattern}, introducing new variable
> >> +bindings which can then be used inside @var{body}.
> > AFAIU, this means only some of the pcase patterns make sense in this
> > context.  If that is true, I'd suggest ti somehow tell which are (or
> > which aren't, if that's easier).
> 
> Not sure what you're thinking of.

See above: not every pattern can be a destructuring one, AFAIU.

> >> +@defmac pcase-dolist (pattern list) body@dots{}
> >> +This construct executes @var{body} once for each element of
> >> +@var{list}, in a context where the destructuring pattern
> >> +@var{pattern} was matched against the element.
> >
> > I don't think I understand what "in a context where the pattern was
> > matched" means here.  Is any aspect of the match except destructuring
> > bindings relevant to execution of the body?
> 
> No.  But those extra bindings are exactly the context I'm referring to.
> In my work, "context" and "environment" are the usual words used to
> refer to the map that links identifiers to their corresponding
> information (typically, type or value depending on the
> ...ahem... context).

I find this too abstract in general, so I think it's better to be
specific where we can.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:14                                                                                                   ` Alan Mackenzie
@ 2018-10-30 19:56                                                                                                     ` Clément Pit-Claudel
  2018-10-31  0:08                                                                                                       ` Andy Moreton
  0 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-30 19:56 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: emacs-devel

On 30/10/2018 14.14, Alan Mackenzie wrote:
> Hello, Clément.

Hey Alan :)

> On Tue, Oct 30, 2018 at 11:05:55 -0400, Clément Pit-Claudel wrote:
>> On 30/10/2018 10.16, Andy Moreton wrote:
>>> How are users meant to write reliable code using such constructs ?
> 
>> Ensure that the pattern actually matches :)
> 
> You mean, unless you can be 100% sure that the pattern will match, you
> mustn't use pcase-... constructs.  That sounds equivalent to saying you
> shouldn't use these constructs at all.

That's an odd conclusion.

>> IOW, only use these constructs when it's an invariant of your program
>> that the pattern will match the data.  For cases in which the pattern
>> might not match, use pcase instead of pcase-dolist.
> 
> pcase is not a looping construct.  pcase-dolist is.  They're not
> replacements for eachother.

I should have written "use `pcase' with `dolist` instead of `pcase-dolist'".  Concretely, replace this:

(pcase-dolist (pat list) …) 

with this: 

(dolist (xyz list) (pcase xyz (pat …) (_ (handle-error-here))))



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:21                                                                                                     ` Stefan Monnier
  2018-10-30 19:54                                                                                                       ` Eli Zaretskii
@ 2018-10-30 20:04                                                                                                       ` Dmitry Gutov
  2018-10-30 20:46                                                                                                         ` Stefan Monnier
  1 sibling, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-30 20:04 UTC (permalink / raw)
  To: Stefan Monnier, emacs-devel

On 30.10.2018 21:21, Stefan Monnier wrote:
>> It would also help to tell what exactly makes a pattern a
>> destructuring one.
> As the paragraph says: it's the context in which it's used.

Couldn't we also say that a pattern with "holes" is a destructuring 
pattern, not matter if it is used in pcase-let, or just pcase?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:54                                                                                                       ` Eli Zaretskii
@ 2018-10-30 20:44                                                                                                         ` Stefan Monnier
  2018-10-31 15:57                                                                                                           ` Eli Zaretskii
  2018-11-01  1:40                                                                                                         ` Garreau, Alexandre
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 20:44 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

> I think the best place of defining them is where we first describe
> them, i.e. in the section about pcase itself.

That's what I tried to do in the patch I had attached.

> No, I think "destructuring" is about right.  How about this text:
>
>   @dfn{Destructuring} of an object is an operation that extracts
>   multiple values stored in the object, e.g., the 2nd and the 3rd
>   element of a list or a vector.  @dfn{Destructuring binding} is
>   similar to a local binding (@pxref{Local Variables}), but it gives
>   values to multiple elements of a variable by extracting those values
>   from an object of compatible structure.

Fine by me.

>> > It would also help to tell what exactly makes a pattern a
>> > destructuring one.
>> As the paragraph says: it's the context in which it's used.
> I'm not sure I understand.  AFAIU, not every pattern described in
> "pcase Macro" can be a destructuring one.  Right?

A destructuring pattern can bind any number of variables, so I don't see
why we should limit this number to be strictly positive.

A pattern like 'Emacs will not be very useful on its own in pcase-let,
admittedly, but it's perfectly valid to use it (it will just do the same
as _, which is often convenient to use when you don't care about the
value).  And of course, it can even be useful to use it within a larger
pattern, e.g.

    (pcase-let (((or (and 'Emacs (let x 'a))
                     `(,x . ,_))
                 'Emacs))
      x)

will return `a` whereas

    (pcase-let (((or (and 'Emacs (let x 'a))
                     `(,x . ,_))
                 'Typer))
      x)

will signal an error (because it's trying to destructure `Typer` according
to `(,x . ,_)).

> See above: not every pattern can be a destructuring one, AFAIU.

They all can be used as destructuring patterns.  Some are more often
useful than others.

> I find this too abstract in general, so I think it's better to be
> specific where we can.

So, but this is as specific as I can be.  Maybe you'd prefer something
less specific.  See new patch below,


        Stefan


diff --git a/doc/lispref/control.texi b/doc/lispref/control.texi
index 5be4b298b4..06c6622bf0 100644
--- a/doc/lispref/control.texi
+++ b/doc/lispref/control.texi
@@ -477,6 +477,7 @@ Pattern-Matching Conditional
 * The @code{pcase} macro: pcase Macro.  Plus examples and caveats.
 * Extending @code{pcase}: Extending pcase.  Define new kinds of patterns.
 * Backquote-Style Patterns: Backquote Patterns.  Structural matching.
+* Destructuring patterns:: Using pcase patterns to extract subfields.
 @end menu
 
 @node pcase Macro
@@ -497,6 +498,10 @@ pcase Macro
 Otherwise, @code{pcase} evaluates to @code{nil}.
 @end defmac
 
+Each @var{pattern} has to be a @dfn{pcase pattern}, which can either
+use one of the core patterns defined below, or use one of the patterns
+defined via @code{pcase-defmacro}.
+
 The rest of this subsection
 describes different forms of core patterns,
 presents some examples,
@@ -1168,6 +1173,90 @@ Backquote Patterns
 (evaluate '(sub 1 2) nil)                 @result{} error
 @end example
 
+@node Destructuring patterns
+@subsection Destructuring Patterns
+@cindex destructuring patterns
+
+Pcase patterns not only express a condition on the form of the objects
+they can match but they can also extract sub-fields of those objects.
+Say we have a list and want to extract 2 elements from it with the
+following code:
+
+@example
+  (pcase l
+    (`(add ,x ,y)  (message "Contains %S and %S" x y)))
+@end example
+
+This will not only extract @code{x} and @code{y} but will additionally
+test that @code{l} is a list containing exactly 3 elements and whose
+first element is the symbol @code{add}.  If any of those tests fail,
+@code{pcase} will directly return @code{nil} without calling
+@code{message}.
+
+@dfn{Destructuring} of an object is an operation that extracts
+multiple values stored in the object, e.g., the 2nd and the 3rd
+element of a list or a vector.  @dfn{Destructuring binding} is
+similar to a local binding (@pxref{Local Variables}), but it gives
+values to multiple elements of a variable by extracting those values
+from an object of compatible structure.
+
+The macros described in this section use @dfn{destructuring
+patterns}, which are normal Pcase patterns used in a context where we
+presume that the object does match the pattern, and we only want
+to extract some subfields.  For example:
+
+@example
+  (pcase-let ((`(add ,x ,y) l))
+    (message "Contains %S and %S" x y))
+@end example
+
+@noindent
+does the same as the previous example, except that it directly tries
+to extract @code{x} and @code{y} from @code{l} without first verifying
+if @code{l} is a list which has the right number of elements and has
+@code{add} as its first element.
+The precise behavior when the object does not actually match the
+pattern is undefined, although the body will not be silently skipped:
+either an error is signaled or the body is run with some of the
+variables potentially bound to arbitrary values like @code{nil}.
+
+@defmac pcase-let bindings body@dots{}
+Bind variables according to @var{bindings} and then eval @var{body}.
+
+@var{bindings} is a list of bindings of the form @w{@code{(@var{pattern}
+@var{exp})}}, where @var{exp} is an expression to evaluate and
+@var{pattern} is a destructuring pattern.
+
+All @var{exp}s are evaluated first after which they are matched
+against their respective @var{pattern}, introducing new variable
+bindings which can then be used inside @var{body}.
+@end defmac
+
+@defmac pcase-let* bindings body@dots{}
+Bind variables according to @var{bindings} and then eval @var{body}.
+
+@var{bindings} is a list of bindings of the form @code{(@var{pattern}
+@var{exp})}, where @var{exp} is an expression to evaluate and
+@var{pattern} is a destructuring pattern.
+
+Unlike @code{pcase-let}, but like @code{let*}, each @var{exp} is
+matched against its corresponding @var{pattern} before passing to the
+next element of @var{bindings}, so the variables introduced in each
+binding are available in the @var{exp}s that follow it, additionally
+to being available in @var{body}.
+@end defmac
+
+@findex dolist
+@defmac pcase-dolist (pattern list) body@dots{}
+This construct executes @var{body} once for each element of
+@var{list}, in a context where the variables appearing in the the
+destructuring pattern @var{pattern} are bound to the corresponding
+values found in the element.
+When @var{pattern} is a simple variable, this ends up being equivalent
+to @code{dolist}.
+@end defmac
+
+
 @node Iteration
 @section Iteration
 @cindex iteration



^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 20:04                                                                                                       ` Dmitry Gutov
@ 2018-10-30 20:46                                                                                                         ` Stefan Monnier
  2018-10-31 13:41                                                                                                           ` Dmitry Gutov
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-30 20:46 UTC (permalink / raw)
  To: emacs-devel

> Couldn't we also say that a pattern with "holes" is a destructuring pattern,
> not matter if it is used in pcase-let, or just pcase?

We could, but the reason why I'm trying to define a new term (which
I called here "destructuring pattern") is to define what happens with
pcase-let, pcase-dolist, pcase-let* where the pattern is assumed
to match.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:29                                                                                         ` Eli Zaretskii
@ 2018-10-30 22:09                                                                                           ` Michael Heerdegen
  2018-10-31 15:59                                                                                             ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-30 22:09 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > Shall I now work on the `DOESNT-UNQUOTE -> 'DOESNT-UNQUOTE patch?
> Yes, I think so.

I noticed that only about a half of these are pcase patterns.  All other
occurrences are in "normal" code.  I wonder if I should fix them all at
once (would be a bit less work for me)?  We speak about somewhat over
1000 occurrences.

BTW, while preparing the first patch I already found tons of unnecessary
quotes outside of pcase patterns: quotes quoting self-evaluating objects
like strings and numbers.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 17:31                                                                                             ` Stefan Monnier
@ 2018-10-30 23:08                                                                                               ` Michael Heerdegen
  2018-10-31  3:09                                                                                                 ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-30 23:08 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Stefan Monnier <monnier@IRO.UMontreal.CA> writes:

> LGTM, thanks.  We could maybe give a hint about why, e.g. saying that
> there are no guarantees about the order and number of times they are run.

Are these the only restrictions?  Are there even cases where side
effects can still be relied on - e.g. in

#+begin_src emacs-lisp
(pcase EXPR
  ((and P1 (guard (prog1 t (setq x 15))) P2) BODY1)
  ...)
#+end_src

is it legitimate to assume that x has been set to 15 if BODY1 is
evaluated (and P1 and P2 don't touch x)?

Or should we say side effects are generally disallowed - maybe also
because we don't know how this could change in the future?


Thanks,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 13:07                                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
@ 2018-10-30 23:30                                                                                                   ` Eric Abrahamsen
  2018-11-01  0:16                                                                                                   ` Garreau, Alexandre
  1 sibling, 0 replies; 375+ messages in thread
From: Eric Abrahamsen @ 2018-10-30 23:30 UTC (permalink / raw)
  To: emacs-devel

Stefan Monnier <monnier@iro.umontreal.ca> writes:

>> In fact, when you think about it, the "case" nature of pcase is pretty
>> orthogonal to the "match/destructure" nature of pcase. If anything
>
> How do you suggest to split the two in cases like:
>
>     (defun cconv-convert (form env extend)
>       (pcase form
>         (`(,(and letsym (or `let* `let)) ,binders . ,body)
>          ...)
>     
>         (`(,(and `(lambda . ,_) fun) . ,args)
>          ...)

[...]

>...)))
>
> That kind of use is the main motivation behind the design of pcase.
>
> Once you have this, you also trivially cover the `cl-case` uses and you
> can easily make it handle the "destructuring" uses.
> Splitting the two will just require more code to get less flexibility.

Sure, it was just a little realization I had, probably nothing that
should lead to an actual code change.

What I imagined, for a moment there, were matching forms that would look
like "(m ,(and `(lambda . ,_) fun))", or something, and then you could use
that matching form in a cl-case clause, or a lambda argument, or a
dolist variable name. Ie, confining the pattern matching/destructuring
to a form, which could be used in the existing macros/functions like
cl-case or dolist.

I can be safely ignored!

Eric




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-28 21:44                                                                                 ` Stefan Monnier
  2018-10-29 13:01                                                                                   ` Alan Mackenzie
  2018-10-29 14:47                                                                                   ` Andy Moreton
@ 2018-10-30 23:34                                                                                   ` Van L
  2018-10-31  3:14                                                                                     ` Stefan Monnier
  2 siblings, 1 reply; 375+ messages in thread
From: Van L @ 2018-10-30 23:34 UTC (permalink / raw)
  To: Emacs developers


> I obviously can't judge fairly how hard it is to use, but I don't find
> any of the examples posted here as evidence of problematic use and even
> less misuse (they look perfectly correct to me).

That would be because you are an expert and 
you’ve lost reachability to your beginner’s 
mind.


^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:56                                                                                                     ` Clément Pit-Claudel
@ 2018-10-31  0:08                                                                                                       ` Andy Moreton
  2018-10-31  3:19                                                                                                         ` Stefan Monnier
  2018-10-31 16:23                                                                                                         ` Clément Pit-Claudel
  0 siblings, 2 replies; 375+ messages in thread
From: Andy Moreton @ 2018-10-31  0:08 UTC (permalink / raw)
  To: emacs-devel

On Tue 30 Oct 2018, Clément Pit-Claudel wrote:

> On 30/10/2018 14.14, Alan Mackenzie wrote:
>> Hello, Clément.
>
> Hey Alan :)
>
>> On Tue, Oct 30, 2018 at 11:05:55 -0400, Clément Pit-Claudel wrote:
>>> On 30/10/2018 10.16, Andy Moreton wrote:
>>>> How are users meant to write reliable code using such constructs ?
>> 
>>> Ensure that the pattern actually matches :)
>> 
>> You mean, unless you can be 100% sure that the pattern will match, you
>> mustn't use pcase-... constructs.  That sounds equivalent to saying you
>> shouldn't use these constructs at all.
>
> That's an odd conclusion.

It is a perfectly reasonable conclusion. `pcase-exhaustive' is available
as a replacement for `pcase', but a similar exhaustive matcher that
signals an error on pattern match failure is missing for all of the
other pcase constructs.

    AndyM




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:00                                                                                               ` Alan Mackenzie
@ 2018-10-31  0:21                                                                                                 ` Andy Moreton
  0 siblings, 0 replies; 375+ messages in thread
From: Andy Moreton @ 2018-10-31  0:21 UTC (permalink / raw)
  To: emacs-devel

On Tue 30 Oct 2018, Alan Mackenzie wrote:

> Hello, Stefan.
>
> On Tue, Oct 30, 2018 at 14:17:10 -0400, Stefan Monnier wrote:
>> > Not everybody is familiar with dolist by any means.  Is dolist's doc
>> > string of sufficiently high quality to act as this basis?
>
>> If dolist's docstring is not good enough, then I don't think it's
>> pcase-dolist's job to fix it.
>
> I think everybody would agree with this point.
>
>> >> We do have to keep the reference to `pcase` because we don't want to
>> >> repeat the definition of what a pcase pattern can look like.
>
>> > Yes, I think that's right.
>
>> > Things I believe MUST appear explicitly in the doc string for
>> > pcase-dolist: 
>> > 1. It is a loop over the elements of LIST, which must be a list.
>> > 2. It attempts to match the current list element with the supplied
>> > PATTERN, which must be a valid pcase style pattern.
>> > 3. The BODY forms are evaluated for each element of the list.
>> > 4. The purpose of the matching is to create bindings for symbols, and
>> > these bindings are in force when the BODY forms are evaluated.
>> > 5. When a pattern match fails, ..... (This needs to be stated).
>
>> This is highly redundant w.r.t pcase-let and dolist.
>
> Maybe, but so what?
>
> Doc strings should be as far as is reasonable self contained.  Have a
> look at the doc strings for let and let*.  They have a great deal in
> common, but each is self contained.

Exactly. For the pcase macros, the docstrings need to describe what the
arguments are, and what the macro actually does. A reference to `pcase'
itself to describe the patterns is fine.  The last thing in the
docstring should be a reference to the similarly named non-pcase
construct with similar behaviour (which is the least important part).

>> Fine for the manual, but not for docstrings.
>
> You seem to be arguing that doc strings needn't say what
> de{fun,macro,var}s do and are, as long as the meaning can be acquired
> through the traversal of a directed acyclic graph of linked doc strings.
> Maybe you find this a good way of acquiring information, but I certainly
> don't.  I just get angry and frustrated, and I'm sure I'm not the only
> one.

Me too. Docstrings are to educate and inform users, and lead them to
discover new functionality (and hopefully read the manual for more
detailed discussion). A little redundancy of presentation is actually a
good thing if it aids the understanding of non-experts who are trying to
learn.

    AndyM






^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 23:08                                                                                               ` Michael Heerdegen
@ 2018-10-31  3:09                                                                                                 ` Stefan Monnier
  2018-11-05  2:01                                                                                                   ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31  3:09 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

>> LGTM, thanks.  We could maybe give a hint about why, e.g. saying that
>> there are no guarantees about the order and number of times they are run.
> Are these the only restrictions?

I think so, yes.

> Are there even cases where side effects can still be relied on -
> e.g. in
>
> #+begin_src emacs-lisp
> (pcase EXPR
>   ((and P1 (guard (prog1 t (setq x 15))) P2) BODY1)
>   ...)
> #+end_src
>
> is it legitimate to assume that x has been set to 15 if BODY1 is
> evaluated (and P1 and P2 don't touch x)?

Yes: pcase doesn't look inside the `guard`s so in order to get to BODY1
it had to evaluate `(prog1 t (setq x 15))` at some point.

But some of the preds and guards of other branches (both before and
after the one of BODY1) may also be run before getting to BODY1.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 23:34                                                                                   ` Replace trivial pcase occurrences in the Emacs sources Van L
@ 2018-10-31  3:14                                                                                     ` Stefan Monnier
  0 siblings, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31  3:14 UTC (permalink / raw)
  To: emacs-devel

>> I obviously can't judge fairly how hard it is to use, but I don't find
>> any of the examples posted here as evidence of problematic use and even
>> less misuse (they look perfectly correct to me).
>
> That would be because you are an expert and 
> you’ve lost reachability to your beginner’s 
> mind.

That's undoubtly true w.r.t "evidence of problematic use" (so I need
someone to explain to me what's problematic about it since I'm too used
to see it), but not w.r.t misuse where it should not be an obstacle to
judge what is a misuse.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31  0:08                                                                                                       ` Andy Moreton
@ 2018-10-31  3:19                                                                                                         ` Stefan Monnier
  2018-10-31 16:23                                                                                                         ` Clément Pit-Claudel
  1 sibling, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31  3:19 UTC (permalink / raw)
  To: emacs-devel

> It is a perfectly reasonable conclusion. `pcase-exhaustive' is available
> as a replacement for `pcase', but a similar exhaustive matcher that
> signals an error on pattern match failure is missing for all of the
> other pcase constructs.

Their absence is a mere reflection of the fact that noone's found
a concrete use for them yet.  They'd be easy to add (just like
pcase-exhaustive was easy to add once someone found a use for it).


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:58                                                                                                             ` Stefan Monnier
@ 2018-10-31 12:08                                                                                                               ` Alan Mackenzie
  2018-10-31 12:33                                                                                                                 ` Stefan Monnier
  2018-11-03 13:13                                                                                                               ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-31 12:08 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: Eli Zaretskii, emacs-devel

Hello, Stefan.

On Tue, Oct 30, 2018 at 14:58:58 -0400, Stefan Monnier wrote:
> >> matching doesn't assign any values to anything directly related to
> >> BODY, so the mechanism by which it affects execution of BODY needs
> >> to be described.

> > Could you please fill that void?  This isn't a repetition of what
> > dolist does.

> I don't know how to say it any better than with the patch I just
> installed into emacs-26.

Thank you for this patch, which is excellent.  However, the doc string
for pcase-dolist is still not quite perfect, in that:

1. It doesn't say what the macro does.
2. It doesn't document the arguments to the macro.
3. It appears to refer to an argument which don't exist (VAR).
4. It forces somebody new to Lisp to traverse 5 nodes of the graph of doc
strings (namely pcase-dolist, pcase, dolist, pcase-let, let) and
synthesise these disparate doc strings to get an idea of what the macro
does.  This is too many nodes, and the task is too difficult.
5. It states the macro is equivalent to an expansion of other macros,
which appear no easier to understand than pcase-dolist itself.

Otherwise, not bad!

Are you willing to put these final touches onto pcase-dolist's doc
string, or would you prefer somebody else to do it?

>         Stefan

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 12:08                                                                                                               ` Alan Mackenzie
@ 2018-10-31 12:33                                                                                                                 ` Stefan Monnier
  2018-10-31 15:47                                                                                                                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31 12:33 UTC (permalink / raw)
  To: emacs-devel

> Are you willing to put these final touches onto pcase-dolist's doc
> string, or would you prefer somebody else to do it?

This is excrutiating for me.  Anyone else but me, please,


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 20:46                                                                                                         ` Stefan Monnier
@ 2018-10-31 13:41                                                                                                           ` Dmitry Gutov
  2018-10-31 13:52                                                                                                             ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-31 13:41 UTC (permalink / raw)
  To: Stefan Monnier, emacs-devel

On 30.10.2018 22:46, Stefan Monnier wrote:
>> Couldn't we also say that a pattern with "holes" is a destructuring pattern,
>> not matter if it is used in pcase-let, or just pcase?
> 
> We could, but the reason why I'm trying to define a new term (which
> I called here "destructuring pattern") is to define what happens with
> pcase-let, pcase-dolist, pcase-let* where the pattern is assumed
> to match.

I only meant to say that introducing a term that somebody fairly 
familiar with the subject might misinterpret without reading its 
definition in the manual, could be suboptimal.

But don't mind me, I don't have any alternative proposals anyway.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 13:41                                                                                                           ` Dmitry Gutov
@ 2018-10-31 13:52                                                                                                             ` Stefan Monnier
  2018-10-31 15:50                                                                                                               ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31 13:52 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: emacs-devel

>>> Couldn't we also say that a pattern with "holes" is a destructuring pattern,
>>> not matter if it is used in pcase-let, or just pcase?
>> We could, but the reason why I'm trying to define a new term (which
>> I called here "destructuring pattern") is to define what happens with
>> pcase-let, pcase-dolist, pcase-let* where the pattern is assumed
>> to match.
> I only meant to say that introducing a term that somebody fairly familiar
> with the subject might misinterpret without reading its definition in the
> manual, could be suboptimal.

Agreed.

> But don't mind me, I don't have any alternative proposals anyway.

Neither do I,


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 12:33                                                                                                                 ` Stefan Monnier
@ 2018-10-31 15:47                                                                                                                   ` Eli Zaretskii
  2018-10-31 16:07                                                                                                                     ` Alan Mackenzie
  2018-11-03 13:16                                                                                                                     ` Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 15:47 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Wed, 31 Oct 2018 08:33:42 -0400
> 
> > Are you willing to put these final touches onto pcase-dolist's doc
> > string, or would you prefer somebody else to do it?
> 
> This is excrutiating for me.  Anyone else but me, please,

I will try, if no one beats me to it.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 13:52                                                                                                             ` Stefan Monnier
@ 2018-10-31 15:50                                                                                                               ` Eli Zaretskii
  2018-10-31 16:05                                                                                                                 ` Dmitry Gutov
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 15:50 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel, dgutov

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Date: Wed, 31 Oct 2018 09:52:37 -0400
> Cc: emacs-devel@gnu.org
> 
> >>> Couldn't we also say that a pattern with "holes" is a destructuring pattern,
> >>> not matter if it is used in pcase-let, or just pcase?
> >> We could, but the reason why I'm trying to define a new term (which
> >> I called here "destructuring pattern") is to define what happens with
> >> pcase-let, pcase-dolist, pcase-let* where the pattern is assumed
> >> to match.
> > I only meant to say that introducing a term that somebody fairly familiar
> > with the subject might misinterpret without reading its definition in the
> > manual, could be suboptimal.
> 
> Agreed.
> 
> > But don't mind me, I don't have any alternative proposals anyway.
> 
> Neither do I,

Can someone enlighten me regarding those "holes"?  What does that
allude to?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 20:44                                                                                                         ` Stefan Monnier
@ 2018-10-31 15:57                                                                                                           ` Eli Zaretskii
  2018-10-31 19:35                                                                                                             ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 15:57 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Cc: emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 16:44:01 -0400
> 
> See new patch below,

Thanks, I think it should go in.  We can always improve it later if we
want.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 22:09                                                                                           ` Michael Heerdegen
@ 2018-10-31 15:59                                                                                             ` Eli Zaretskii
  2018-10-31 19:37                                                                                               ` Stefan Monnier
  2018-10-31 20:31                                                                                               ` Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 15:59 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 23:09:47 +0100
> 
> Eli Zaretskii <eliz@gnu.org> writes:
> 
> > > Shall I now work on the `DOESNT-UNQUOTE -> 'DOESNT-UNQUOTE patch?
> > Yes, I think so.
> 
> I noticed that only about a half of these are pcase patterns.  All other
> occurrences are in "normal" code.  I wonder if I should fix them all at
> once (would be a bit less work for me)?  We speak about somewhat over
> 1000 occurrences.

Not sure I follow: fixing _all_ of them will be _less_ work for you?

I'm okay with only fixing pcase usage at this time, if you feel that
would be enough for one changeset.

> BTW, while preparing the first patch I already found tons of unnecessary
> quotes outside of pcase patterns: quotes quoting self-evaluating objects
> like strings and numbers.

Really?  Can you show a few examples?  Maybe there's something wrong
with our documentation if people make such mistakes.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 15:50                                                                                                               ` Eli Zaretskii
@ 2018-10-31 16:05                                                                                                                 ` Dmitry Gutov
  2018-10-31 16:13                                                                                                                   ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-31 16:05 UTC (permalink / raw)
  To: Eli Zaretskii, Stefan Monnier; +Cc: emacs-devel

On 31.10.2018 17:50, Eli Zaretskii wrote:

>>>>> Couldn't we also say that a pattern with "holes" is a destructuring pattern,
>>>>> not matter if it is used in pcase-let, or just pcase?
>>>> We could, but the reason why I'm trying to define a new term (which
>>>> I called here "destructuring pattern") is to define what happens with
>>>> pcase-let, pcase-dolist, pcase-let* where the pattern is assumed
>>>> to match.
>>> I only meant to say that introducing a term that somebody fairly familiar
>>> with the subject might misinterpret without reading its definition in the
>>> manual, could be suboptimal.
>>
>> Agreed.
>>
>>> But don't mind me, I don't have any alternative proposals anyway.
>>
>> Neither do I,
> 
> Can someone enlighten me regarding those "holes"?  What does that
> allude to?

I stole the term from Clement here: 
http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 15:47                                                                                                                   ` Eli Zaretskii
@ 2018-10-31 16:07                                                                                                                     ` Alan Mackenzie
  2018-10-31 16:20                                                                                                                       ` Eli Zaretskii
  2018-11-03 13:16                                                                                                                     ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Alan Mackenzie @ 2018-10-31 16:07 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

Hello, Eli.

On Wed, Oct 31, 2018 at 17:47:26 +0200, Eli Zaretskii wrote:
> > From: Stefan Monnier <monnier@iro.umontreal.ca>
> > Date: Wed, 31 Oct 2018 08:33:42 -0400

> > > Are you willing to put these final touches onto pcase-dolist's doc
> > > string, or would you prefer somebody else to do it?

> > This is excrutiating for me.  Anyone else but me, please,

> I will try, if no one beats me to it.

A beating attempt, first draught:

    (pcase-dolist (PATTERN LIST) BODY...)

    Loop over a list.

    Evaluate BODY with bindings made by matching PATTERN to each
    element of LIST in turn.  PATTERN is a pcase pattern, the
    matching being done as described in `pcase'.  The return value is
    not significant.

    Should the matching fail for any LIST element, the results are
    undefined.

    See also `dolist'

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:05                                                                                                                 ` Dmitry Gutov
@ 2018-10-31 16:13                                                                                                                   ` Eli Zaretskii
  2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
                                                                                                                                       ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 16:13 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: monnier, emacs-devel

> Cc: emacs-devel@gnu.org
> From: Dmitry Gutov <dgutov@yandex.ru>
> Date: Wed, 31 Oct 2018 18:05:44 +0200
> 
> > Can someone enlighten me regarding those "holes"?  What does that
> > allude to?
> 
> I stole the term from Clement here: 
> http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html

Ah, the elements that are assigned by destructuring?  I indeed hoped
we could identify in some way the patterns which satisfy that
condition.  I didn't give up yet.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:07                                                                                                                     ` Alan Mackenzie
@ 2018-10-31 16:20                                                                                                                       ` Eli Zaretskii
  2018-11-01  8:36                                                                                                                         ` Achim Gratz
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 16:20 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: monnier, emacs-devel

> Date: Wed, 31 Oct 2018 16:07:29 +0000
> Cc: Stefan Monnier <monnier@iro.umontreal.ca>, emacs-devel@gnu.org
> From: Alan Mackenzie <acm@muc.de>
> 
> > I will try, if no one beats me to it.
> 
> A beating attempt, first draught:
> 
>     (pcase-dolist (PATTERN LIST) BODY...)
> 
>     Loop over a list.
> 
>     Evaluate BODY with bindings made by matching PATTERN to each
>     element of LIST in turn.  PATTERN is a pcase pattern, the
>     matching being done as described in `pcase'.  The return value is
>     not significant.
> 
>     Should the matching fail for any LIST element, the results are
>     undefined.
> 
>     See also `dolist'

Thanks.

I think we can do better in this part:

    Evaluate BODY with bindings made by matching PATTERN to each
    element of LIST in turn.  PATTERN is a pcase pattern

I think using "matching" here is detrimental to understanding what's
going on, which is a destructuring binding that uses pcase patterns.
(The "matching" here is between the structures of PATTERN and elements
of LIST, but the usual meaning of "matching" in Emacs is different,
especially when "patterns" are mentioned nearby.  So we should not use
"matching" here, at least not without significant qualifiers, like
"structure matching" or somesuch.)

And this:

    Should the matching fail for any LIST element, the results are
    undefined.

should be reworded to explain that elements of LIST should have a
structure compatible with PATTERN, so that the destructuring works.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31  0:08                                                                                                       ` Andy Moreton
  2018-10-31  3:19                                                                                                         ` Stefan Monnier
@ 2018-10-31 16:23                                                                                                         ` Clément Pit-Claudel
  2018-11-01 14:44                                                                                                           ` Andy Moreton
  1 sibling, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-31 16:23 UTC (permalink / raw)
  To: emacs-devel

On 30/10/2018 20.08, Andy Moreton wrote:
> On Tue 30 Oct 2018, Clément Pit-Claudel wrote:
> 
>> On 30/10/2018 14.14, Alan Mackenzie wrote:
>>> Hello, Clément.
>>
>> Hey Alan :)
>>
>>> On Tue, Oct 30, 2018 at 11:05:55 -0400, Clément Pit-Claudel wrote:
>>>> On 30/10/2018 10.16, Andy Moreton wrote:
>>>>> How are users meant to write reliable code using such constructs ?
>>>
>>>> Ensure that the pattern actually matches :)
>>>
>>> You mean, unless you can be 100% sure that the pattern will match, you
>>> mustn't use pcase-... constructs.  That sounds equivalent to saying you
>>> shouldn't use these constructs at all.
>>
>> That's an odd conclusion.
> 
> It is a perfectly reasonable conclusion. 

Why?  A large number of ELisp functions don't say what they do if their argument isn't of the expected type, or doesn't have the expected structure.  If you're not 100% sure that the argument has the right type, you shouldn't use them (instead, you should do an appropriate check first).  This is not equivalent to saying that they shouldn't be used at all.

I don't understand what's so special about pcase-*.  Functions like lookup-key or define-key don't tell you what happens if you pass something else that a keymap; does that mean you should never use them? Same for a function like `c-common-init' in cc-mode (the doc doesn't tell you what happens if you pass a symbol that isn't a mode; AFAICT, if you do, you get an error but the current buffer is left in a broken state.

This is a pattern across most ELisp functions, really: if you pass them the wrong thing, some do sanity checks and exit cleanly, some exit silently, some raise a seemingly unrelated error, etc. Most of them don't document that behavior (some, like car and cdr, do).

If pcase-dolist, pcase-let, or pcase-lambda happen across a value that doesn't match the pattern, they'll typically raise an error; that behavior isn't guaranteed, so you're not supposed to rely on it. The docs point it out. We can debate whether they should be amended to have more predictable behavior in the face of match failures, but it's sounds like a real stretch to conclude that they shouldn't be used at all use them at all.

Clément.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:13                                                                                                                   ` Eli Zaretskii
@ 2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
  2018-10-31 16:33                                                                                                                       ` Dmitry Gutov
                                                                                                                                         ` (2 more replies)
  2018-10-31 17:48                                                                                                                     ` Clément Pit-Claudel
  2018-11-03 13:15                                                                                                                     ` Eli Zaretskii
  2 siblings, 3 replies; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-31 16:27 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

On 31.10.2018 18:13, Eli Zaretskii wrote:

> Ah, the elements that are assigned by destructuring?  I indeed hoped
> we could identify in some way the patterns which satisfy that
> condition.  I didn't give up yet.

Yeah, so we could say a pattern is a "destructuring" one if it 
introduces new bindings, so to speak.

Not sure if it will help with the manual entries, though.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
@ 2018-10-31 16:33                                                                                                                       ` Dmitry Gutov
  2018-10-31 16:54                                                                                                                         ` Eli Zaretskii
  2018-10-31 16:52                                                                                                                       ` Eli Zaretskii
  2018-10-31 18:55                                                                                                                       ` Michael Heerdegen
  2 siblings, 1 reply; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-31 16:33 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

On 31.10.2018 18:27, Dmitry Gutov wrote:
> On 31.10.2018 18:13, Eli Zaretskii wrote:
> 
>> Ah, the elements that are assigned by destructuring?  I indeed hoped
>> we could identify in some way the patterns which satisfy that
>> condition.  I didn't give up yet.
> 
> Yeah, so we could say a pattern is a "destructuring" one if it 
> introduces new bindings, so to speak.
> 
> Not sure if it will help with the manual entries, though.

...after all, a destructuring construct like pcase-dolist or pcase-let 
doesn't *have to* be used with destructuring patterns as defined above.

It would simply be pointless to do otherwise, most of the time, but they 
can be used with simple ones, too.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
  2018-10-31 16:33                                                                                                                       ` Dmitry Gutov
@ 2018-10-31 16:52                                                                                                                       ` Eli Zaretskii
  2018-10-31 18:55                                                                                                                       ` Michael Heerdegen
  2 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 16:52 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: monnier, emacs-devel

> Cc: monnier@IRO.UMontreal.CA, emacs-devel@gnu.org
> From: Dmitry Gutov <dgutov@yandex.ru>
> Date: Wed, 31 Oct 2018 18:27:04 +0200
> 
> On 31.10.2018 18:13, Eli Zaretskii wrote:
> 
> > Ah, the elements that are assigned by destructuring?  I indeed hoped
> > we could identify in some way the patterns which satisfy that
> > condition.  I didn't give up yet.
> 
> Yeah, so we could say a pattern is a "destructuring" one if it 
> introduces new bindings, so to speak.

Something like that, yes.  I'm still looking for the right wording.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:33                                                                                                                       ` Dmitry Gutov
@ 2018-10-31 16:54                                                                                                                         ` Eli Zaretskii
  2018-10-31 16:58                                                                                                                           ` Dmitry Gutov
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 16:54 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: monnier, emacs-devel

> From: Dmitry Gutov <dgutov@yandex.ru>
> Cc: monnier@IRO.UMontreal.CA, emacs-devel@gnu.org
> Date: Wed, 31 Oct 2018 18:33:43 +0200
> 
> ...after all, a destructuring construct like pcase-dolist or pcase-let 
> doesn't *have to* be used with destructuring patterns as defined above.
> 
> It would simply be pointless to do otherwise, most of the time, but they 
> can be used with simple ones, too.

I think it is important to explain which patterns make most sense in
these macros.  That other patterns can be used with little or no
usefulness shouldn't deter us from saying what _is_ useful.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:54                                                                                                                         ` Eli Zaretskii
@ 2018-10-31 16:58                                                                                                                           ` Dmitry Gutov
  0 siblings, 0 replies; 375+ messages in thread
From: Dmitry Gutov @ 2018-10-31 16:58 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

On 31.10.2018 18:54, Eli Zaretskii wrote:

> I think it is important to explain which patterns make most sense in
> these macros.  That other patterns can be used with little or no
> usefulness shouldn't deter us from saying what _is_ useful.

Agreed.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:13                                                                                                                   ` Eli Zaretskii
  2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
@ 2018-10-31 17:48                                                                                                                     ` Clément Pit-Claudel
  2018-10-31 18:11                                                                                                                       ` Eli Zaretskii
  2018-11-01  1:34                                                                                                                       ` Garreau, Alexandre
  2018-11-03 13:15                                                                                                                     ` Eli Zaretskii
  2 siblings, 2 replies; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-31 17:48 UTC (permalink / raw)
  To: emacs-devel

On 31/10/2018 12.13, Eli Zaretskii wrote:
>> Cc: emacs-devel@gnu.org
>> From: Dmitry Gutov <dgutov@yandex.ru>
>> Date: Wed, 31 Oct 2018 18:05:44 +0200
>>
>>> Can someone enlighten me regarding those "holes"?  What does that
>>> allude to?
>>
>> I stole the term from Clement here: 
>> http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html
> 
> Ah, the elements that are assigned by destructuring?  I indeed hoped
> we could identify in some way the patterns which satisfy that
> condition.  I didn't give up yet.

Regarding the word "holes": I think these ","-prefixed symbols are typically called "pattern-matching variables", or "placeholders".  "holes" is the more colloquial term, the idea being that if you "fill" the "holes" in the pattern with the appropriate values, you get the original data back (formally, you perform a "substitution" of the "placeholders").

Regarding the term "destructuring pattern": I think it's perfect.  The only other decent alternative I can think of would be "variable-binding pattern".

Clément.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 17:48                                                                                                                     ` Clément Pit-Claudel
@ 2018-10-31 18:11                                                                                                                       ` Eli Zaretskii
  2018-10-31 18:28                                                                                                                         ` Clément Pit-Claudel
  2018-11-01  1:34                                                                                                                       ` Garreau, Alexandre
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 18:11 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
> Date: Wed, 31 Oct 2018 13:48:42 -0400
> 
> >> I stole the term from Clement here: 
> >> http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html
> > 
> > Ah, the elements that are assigned by destructuring?  I indeed hoped
> > we could identify in some way the patterns which satisfy that
> > condition.  I didn't give up yet.
> 
> Regarding the word "holes": I think these ","-prefixed symbols are typically called "pattern-matching variables", or "placeholders".  "holes" is the more colloquial term, the idea being that if you "fill" the "holes" in the pattern with the appropriate values, you get the original data back (formally, you perform a "substitution" of the "placeholders").

I actually think you meant "slots", not "holes".

> Regarding the term "destructuring pattern": I think it's perfect.

But the pattern is not the one that destructures.  So I think
"pattern-based destructuring" or "destructuring using patterns" would
be better.  Or something like that.  I'm still looking for an
appropriate term.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 18:11                                                                                                                       ` Eli Zaretskii
@ 2018-10-31 18:28                                                                                                                         ` Clément Pit-Claudel
  2018-10-31 18:33                                                                                                                           ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-31 18:28 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

On 31/10/2018 14.11, Eli Zaretskii wrote:
>> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
>> Date: Wed, 31 Oct 2018 13:48:42 -0400
>>
>>>> I stole the term from Clement here: 
>>>> http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html
>>>
>>> Ah, the elements that are assigned by destructuring?  I indeed hoped
>>> we could identify in some way the patterns which satisfy that
>>> condition.  I didn't give up yet.
>>
>> Regarding the word "holes": I think these ","-prefixed symbols are typically called "pattern-matching variables", or "placeholders".  "holes" is the more colloquial term, the idea being that if you "fill" the "holes" in the pattern with the appropriate values, you get the original data back (formally, you perform a "substitution" of the "placeholders").
> 
> I actually think you meant "slots", not "holes".

No, I meant holes :) I've seen that term used both with patterns (see e.g. http://people.cs.uchicago.edu/~blume/classes/aut2008/proglang/handouts/lec-sml.pdf) and contexts (http://homepages.inf.ed.ac.uk/slindley/papers/many-holes.pdf).

>> Regarding the term "destructuring pattern": I think it's perfect.
> 
> But the pattern is not the one that destructures.  So I think
> "pattern-based destructuring" or "destructuring using patterns" would
> be better.  Or something like that.  I'm still looking for an
> appropriate term.

I think I don't understand what kind of term you're looking for, then :/
A "destructuring pattern" is a thing; "destructuring using patterns" is an action.

Sorry for the noise if I'm misunderstanding something.
Clément




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 18:28                                                                                                                         ` Clément Pit-Claudel
@ 2018-10-31 18:33                                                                                                                           ` Eli Zaretskii
  2018-10-31 19:00                                                                                                                             ` Yuri Khan
                                                                                                                                               ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 18:33 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

> Cc: emacs-devel@gnu.org
> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
> Date: Wed, 31 Oct 2018 14:28:45 -0400
> 
> > But the pattern is not the one that destructures.  So I think
> > "pattern-based destructuring" or "destructuring using patterns" would
> > be better.  Or something like that.  I'm still looking for an
> > appropriate term.
> 
> I think I don't understand what kind of term you're looking for, then :/
> A "destructuring pattern" is a thing; "destructuring using patterns" is an action.

A thing can be called "destructuring" if it destructures something.
It's like a "flying carpet": the carpet that flies.  But in our case
the patterns don't destructure anything, they are a means for
destructuring.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
  2018-10-31 16:33                                                                                                                       ` Dmitry Gutov
  2018-10-31 16:52                                                                                                                       ` Eli Zaretskii
@ 2018-10-31 18:55                                                                                                                       ` Michael Heerdegen
  2018-10-31 19:23                                                                                                                         ` Eli Zaretskii
  2 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-31 18:55 UTC (permalink / raw)
  To: Dmitry Gutov; +Cc: Eli Zaretskii, monnier, emacs-devel

Dmitry Gutov <dgutov@yandex.ru> writes:

> Yeah, so we could say a pattern is a "destructuring" one if it
> introduces new bindings, so to speak.

I wouldn't call a `let' or `app' pattern that introduces a new binding
destructuring per se.  OTOH, I would call a pattern using ` that tests
e.g. the car of the matched object with e.g. `pred' destructuring even
if that car is not bound to a variable.

With other words: I would say a pattern where subpatterns are matched
against parts of a compound object is desctructuring.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 18:33                                                                                                                           ` Eli Zaretskii
@ 2018-10-31 19:00                                                                                                                             ` Yuri Khan
  2018-10-31 19:20                                                                                                                               ` Eli Zaretskii
  2018-10-31 19:21                                                                                                                             ` Clément Pit-Claudel
  2018-10-31 20:03                                                                                                                             ` Stefan Monnier
  2 siblings, 1 reply; 375+ messages in thread
From: Yuri Khan @ 2018-10-31 19:00 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Clément Pit-Claudel, Emacs developers

On Thu, Nov 1, 2018 at 1:34 AM Eli Zaretskii <eliz@gnu.org> wrote:

> A thing can be called "destructuring" if it destructures something.
> It's like a "flying carpet": the carpet that flies.  But in our case
> the patterns don't destructure anything, they are a means for
> destructuring.

The construct “<verb>ing <noun>” could alternatively be parsed as
“<gerund> <noun>”, with the gerund in the role of a determiner, e.g.:
a “walking stick” is a stick that is used for walking, or a “thinking
cap” is a cap for thinking. They don’t walk and think on their own,
but are tools used in a specific activity.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:00                                                                                                                             ` Yuri Khan
@ 2018-10-31 19:20                                                                                                                               ` Eli Zaretskii
  2018-11-01  0:11                                                                                                                                 ` Dmitry Gutov
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 19:20 UTC (permalink / raw)
  To: Yuri Khan; +Cc: cpitclaudel, emacs-devel

> From: Yuri Khan <yurivkhan@gmail.com>
> Date: Thu, 1 Nov 2018 02:00:39 +0700
> Cc: Clément Pit-Claudel <cpitclaudel@gmail.com>, 
> 	Emacs developers <emacs-devel@gnu.org>
> 
> a “walking stick” is a stick that is used for walking, or a “thinking
> cap” is a cap for thinking. They don’t walk and think on their own,
> but are tools used in a specific activity.

No, they are tools that help in that activity: the stick helps in
walking, the hat helps thinking.

By contrast, those patterns don't "help" destructuring in any way I
could spot.

In any case, even if we can find some convoluted justification for
"destructuring patterns", I think it's worth our while to try to look
for better terminology that doesn't need so many words to explain it,
but instead speaks for itself.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 18:33                                                                                                                           ` Eli Zaretskii
  2018-10-31 19:00                                                                                                                             ` Yuri Khan
@ 2018-10-31 19:21                                                                                                                             ` Clément Pit-Claudel
  2018-10-31 19:29                                                                                                                               ` Eli Zaretskii
  2018-10-31 20:03                                                                                                                             ` Stefan Monnier
  2 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-31 19:21 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

On 31/10/2018 14.33, Eli Zaretskii wrote:
>> Cc: emacs-devel@gnu.org
>> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
>> Date: Wed, 31 Oct 2018 14:28:45 -0400
>>
>>> But the pattern is not the one that destructures.  So I think
>>> "pattern-based destructuring" or "destructuring using patterns" would
>>> be better.  Or something like that.  I'm still looking for an
>>> appropriate term.
>>
>> I think I don't understand what kind of term you're looking for, then :/
>> A "destructuring pattern" is a thing; "destructuring using patterns" is an action.
> 
> A thing can be called "destructuring" if it destructures something.
> It's like a "flying carpet": the carpet that flies.  But in our case
> the patterns don't destructure anything, they are a means for
> destructuring.

But something can also be called "destructuring" if it's used *for* destructuring: a "swimming pool" is not a pool that swims, it's a pool that's used for swimming.  I think of "destructuring" in "destructuring pattern" as a gerund, not a present participle:<we have "shopping lists" and "shaving cream", so why not "destructuring patterns"? :)

Clément.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 18:55                                                                                                                       ` Michael Heerdegen
@ 2018-10-31 19:23                                                                                                                         ` Eli Zaretskii
  2018-10-31 19:50                                                                                                                           ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 19:23 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel, monnier, dgutov

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Eli Zaretskii <eliz@gnu.org>,  monnier@IRO.UMontreal.CA,  emacs-devel@gnu.org
> Date: Wed, 31 Oct 2018 19:55:23 +0100
> 
> I wouldn't call a `let' or `app' pattern that introduces a new binding
> destructuring per se.  OTOH, I would call a pattern using ` that tests
> e.g. the car of the matched object with e.g. `pred' destructuring even
> if that car is not bound to a variable.

Can you give an example?  I don't think I follow.

> With other words: I would say a pattern where subpatterns are matched
> against parts of a compound object is desctructuring.

But note that your generalization is inconsistent with your example:
there's no "pattern matching" in the example, there's only a "matched
object", which is a matching of an entirely different kind.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:21                                                                                                                             ` Clément Pit-Claudel
@ 2018-10-31 19:29                                                                                                                               ` Eli Zaretskii
  2018-10-31 19:31                                                                                                                                 ` Clément Pit-Claudel
                                                                                                                                                   ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 19:29 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

> Cc: emacs-devel@gnu.org
> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
> Date: Wed, 31 Oct 2018 15:21:05 -0400
> 
> But something can also be called "destructuring" if it's used *for* destructuring: a "swimming pool" is not a pool that swims, it's a pool that's used for swimming.  I think of "destructuring" in "destructuring pattern" as a gerund, not a present participle:<we have "shopping lists" and "shaving cream", so why not "destructuring patterns"? :)

They are a kind of jargon.  Try to explain that to a Martian.  Or even
to a non-native English speakers.  I speak a couple of languages other
than English, and none of them has "swimming pools" and "shopping
lists", verbatim.

Anyway, I think this argument is futile.  I'm trying to find a better
terminology that doesn't need explaining; I don't think anyone should
have a problem with a clearer terminology.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:29                                                                                                                               ` Eli Zaretskii
@ 2018-10-31 19:31                                                                                                                                 ` Clément Pit-Claudel
  2018-10-31 20:36                                                                                                                                   ` Eli Zaretskii
  2018-11-01  0:13                                                                                                                                 ` Dmitry Gutov
  2018-11-01  1:31                                                                                                                                 ` Garreau, Alexandre
  2 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-10-31 19:31 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

On 31/10/2018 15.29, Eli Zaretskii wrote:
>> Cc: emacs-devel@gnu.org From: Clément Pit-Claudel
>> <cpitclaudel@gmail.com> Date: Wed, 31 Oct 2018 15:21:05 -0400
>> 
>> But something can also be called "destructuring" if it's used *for*
>> destructuring: a "swimming pool" is not a pool that swims, it's a
>> pool that's used for swimming.  I think of "destructuring" in
>> "destructuring pattern" as a gerund, not a present participle:<we
>> have "shopping lists" and "shaving cream", so why not
>> "destructuring patterns"? :)
> 
> They are a kind of jargon.  Try to explain that to a Martian.  Or
> even to a non-native English speakers.

You're talking to one :)

> Anyway, I think this argument is futile.  

OK, apologies.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 15:57                                                                                                           ` Eli Zaretskii
@ 2018-10-31 19:35                                                                                                             ` Stefan Monnier
  0 siblings, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31 19:35 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel

> Thanks, I think it should go in.  We can always improve it later if we
> want.

Done, thanks,


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 15:59                                                                                             ` Eli Zaretskii
@ 2018-10-31 19:37                                                                                               ` Stefan Monnier
  2018-10-31 20:31                                                                                               ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31 19:37 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Michael Heerdegen, emacs-devel

> Really?  Can you show a few examples?  Maybe there's something wrong
> with our documentation if people make such mistakes.

I don't think calling them mistakes is right.  It might just be
a stylistic preference on the part of the author, or it can be the
result of evolution of code (where the data started as non-self-quoting
and the quote wasn't removed when the data changed), but it still
perfectly valid.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:23                                                                                                                         ` Eli Zaretskii
@ 2018-10-31 19:50                                                                                                                           ` Michael Heerdegen
  2018-10-31 20:05                                                                                                                             ` Eli Zaretskii
  2018-10-31 20:06                                                                                                                             ` Stefan Monnier
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-31 19:50 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel, monnier, dgutov

Eli Zaretskii <eliz@gnu.org> writes:

> > I wouldn't call a `let' or `app' pattern that introduces a new binding
> > destructuring per se.  OTOH, I would call a pattern using ` that tests
> > e.g. the car of the matched object with e.g. `pred' destructuring even
> > if that car is not bound to a variable.
>
> Can you give an example?  I don't think I follow.

(pcase '(1 2 3)
  ((let a 3) a))
==> 3

Is the used pattern destructuring?  It binds a variable.

Or

(pcase '(1 2 3)
  ((app (lambda (thing) 27) x) x))
==> 27

As in the above example, the pattern ignores the given object.  OTOH,
when you use `app' with a function like `car' (the ` pcase macro is
defined like this), it can be used for destructuring.  The feature to
bind variables is totally orthogonal to destructuring.  The two are
often used together, however, but that shouldn't let us confuse these
two different things.

> > With other words: I would say a pattern where subpatterns are matched
> > against parts of a compound object is desctructuring.
>
> But note that your generalization is inconsistent with your example:
> there's no "pattern matching" in the example, there's only a "matched
> object", which is a matching of an entirely different kind.

I think it is.  I mean a pattern like `(,a ,b) is destructuring,
independently from the object being matched, because when used for
matching it (tries to) extract parts of a compound object and tests
these with subpatterns (a, b in this case).  The pattern fails to match
objects that are not compound or have the wrong structure.  But trying
to use the pattern for matching tries to extract and analyse the parts
of any object.  That's why I would call the pattern destructuring.

To give an exact accurate definition is nearly impossible, however.  For
example, is

  (or 'foo `(,a ,b))

desctructuring?

Is

 (pred some-fun)

destructuring if SOME-FUN may look at the parts of its argument?  How
would you define that?

I don't think "destructuring" is such a good term to use in the docs,
apart from giving a hint what ` is about.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 18:33                                                                                                                           ` Eli Zaretskii
  2018-10-31 19:00                                                                                                                             ` Yuri Khan
  2018-10-31 19:21                                                                                                                             ` Clément Pit-Claudel
@ 2018-10-31 20:03                                                                                                                             ` Stefan Monnier
  2018-11-01  0:07                                                                                                                               ` Dmitry Gutov
  2 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31 20:03 UTC (permalink / raw)
  To: emacs-devel

> A thing can be called "destructuring" if it destructures something.
> It's like a "flying carpet": the carpet that flies.  But in our case
> the patterns don't destructure anything, they are a means for
> destructuring.

And let's not forget that what I used this term currently is to talk
about the specific way pcase patterns are used within pcase-let
(i.e. the way pcase-let and friends skip the tests to verify that the
pattern does match).

So maybe we should just say "a pattern used to destructure" to clarify
that it's not a property of the pattern but of the way it's being used.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:50                                                                                                                           ` Michael Heerdegen
@ 2018-10-31 20:05                                                                                                                             ` Eli Zaretskii
  2018-10-31 20:41                                                                                                                               ` Michael Heerdegen
  2018-10-31 20:06                                                                                                                             ` Stefan Monnier
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 20:05 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel, monnier, dgutov

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: dgutov@yandex.ru,  monnier@IRO.UMontreal.CA,  emacs-devel@gnu.org
> Date: Wed, 31 Oct 2018 20:50:58 +0100
> 
> Eli Zaretskii <eliz@gnu.org> writes:
> 
> > > I wouldn't call a `let' or `app' pattern that introduces a new binding
> > > destructuring per se.  OTOH, I would call a pattern using ` that tests
> > > e.g. the car of the matched object with e.g. `pred' destructuring even
> > > if that car is not bound to a variable.
> >
> > Can you give an example?  I don't think I follow.
> 
> (pcase '(1 2 3)
>   ((let a 3) a))
> ==> 3

Thanks, but I meant an example of what's described after the "OTOH".

> To give an exact accurate definition is nearly impossible, however.

That's not what I'm after.  I'm after a definition that's usable and
useful in practice, even if it has to be slightly inaccurate.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:50                                                                                                                           ` Michael Heerdegen
  2018-10-31 20:05                                                                                                                             ` Eli Zaretskii
@ 2018-10-31 20:06                                                                                                                             ` Stefan Monnier
  2018-10-31 20:12                                                                                                                               ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-10-31 20:06 UTC (permalink / raw)
  To: emacs-devel

> (pcase '(1 2 3)
>   ((let a 3) a))
> ==> 3
>
> Is the used pattern destructuring?  It binds a variable.

I think it's not worth trying to define precisely which patterns are
"destructuring" and which aren't.  We can just show two clear examples,
like a 'emacs pattern and a `(,a . ,b) pattern to contrast the two.


        Stefan




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:06                                                                                                                             ` Stefan Monnier
@ 2018-10-31 20:12                                                                                                                               ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 20:12 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@iro.umontreal.ca>
> Date: Wed, 31 Oct 2018 16:06:38 -0400
> 
> I think it's not worth trying to define precisely which patterns are
> "destructuring" and which aren't.  We can just show two clear examples,
> like a 'emacs pattern and a `(,a . ,b) pattern to contrast the two.

Agreed.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 15:59                                                                                             ` Eli Zaretskii
  2018-10-31 19:37                                                                                               ` Stefan Monnier
@ 2018-10-31 20:31                                                                                               ` Michael Heerdegen
  2018-10-31 23:33                                                                                                 ` Garreau, Alexandre
                                                                                                                   ` (3 more replies)
  1 sibling, 4 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-31 20:31 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

[-- Attachment #1: Type: text/plain, Size: 1243 bytes --]

Eli Zaretskii <eliz@gnu.org> writes:

> > I noticed that only about a half of these are pcase patterns.  All
> > other occurrences are in "normal" code.  I wonder if I should fix
> > them all at once (would be a bit less work for me)?  We speak about
> > somewhat over 1000 occurrences.
>
> Not sure I follow: fixing _all_ of them will be _less_ work for you?

I mean less work in summa.

> I'm okay with only fixing pcase usage at this time, if you feel that
> would be enough for one changeset.

It would be ok for me to do both at once if that's also ok for you.

> > BTW, while preparing the first patch I already found tons of
> > unnecessary quotes outside of pcase patterns: quotes quoting
> > self-evaluating objects like strings and numbers.
>
> Really?  Can you show a few examples?  Maybe there's something wrong
> with our documentation if people make such mistakes.

Here is the result of a quick search.  As Stefan said, I don't say we
should fix (all of) these.  But some really look strange.  There are
many quoted strings - I wonder if these quotes change the behavior of
the compiler or so?  I tiny fraction of the matches may be cases where
the quote is significant, e.g. when located in a quoted structure, like
in '('1).


[-- Attachment #2: un-quoted.txt --]
[-- Type: text/plain, Size: 15416 bytes --]

;;; ** Search the Emacs Elisp sources for
`',(or
    (pred keywordp)
    (pred numberp)
    (pred stringp))

;;; ** 509 matches in 50 files:



;;; *** /home/micha/software/emacs/lisp/allout.el  (1 match)

;;;; Line 5138
':


;;; *** /home/micha/software/emacs/lisp/cus-edit.el  (2 matches)

;;;; Line 4711
':style

;;;; Line 4712
':selected


;;; *** /home/micha/software/emacs/lisp/cus-load.el  (154 matches)

;;;; Line 929
'"20.4"

;;;; Line 931
'"21.1"

;;;; Line 933
'"21.1"

;;;; Line 941
'"23.1"

;;;; Line 943
'"21.1"

;;;; Line 945
'"21.1"

;;;; Line 947
'"20.3"

;;;; Line 949
'"22.1"

;;;; Line 951
'"20.3"

;;;; Line 953
'"22.1"

;;;; Line 955
'"21.1"

;;;; Line 957
'"21.1"

;;;; Line 959
'"22.2"

;;;; Line 961
'"20"

;;;; Line 964
'"20"

;;;; Line 967
'"20"

;;;; Line 970
'"20"

;;;; Line 973
'"20"

;;;; Line 976
'"20"

;;;; Line 979
'"20"

;;;; Line 982
'"20"

;;;; Line 985
'"20"

;;;; Line 988
'"20"

;;;; Line 991
'"20"

;;;; Line 993
'"21.1"

;;;; Line 995
'"21.1"

;;;; Line 997
'"24.1"

;;;; Line 999
'"23.1"

;;;; Line 1001
'"23.1"

;;;; Line 1003
'"23.1"

;;;; Line 1006
'"24.3"

;;;; Line 1008
'"24.3"

;;;; Line 1010
'"21.1"

;;;; Line 1015
'"21.1"

;;;; Line 1017
'"25.1"

;;;; Line 1019
'"22.1"

;;;; Line 1021
'"23.1"

;;;; Line 1023
'"21.1"

;;;; Line 1025
'"21.1"

;;;; Line 1027
'"20.3"

;;;; Line 1029
'"23.2"

;;;; Line 1031
'"23.2"

;;;; Line 1033
'"23.2"

;;;; Line 1035
'"20.3"

;;;; Line 1037
'"21.1"

;;;; Line 1039
'"22.1"

;;;; Line 1041
'"21.1"

;;;; Line 1043
'"25.1"

;;;; Line 1045
'"22.1"

;;;; Line 1047
'"22.1"

;;;; Line 1049
'"24.4"

;;;; Line 1051
'"24.4"

;;;; Line 1053
'"24.3"

;;;; Line 1055
'"22.1"

;;;; Line 1057
'"22.1"

;;;; Line 1059
'"24.1"

;;;; Line 1061
'"24.1"

;;;; Line 1063
'"22.1"

;;;; Line 1065
'"22.1"

;;;; Line 1070
'"22.1"

;;;; Line 1072
'"22.1"

;;;; Line 1074
'"21.1"

;;;; Line 1076
'"22.1"

;;;; Line 1078
'"22.1"

;;;; Line 1080
'"21.1"

;;;; Line 1082
'"26.1"

;;;; Line 1084
'"21.1"

;;;; Line 1086
'"21.1"

;;;; Line 1088
'"21.1"

;;;; Line 1090
'"21.1"

;;;; Line 1092
'"20.3"

;;;; Line 1094
'"21.1"

;;;; Line 1096
'"23.1"

;;;; Line 1098
'"20.3"

;;;; Line 1100
'"22.1"

;;;; Line 1102
'"25.1"

;;;; Line 1104
'"25.1"

;;;; Line 1106
'"24.4"

;;;; Line 1108
'"24.2"

;;;; Line 1111
'"24.4"

;;;; Line 1114
'"24.4"

;;;; Line 1117
'"24.4"

;;;; Line 1120
'"22.1"

;;;; Line 1126
'"24.1"

;;;; Line 1128
'"21.1"

;;;; Line 1130
'"21.1"

;;;; Line 1132
'"24.1"

;;;; Line 1134
'"20"

;;;; Line 1137
'"22.1"

;;;; Line 1140
'"24.3"

;;;; Line 1142
'"24.3"

;;;; Line 1144
'"25.1"

;;;; Line 1146
'"20"

;;;; Line 1148
'"20"

;;;; Line 1151
'"20"

;;;; Line 1154
'"20"

;;;; Line 1157
'"20"

;;;; Line 1160
'"20"

;;;; Line 1163
'"20"

;;;; Line 1166
'"20"

;;;; Line 1169
'"20"

;;;; Line 1172
'"20"

;;;; Line 1175
'"20"

;;;; Line 1178
'"20"

;;;; Line 1181
'"20"

;;;; Line 1184
'"24.3"

;;;; Line 1186
'"26.1"

;;;; Line 1188
'"21.1"

;;;; Line 1190
'"22.1"

;;;; Line 1192
'"21.1"

;;;; Line 1194
'"25.1"

;;;; Line 1196
'"23.1"

;;;; Line 1198
'"21.1"

;;;; Line 1200
'"21.1"

;;;; Line 1203
'"21.1"

;;;; Line 1205
'"21.1"

;;;; Line 1207
'"22.1"

;;;; Line 1209
'"22.1"

;;;; Line 1211
'"21.1"

;;;; Line 1214
'"25.1"

;;;; Line 1216
'"22.1"

;;;; Line 1218
'"20.4"

;;;; Line 1220
'"24.1"

;;;; Line 1222
'"22.2"

;;;; Line 1224
'"22.1"

;;;; Line 1229
'"22.1"

;;;; Line 1232
'"21.1"

;;;; Line 1234
'"22.1"

;;;; Line 1236
'"21.1"

;;;; Line 1238
'"24.4"

;;;; Line 1240
'"24.4"

;;;; Line 1242
'"24.4"

;;;; Line 1244
'"24.4"

;;;; Line 1246
'"24.4"

;;;; Line 1248
'"24.4"

;;;; Line 1250
'"22.1"

;;;; Line 1252
'"22.1"

;;;; Line 1254
'"22.1"

;;;; Line 1256
'"22.2"

;;;; Line 1258
'"24.1"

;;;; Line 1260
'"24.1"

;;;; Line 1262
'"24.1"

;;;; Line 1264
'"24.1"

;;;; Line 1266
'"24.1"

;;;; Line 1268
'"24.1"

;;;; Line 1270
'"25.1"

;;;; Line 1272
'"24.1"

;;;; Line 1274
'"22.2"

;;;; Line 1276
'"22.2"

;;;; Line 1278
'"22.1"

;;;; Line 1280
'"22.1"

;;;; Line 1282
'"23.1"

;;;; Line 1284
'"21.1"

;;;; Line 1286
'"25.1"


;;; *** /home/micha/software/emacs/lisp/descr-text.el  (1 match)

;;;; Line 684
'#xa0


;;; *** /home/micha/software/emacs/lisp/ezimage.el  (1 match)

;;;; Line 105
':file


;;; *** /home/micha/software/emacs/lisp/filesets.el  (45 matches)

;;;; Line 184
':test

;;;; Line 1151
':dirs

;;;; Line 1153
':files

;;;; Line 1220
':files

;;;; Line 1236
':constraintp

;;;; Line 1237
':constraint-flag

;;;; Line 1289
':ignore-on-open-all

;;;; Line 1290
':ignore-on-read-text

;;;; Line 1317
':capture-output

;;;; Line 1318
':open-hook

;;;; Line 1319
':args

;;;; Line 1471
':open

;;;; Line 1478
':save

;;;; Line 1482
':files

;;;; Line 1488
':files

;;;; Line 1492
':verbosity

;;;; Line 1496
':file

;;;; Line 1501
':pattern

;;;; Line 1517
':tree

;;;; Line 1521
':dormant-p

;;;; Line 1524
':dormant-flag

;;;; Line 1528
':filter-dirs-flag

;;;; Line 1532
':tree-max-level

;;;; Line 1536
':ingroup

;;;; Line 1622
':ingroup

;;;; Line 1623
':tree

;;;; Line 1734
':files

;;;; Line 1741
':files

;;;; Line 1822
':files

;;;; Line 1847
':files

;;;; Line 1860
':pattern

;;;; Line 1978
':pattern

;;;; Line 2057
':pattern

;;;; Line 2058
':name

;;;; Line 2059
':preprocess

;;;; Line 2060
':match-number

;;;; Line 2062
':scan-depth

;;;; Line 2063
':case-sensitive

;;;; Line 2065
':get-file-name

;;;; Line 2066
':stubp

;;;; Line 2067
':stub-flag

;;;; Line 2141
':ingroup

;;;; Line 2155
':ingroup

;;;; Line 2193
':tree

;;;; Line 2228
':tree


;;; *** /home/micha/software/emacs/lisp/info.el  (1 match)

;;;; Line 5163
'"(dir)top"


;;; *** /home/micha/software/emacs/lisp/ldefs-boot.el  (57 matches)

;;;; Line 393
'3

;;;; Line 395
'2

;;;; Line 1993
'1

;;;; Line 2003
'1

;;;; Line 2613
'"25.1"

;;;; Line 2680
'"25.1"

;;;; Line 2704
'"25.1"

;;;; Line 2724
'"25.1"

;;;; Line 2744
'"25.1"

;;;; Line 2786
'"25.1"

;;;; Line 3311
'3

;;;; Line 4378
'3

;;;; Line 7031
'4

;;;; Line 8151
'2

;;;; Line 8182
'2

;;;; Line 8210
'1

;;;; Line 8218
'1

;;;; Line 10217
'"24.5"

;;;; Line 10678
'"25.1"

;;;; Line 11050
'3

;;;; Line 11052
'2

;;;; Line 11380
'"25.1"

;;;; Line 11404
'"25.1"

;;;; Line 11428
'"25.1"

;;;; Line 11450
'"25.1"

;;;; Line 11478
'"27.1"

;;;; Line 11501
'"27.1"

;;;; Line 11516
'"25.1"

;;;; Line 12626
'1

;;;; Line 13969
'1

;;;; Line 13971
'7

;;;; Line 14001
'"24.4"

;;;; Line 15482
'2

;;;; Line 15492
'1

;;;; Line 15517
'2

;;;; Line 16855
'1

;;;; Line 16857
'2

;;;; Line 16899
'2

;;;; Line 16901
'3

;;;; Line 16919
'2

;;;; Line 16921
'2

;;;; Line 17811
'3

;;;; Line 18694
'3

;;;; Line 19704
'1

;;;; Line 20396
'"24.1"

;;;; Line 22221
'"23.1"

;;;; Line 25032
'1

;;;; Line 25040
'1

;;;; Line 25050
'2

;;;; Line 25061
'1

;;;; Line 25073
'1

;;;; Line 25080
'1

;;;; Line 25092
'2

;;;; Line 25094
'3

;;;; Line 30787
'2

;;;; Line 37769
'"this function has no effect."

;;;; Line 37769
'"24.1"


;;; *** /home/micha/software/emacs/lisp/loaddefs.el  (57 matches)

;;;; Line 393
'3

;;;; Line 395
'2

;;;; Line 1993
'1

;;;; Line 2003
'1

;;;; Line 2613
'"25.1"

;;;; Line 2680
'"25.1"

;;;; Line 2704
'"25.1"

;;;; Line 2724
'"25.1"

;;;; Line 2744
'"25.1"

;;;; Line 2786
'"25.1"

;;;; Line 3311
'3

;;;; Line 4378
'3

;;;; Line 7031
'4

;;;; Line 8151
'2

;;;; Line 8182
'2

;;;; Line 8210
'1

;;;; Line 8218
'1

;;;; Line 10217
'"24.5"

;;;; Line 10678
'"25.1"

;;;; Line 11050
'3

;;;; Line 11052
'2

;;;; Line 11380
'"25.1"

;;;; Line 11404
'"25.1"

;;;; Line 11428
'"25.1"

;;;; Line 11450
'"25.1"

;;;; Line 11478
'"27.1"

;;;; Line 11501
'"27.1"

;;;; Line 11516
'"25.1"

;;;; Line 12626
'1

;;;; Line 13969
'1

;;;; Line 13971
'7

;;;; Line 14001
'"24.4"

;;;; Line 15482
'2

;;;; Line 15492
'1

;;;; Line 15517
'2

;;;; Line 16855
'1

;;;; Line 16857
'2

;;;; Line 16899
'2

;;;; Line 16901
'3

;;;; Line 16919
'2

;;;; Line 16921
'2

;;;; Line 17811
'3

;;;; Line 18694
'3

;;;; Line 19704
'1

;;;; Line 20396
'"24.1"

;;;; Line 22221
'"23.1"

;;;; Line 25035
'1

;;;; Line 25043
'1

;;;; Line 25053
'2

;;;; Line 25065
'1

;;;; Line 25078
'1

;;;; Line 25089
'1

;;;; Line 25101
'2

;;;; Line 25103
'3

;;;; Line 30796
'2

;;;; Line 37778
'"this function has no effect."

;;;; Line 37778
'"24.1"


;;; *** /home/micha/software/emacs/lisp/xwidget.el  (1 match)

;;;; Line 63
':xwidget


;;; *** /home/micha/software/emacs/lisp/calc/calc-aent.el  (2 matches)

;;;; Line 718
'?\.

;;;; Line 721
'?_


;;; *** /home/micha/software/emacs/lisp/calc/calc-prog.el  (1 match)

;;;; Line 1959
':


;;; *** /home/micha/software/emacs/lisp/cedet/ede/project-am.el  (2 matches)

;;;; Line 576
':default-value

;;;; Line 579
':default-value


;;; *** /home/micha/software/emacs/lisp/cedet/semantic/bovine/c-by.el  (1 match)

;;;; Line 2063
':pure-virtual-flag


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/cl-extra.el  (9 matches)

;;;; Line 479
'8388608e0

;;;; Line 505
'2e1

;;;; Line 506
'2e0

;;;; Line 530
'1e0

;;;; Line 531
'1e0

;;;; Line 531
'1e0

;;;; Line 533
'1e0

;;;; Line 534
'1e0

;;;; Line 534
'1e0


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/cl-loaddefs.el  (39 matches)

;;;; Line 317
'3

;;;; Line 319
'2

;;;; Line 328
'3

;;;; Line 330
'2

;;;; Line 354
'3

;;;; Line 356
'2

;;;; Line 370
'2

;;;; Line 380
'1

;;;; Line 400
'1

;;;; Line 408
'1

;;;; Line 419
'1

;;;; Line 427
'1

;;;; Line 441
'1

;;;; Line 458
'1

;;;; Line 516
'2

;;;; Line 541
'2

;;;; Line 551
'1

;;;; Line 561
'1

;;;; Line 595
'1

;;;; Line 602
'1

;;;; Line 621
'2

;;;; Line 637
'1

;;;; Line 645
'1

;;;; Line 658
'1

;;;; Line 666
'1

;;;; Line 675
'1

;;;; Line 687
'2

;;;; Line 698
'1

;;;; Line 710
'1

;;;; Line 763
'1

;;;; Line 772
'1

;;;; Line 781
'2

;;;; Line 789
'3

;;;; Line 801
'2

;;;; Line 823
'2

;;;; Line 825
'1

;;;; Line 875
'2

;;;; Line 896
'3

;;;; Line 898
'2


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/cl-macs.el  (1 match)

;;;; Line 2917
':read-only


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/cl-seq.el  (1 match)

;;;; Line 78
(quote :allow-other-keys)


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/eieio-loaddefs.el  (7 matches)

;;;; Line 27
'3

;;;; Line 29
'"25.1"

;;;; Line 59
'3

;;;; Line 61
'"25.1"

;;;; Line 78
'"24.1"

;;;; Line 85
'"24.1"

;;;; Line 92
'"25.1"


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/ert.el  (3 matches)

;;;; Line 121
':passed

;;;; Line 959
':failed

;;;; Line 965
':passed


;;; *** /home/micha/software/emacs/lisp/emacs-lisp/rx.el  (4 matches)

;;;; Line 356
':

;;;; Line 382
':

;;;; Line 695
':

;;;; Line 706
':


;;; *** /home/micha/software/emacs/lisp/erc/erc-stamp.el  (1 match)

;;;; Line 265
':align-to


;;; *** /home/micha/software/emacs/lisp/eshell/esh-module.el  (4 matches)

;;;; Line 69
':tag

;;;; Line 75
':tag

;;;; Line 77
':link

;;;; Line 78
':doc


;;; *** /home/micha/software/emacs/lisp/eshell/esh-opt.el  (6 matches)

;;;; Line 106
':preserve-args

;;;; Line 135
':show-usage

;;;; Line 149
':usage

;;;; Line 150
':external

;;;; Line 151
':post-usage

;;;; Line 228
':external


;;; *** /home/micha/software/emacs/lisp/gnus/gnus.el  (2 matches)

;;;; Line 2495
':interactive

;;;; Line 2504
':interactive


;;; *** /home/micha/software/emacs/lisp/gnus/mail-source.el  (2 matches)

;;;; Line 577
':password

;;;; Line 579
':password


;;; *** /home/micha/software/emacs/lisp/gnus/nnmail.el  (1 match)

;;;; Line 1387
':


;;; *** /home/micha/software/emacs/lisp/mail/rmail.el  (1 match)

;;;; Line 457
':value


;;; *** /home/micha/software/emacs/lisp/mh-e/mh-e.el  (1 match)

;;;; Line 688
':package-version


;;; *** /home/micha/software/emacs/lisp/mh-e/mh-xface.el  (4 matches)

;;;; Line 104
':data

;;;; Line 110
':data

;;;; Line 122
':data

;;;; Line 415
':data


;;; *** /home/micha/software/emacs/lisp/net/eudc-vars.el  (2 matches)

;;;; Line 70
':tag

;;;; Line 85
':tag


;;; *** /home/micha/software/emacs/lisp/net/eudc.el  (1 match)

;;;; Line 320
':tag


;;; *** /home/micha/software/emacs/lisp/net/shr.el  (1 match)

;;;; Line 1338
':xlink:href


;;; *** /home/micha/software/emacs/lisp/obsolete/cl-compat.el  (3 matches)

;;;; Line 125
':test-not

;;;; Line 126
':test

;;;; Line 127
':key


;;; *** /home/micha/software/emacs/lisp/obsolete/lmenu.el  (5 matches)

;;;; Line 95
':active

;;;; Line 100
':suffix

;;;; Line 103
':keys

;;;; Line 106
':style

;;;; Line 109
':selected


;;; *** /home/micha/software/emacs/lisp/org/org-loaddefs.el  (6 matches)

;;;; Line 149
'1

;;;; Line 158
'1

;;;; Line 167
'1

;;;; Line 176
'1

;;;; Line 1722
'2

;;;; Line 1758
'2


;;; *** /home/micha/software/emacs/lisp/progmodes/ada-prj.el  (6 matches)

;;;; Line 553
':prj-field

;;;; Line 575
':prj-field

;;;; Line 585
':prj-field

;;;; Line 601
':prj-field

;;;; Line 602
':prj-field

;;;; Line 673
':prj-field


;;; *** /home/micha/software/emacs/lisp/progmodes/idlwave.el  (5 matches)

;;;; Line 4117
':size

;;;; Line 4117
':test

;;;; Line 4127
':size

;;;; Line 4127
':test

;;;; Line 7126
':activate-callback


;;; *** /home/micha/software/emacs/lisp/progmodes/ruby-mode.el  (3 matches)

;;;; Line 98
'"\\(def\\|class\\|module\\)"

;;;; Line 472
'?w

;;;; Line 476
'?w


;;; *** /home/micha/software/emacs/lisp/progmodes/vhdl-mode.el  (46 matches)

;;;; Line 2624
'87

;;;; Line 3714
'87

;;;; Line 3716
'87

;;;; Line 3719
'93

;;;; Line 3721
'93

;;;; Line 3724
'08

;;;; Line 3726
'08

;;;; Line 5355
'08

;;;; Line 5361
'08

;;;; Line 5368
'08

;;;; Line 5383
'08

;;;; Line 5388
'08

;;;; Line 5392
'08

;;;; Line 5723
'08

;;;; Line 8863
'87

;;;; Line 8939
'87

;;;; Line 8996
'87

;;;; Line 9055
'87

;;;; Line 9059
'87

;;;; Line 9233
'87

;;;; Line 9274
'87

;;;; Line 9353
'87

;;;; Line 9392
'87

;;;; Line 9398
'87

;;;; Line 9492
'87

;;;; Line 9592
'87

;;;; Line 9837
'87

;;;; Line 9886
'87

;;;; Line 9907
'87

;;;; Line 9945
'08

;;;; Line 9966
'87

;;;; Line 10098
'87

;;;; Line 10312
'87

;;;; Line 10684
'87

;;;; Line 10685
'93

;;;; Line 10686
'08

;;;; Line 11965
'87

;;;; Line 11988
'87

;;;; Line 11991
'87

;;;; Line 12360
'87

;;;; Line 12438
'87

;;;; Line 12696
'87

;;;; Line 16209
'87

;;;; Line 16247
'87

;;;; Line 16254
'87

;;;; Line 16698
'87


;;; *** /home/micha/software/emacs/lisp/textmodes/enriched.el  (2 matches)

;;;; Line 484
':foreground

;;;; Line 490
':background


;;; *** /home/micha/software/emacs/lisp/textmodes/texinfmt.el  (1 match)

;;;; Line 1371
'\:


;;; *** /home/micha/software/emacs/lisp/vc/smerge-mode.el  (2 matches)

;;;; Line 1121
'?c

;;;; Line 1127
'?c


;;; *** /home/micha/software/emacs/test/lisp/subr-tests.el  (4 matches)

;;;; Line 38
(quote 10)

;;;; Line 39
(quote 25)

;;;; Line 47
(quote 25)

;;;; Line 59
(quote
 "\\<\\(?:\\(?:fals\\|tru\\)e\\)\\>")


;;; *** /home/micha/software/emacs/test/lisp/emacs-lisp/ert-tests.el  (2 matches)

;;;; Line 367
':passed

;;;; Line 429
':failed


;;; *** /home/micha/software/emacs/test/lisp/emacs-lisp/map-tests.el  (1 match)

;;;; Line 77
'2


;;; *** /home/micha/software/emacs/test/lisp/emacs-lisp/nadvice-tests.el  (3 matches)

;;;; Line 54
'5

;;;; Line 57
'5

;;;; Line 59
'5


;;; *** /home/micha/software/emacs/test/lisp/emacs-lisp/pcase-tests.el  (2 matches)

;;;; Line 29
'2

;;;; Line 29
'1


;;; *** /home/micha/software/emacs/test/lisp/emacs-lisp/package-resources/macro-problem-package-2.0/macro-problem.el  (1 match)

;;;; Line 18
'1


;;; *** /home/micha/software/emacs/test/src/data-tests.el  (1 match)

;;;; Line 523
'2

[-- Attachment #3: Type: text/plain, Size: 12 bytes --]




Michael.

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:31                                                                                                                                 ` Clément Pit-Claudel
@ 2018-10-31 20:36                                                                                                                                   ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-10-31 20:36 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

> Cc: emacs-devel@gnu.org
> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
> Date: Wed, 31 Oct 2018 15:31:58 -0400
> 
> > Anyway, I think this argument is futile.  
> 
> OK, apologies.

No need to apologize.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:05                                                                                                                             ` Eli Zaretskii
@ 2018-10-31 20:41                                                                                                                               ` Michael Heerdegen
  2018-11-01  4:14                                                                                                                                 ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-31 20:41 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel, monnier, dgutov

Eli Zaretskii <eliz@gnu.org> writes:

> > (pcase '(1 2 3)
> >   ((let a 3) a))
> > ==> 3
>
> Thanks, but I meant an example of what's described after the "OTOH".

Oh, sorry.  How about this:

(defun second-elt-is-positive-p (l)
    (pcase l
      (`(,_ ,(pred (< 0)) . ,_) t)))

(second-elt-is-positive-p (list 1 2 3))
==> t

(second-elt-is-positive-p (list 1 -2 3))
==> nil

Is the pattern `(,_ ,(pred (< 0)) . ,_) destructuring or does it
additionally have to bind at least one variable to be called like that?

Such patterns are used in real life - some bind variables, but others
are only used as tests to see if the structure fulfils certain
requirements.  I guess there is no sharp dividing line.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-30 13:14                                                                                                 ` Stefan Monnier
@ 2018-10-31 23:13                                                                                                   ` Garreau, Alexandre
  2018-11-01 13:22                                                                                                     ` Clément Pit-Claudel
  0 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-31 23:13 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-30 at 09:14, Stefan Monnier wrote:
>> #+BEGIN_SRC ocaml
>>   match [1;2;3] with [a;b;c] -> [a;b;c]
>> #+END_SRC
>>
>> But this is a non-primordial side effect.  Notice how in the later case
>> the matched data *always* look the same as the pattern (beside replacing
>> a number per an identifier): *that’s* the purpose of pattern matching.
>> While in the lisp case you got those extra “,”.
>
> That's for a very simple reason: OCaml doesn't have Lisp's symbols, so
> its [a;b;c] can't mean "a list containing the symbols a, b, and c".

In lisp I would have prefered to be able to directly quote each symbol,
and have this to work, eg: “(pcase (list 1 2 3) (('a 'b 'c) t))” to
return nil, and “(pcase (list 'a 'b 'c) (('a 'b 'c) t))” to return t
(and this is like many other lisp pattern-matching implementations
already work).  In current pcase, pattern “(a b c)” does *not* mean
“with symbols 'a, 'b and 'c”.

“('(a b c) t)” (or same with “`”) seems okay to me, but as “(`(,a ,b ,c)
t)” *may* be confusing (the intended, actual and current meaning must be
intuitive under some definition of “intuitive” too since others
independantly do it too), I’d prefer “((a b c) t)” to work.

> OCaml still has to distinguish between variables and data constructors,
> but instead of using a "," to distinguish the two cases, they force
> constructors to be capitalized.

Oh… yet another (disappointing) reason why they did what (incredibly
limited) they did (though afaik it’s nothing new, it have to come from
Smalltalk, and I’m not that much opposed to identifiers names/meaning
intermeddling).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:31                                                                                               ` Michael Heerdegen
@ 2018-10-31 23:33                                                                                                 ` Garreau, Alexandre
  2018-10-31 23:44                                                                                                 ` Garreau, Alexandre
                                                                                                                   ` (2 subsequent siblings)
  3 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-31 23:33 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, monnier, emacs-devel

On 2018-10-31 at 15:37, Stefan Monnier wrote:
>> Really?  Can you show a few examples?  Maybe there's something wrong
>> with our documentation if people make such mistakes.
>
> I don't think calling them mistakes is right.  It might just be
> a stylistic preference on the part of the author, […]

On 2018-10-31 at 21:31, Michael Heerdegen wrote:
> Eli Zaretskii <eliz@gnu.org> writes:
>> > BTW, while preparing the first patch I already found tons of
>> > unnecessary quotes outside of pcase patterns: quotes quoting
>> > self-evaluating objects like strings and numbers.
>>
>> Really?  Can you show a few examples?  Maybe there's something wrong
>> with our documentation if people make such mistakes.
>
> Here is the result of a quick search.  As Stefan said, I don't say we
> should fix (all of) these.  But some really look strange.  There are
> many quoted strings - I wonder if these quotes change the behavior of
> the compiler or so?

I want to notice this kind of questionment is exactly the kind of
reasons why such “author stylistic preference” usage should be avoided:
because unless a such “stylistic preference”, along with its reason,
meanings, and use cases, is formally made explicit somewhere so that its
meaning (and use) is clear (but then we will end with yet another
non-self-quoting semantic formatting usage (just as “((alist cons key)
. (alist cons value list))” and “((alist cons key) alist cons value
list)”)) then people will begin to really (hence unacknoweldgly,
irrationally, and thus inconsistently) believe this may be kind of
special low-level optimization wizard trick, and recopy that without
understanding, so that supposed “meaningful stylistic preference” will
end up in inconsistent garbage random obfuscation everywhere (I’m
exagerating but this is a useless risk).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:31                                                                                               ` Michael Heerdegen
  2018-10-31 23:33                                                                                                 ` Garreau, Alexandre
@ 2018-10-31 23:44                                                                                                 ` Garreau, Alexandre
  2018-10-31 23:58                                                                                                   ` Michael Heerdegen
  2018-11-01  4:15                                                                                                 ` Eli Zaretskii
  2018-11-01 12:30                                                                                                 ` Stefan Monnier
  3 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-10-31 23:44 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, monnier, emacs-devel

On 2018-10-31 at 21:31, Michael Heerdegen wrote:
> ;;; ** Search the Emacs Elisp sources for
> `',(or
>     (pred keywordp)
>     (pred numberp)
>     (pred stringp))
>
> ;;; ** 509 matches in 50 files:
>

I believe a “few examples” contexts might be useful:

> ;;; *** /home/micha/software/emacs/lisp/allout.el  (1 match)
>
> ;;;; Line 5138
> ':

Context:
> 	  (cond ((eq curr-elem '*) (allout-show-current-subtree)
> 		 (if (> allout-recent-end-of-subtree max-pos)
> 		     (setq max-pos allout-recent-end-of-subtree)))
>                 ((eq curr-elem '+)
>                  (if (not (allout-hidden-p))
>                      (save-excursion (allout-hide-current-subtree t)))
>                  (allout-show-current-branches)
> 		 (if (> allout-recent-end-of-subtree max-pos)
> 		     (setq max-pos allout-recent-end-of-subtree)))
> 		((eq curr-elem '-) (allout-show-current-entry))
> 		((eq curr-elem ':)
> 		 (setq stay t)
> 		 ;; Expand the `repeat' spec to an explicit version,
> 		 ;; w.r.t. remaining siblings:

> ;;; *** /home/micha/software/emacs/lisp/cus-edit.el  (2 matches)
>
> ;;;; Line 4711
> ':style

Context:
> (widget-put (get 'boolean 'widget-type)
> 	    :custom-menu (lambda (_widget symbol)
> 			   (vector (custom-unlispify-menu-entry symbol)
> 				   `(customize-variable ',symbol)
> 				   ':style 'toggle
> 				   ':selected symbol)))

> ;;; *** /home/micha/software/emacs/lisp/cus-load.el  (154 matches)
>
> ;;;; Line 929
> '"20.4"
>
> ;;;; Line 931
> '"21.1"


Context:
> (custom-put-if-not 'SQL 'custom-version '"20.4")
> […]
> (custom-put-if-not 'align 'custom-version '"21.1")

And so on…

> ;;; *** /home/micha/software/emacs/lisp/descr-text.el  (1 match)
>
> ;;;; Line 684
> '#xa0

>                             ((and nobreak-char-display char (eq char '#xa0))
>                              'nobreak-space)

> ;;; *** /home/micha/software/emacs/lisp/info.el  (1 match)
>
> ;;;; Line 5163
> '"(dir)top"

Context:
> 	(setq completions
> 	      (Info-speedbar-fetch-file-nodes (or node '"(dir)top"))))

> ;;; *** /home/micha/software/emacs/lisp/ldefs-boot.el  (57 matches)
>
> ;;;; Line 393
> '3

Context:
> (function-put 'defadvice 'doc-string-elt '3)


> ;;; *** /home/micha/software/emacs/lisp/calc/calc-aent.el  (2 matches)
>
> ;;;; Line 718
> '?\.
>
> ;;;; Line 721
> '?_

Context:
> 		 (and (eq ch '?\.)
> 		      (eq (string-match "\\.[0-9]" math-exp-str math-exp-pos)
>                           math-exp-pos))
> 		 (and (eq ch '?_)
> 		      (eq (string-match "_\\.?[0-9]" math-exp-str math-exp-pos)
>                           math-exp-pos)

All the rest is alike.

In the end I believe the maximally useful and compact presentation would
be one example per type, with context along (most often upper sexp is
enough, maybe some lines around too).  Suggesting that for el-search.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 23:44                                                                                                 ` Garreau, Alexandre
@ 2018-10-31 23:58                                                                                                   ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-10-31 23:58 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: Eli Zaretskii, monnier, emacs-devel

"Garreau, Alexandre" <galex-713@galex-713.eu> writes:

> In the end I believe the maximally useful and compact presentation

I guess that could also just be a patch with the quotes removed, in this
case.  Then it's trivial to browse all the occurrences in the files you
are interested in.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:03                                                                                                                             ` Stefan Monnier
@ 2018-11-01  0:07                                                                                                                               ` Dmitry Gutov
  0 siblings, 0 replies; 375+ messages in thread
From: Dmitry Gutov @ 2018-11-01  0:07 UTC (permalink / raw)
  To: Stefan Monnier, emacs-devel

On 31.10.2018 22:03, Stefan Monnier wrote:
>> A thing can be called "destructuring" if it destructures something.
>> It's like a "flying carpet": the carpet that flies.  But in our case
>> the patterns don't destructure anything, they are a means for
>> destructuring.
> 
> And let's not forget that what I used this term currently is to talk
> about the specific way pcase patterns are used within pcase-let
> (i.e. the way pcase-let and friends skip the tests to verify that the
> pattern does match).

That part of the explanation is pretty counter-intuitive to me. I mean, 
I get what it's saying (pcase-let skips certain checks), but that's not 
a property of a pattern (which is a certain form), so the phrase 
"destructuring pattern" (which, in my mind, should just describe the 
pattern) shouldn't imply a particular aspect of its use.

The way I think of the situation is pcase performs both the structure 
check and destructuring, and pcase-let only performs destructuring. But 
destructuring is present in both cases and it's a property of the 
pattern (and maybe of the input data if the pattern includes an "(or").

> So maybe we should just say "a pattern used to destructure" to clarify
> that it's not a property of the pattern but of the way it's being used.

Maybe we shouldn't try to explain that through saying that patterns 
exhibit a certain property in this situation, and explain that purely in 
terms of behavior of certain macros (pcase-let and pcase-dolist, IIRC)?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:20                                                                                                                               ` Eli Zaretskii
@ 2018-11-01  0:11                                                                                                                                 ` Dmitry Gutov
  0 siblings, 0 replies; 375+ messages in thread
From: Dmitry Gutov @ 2018-11-01  0:11 UTC (permalink / raw)
  To: Eli Zaretskii, Yuri Khan; +Cc: cpitclaudel, emacs-devel

On 31.10.2018 21:20, Eli Zaretskii wrote:

>> a “walking stick” is a stick that is used for walking, or a “thinking
>> cap” is a cap for thinking. They don’t walk and think on their own,
>> but are tools used in a specific activity.
> 
> No, they are tools that help in that activity: the stick helps in
> walking, the hat helps thinking.
> 
> By contrast, those patterns don't "help" destructuring in any way I
> could spot.

Surely they do: they provide the whole destructuring logic, in a 
declarative way. pcase then simply interprets it according to its rules.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:29                                                                                                                               ` Eli Zaretskii
  2018-10-31 19:31                                                                                                                                 ` Clément Pit-Claudel
@ 2018-11-01  0:13                                                                                                                                 ` Dmitry Gutov
  2018-11-01  1:31                                                                                                                                 ` Garreau, Alexandre
  2 siblings, 0 replies; 375+ messages in thread
From: Dmitry Gutov @ 2018-11-01  0:13 UTC (permalink / raw)
  To: Eli Zaretskii, Clément Pit-Claudel; +Cc: emacs-devel

On 31.10.2018 21:29, Eli Zaretskii wrote:

> They are a kind of jargon.  Try to explain that to a Martian.  Or even
> to a non-native English speakers. 

I am one as well.

> I speak a couple of languages other
> than English, and none of them has "swimming pools" and "shopping
> lists", verbatim.

German does, I think. Not that I know it very well, though.

> Anyway, I think this argument is futile.  I'm trying to find a better
> terminology that doesn't need explaining; I don't think anyone should
> have a problem with a clearer terminology.

I think this term is fine, but please don't let me stop you.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 13:07                                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
  2018-10-30 23:30                                                                                                   ` Eric Abrahamsen
@ 2018-11-01  0:16                                                                                                   ` Garreau, Alexandre
  1 sibling, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01  0:16 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

On 2018-10-30 at 09:07, Stefan Monnier wrote:
>> In fact, when you think about it, the "case" nature of pcase is pretty
>> orthogonal to the "match/destructure" nature of pcase. If anything
>
> How do you suggest to split the two in cases like:
>
> […]

Wouldn’t a “cl-case :test #'match ...”, where each `match' would be the
simple-destructuring case-less version of `pcase' and `cl-case' would
manage `:test' optional keyword, work?  As for using bindings, either
modifying cl-case (maybe getting it able to use external hooks?), either
with ugly side effects (replacing “#'match” per “(lambda (arg) (setq
local-pattern-env (match arg)))”, then wrapping bodies with a “let-alist
local-pattern-env”) (and making that a macro, but agreed it would be
ugly and not optimized)?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 19:29                                                                                                                               ` Eli Zaretskii
  2018-10-31 19:31                                                                                                                                 ` Clément Pit-Claudel
  2018-11-01  0:13                                                                                                                                 ` Dmitry Gutov
@ 2018-11-01  1:31                                                                                                                                 ` Garreau, Alexandre
  2 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01  1:31 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Clément Pit-Claudel, emacs-devel

On 2018-10-31 at 21:29, Eli Zaretskii wrote:
>> Cc: emacs-devel@gnu.org
>> From: Clément Pit-Claudel <cpitclaudel@gmail.com>
>> Date: Wed, 31 Oct 2018 15:21:05 -0400
>> 
>> But something can also be called "destructuring" if it's used *for*
>> destructuring: a "swimming pool" is not a pool that swims, it's a
>> pool that's used for swimming.  I think of "destructuring" in
>> "destructuring pattern" as a gerund, not a present participle:<we
>> have "shopping lists" and "shaving cream", so why not "destructuring
>> patterns"? :)
>
> They are a kind of jargon.  Try to explain that to a Martian.  Or even
> to a non-native English speakers.

On 2018-10-31 at 15:31, Clément Pit-Claudel wrote:
> You're talking to one :)

I’d say the non english-alphabet letter in the name was an hint ;)

Jargon are no harm I’d say, from the moment it is logically as well as
straightforwardly formed from other jargon words which are known, and
whose relation is imaginable from further explanation (especially
definition).

Me too btw (perhaps from same place):

> I speak a couple of languages other than English, and none of them has
> "swimming pools" and "shopping lists", verbatim.

Esperanto has (“naĝejo” is litteraly “swimming place”: usually
“<verb>ejo” is “place where you <verb>”, very simple to explain to a
Martian (and simple generalization of the afterwards-described
stacking-language feature (afaik it takes it from Russian and other
slavic languages))).  I always interpreted english adjectives not to
mean “being part of” (or even also “being used for”) but “being related
to”: that’s also one key difference between english or esperanto to ido
or french (or italian), and I easily understood that at first, while
being native of both the two later.

For instance, first time I saw it (the stacking-language feature of
esperanto) described (it was formally enough “to be understood by a
Martian” in intent, I believe), it was about “vaporŝipo” (steamship,
notice it’s a direct mapping of meaning with english btw): “it is not a
‘ŝipo’ [ship] made of ‘vaporo’ [steam], it is a ‘ship[…]’ *using*
[steam]”, afair, from original Fundamento.

In french it’s more precise, like you say “Bateau à vapeur” (ship with
(“à” [0] is actually more specific and refer to usage) steam), in
italian (“nave a vapore” (same), “vaporetto” (little steam, really quite
unrelated), “piroscafo” (made from greek, fire+dive, completely
unrelated): these are good languages if you like useless exceptions and
dislike useful generalizations.

It was also a key difference of “Ido” fork of esperanto: instead of
simply stacking related radicals, you use lots of collections of rich
preposition that each indicate how in fact they are related: one for
transformation, one for composition, one for addition, one for state,
one for action [1]…  in the end Ido was almost only used by the
linguists who invented it, unlike esperanto which, unlike what was
claimed by these last, is still used and wasn’t block by some fantasmed
“primordial confusion in front of its exagerated generality”.

> Anyway, I think this argument is futile.  I'm trying to find a better
> terminology that doesn't need explaining; I don't think anyone should
> have a problem with a clearer terminology.

What about a heavier terminology?  lighter (and simpler) terms should
always be welcome too I believe.

Notes and references:
[0] https://en.wiktionary.org/wiki/%C3%A0#Preposition_3
[1] <https://fr.wikipedia.org/wiki/Ido#Un_syst%C3%A8me_de_composition_plus_strict>
Translation [2]:

Composition in Ido obeys stricter rules than in esperanto, especially
names, adectives and verbs formations from a radical of a different
class.  The reversibility principle assume that for each composition
rule (affix addition), decomposition rule (affix remove) is valid.

Henceforth, while in esperanto an adjective (for instance /papera/,
formed on the radical /papero/) can mean an attribute (/papera
enciklopedio/: /paper-made encyclopedia/), and a relation (/papera
fabriko/: /paper-making factory/), ido will distinguish per construction
the attribute /papera/ (“paper” or “of paper” (not “paper-made”
exactely)) from the relation /paperala/ (“paper-making”).

Similarily, /krono/ mean in esperanto and ido “crown”; where esperanto
allow formation of “to crown” by simple /kroni/ (“the fact to crown” is
/kronado/), ido requires an affix so the composition is reversible:
/kronizar/ (“the fact to crown” is /kronizo/).

According Claude Piron, some modifications brought by Ido are in
practice impossible to use and ruin spontaneous expression: “Ido
displays, on linguistical level, other drawbacks which esperanto
suceeded to avoid, but I don’t have at hand documents which would allow
me to more go in detail.  For instance, if I remember correctly, where
esperanto only has the suffix “-igi*”, ido has several: “*-ifar*”,
“*-izar*”, “*-igar*”, which match subtleties which were meant to make
language clearer, but that, in practice, inhibit natural expression.”
[30].

[2] Sorry to embed this here, but I’m still trying to recover my
wikipedia account and understand wikicode (and translate it too >< since
it’s localized…) before to add this to wikipedia… anyway maybe it would
be removed anyway, if done incorrectly enough.

[30] http://claudepiron.free.fr/lettresouvertes/ido.htm



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 17:48                                                                                                                     ` Clément Pit-Claudel
  2018-10-31 18:11                                                                                                                       ` Eli Zaretskii
@ 2018-11-01  1:34                                                                                                                       ` Garreau, Alexandre
  1 sibling, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01  1:34 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

On 2018-10-31 at 13:48, Clément Pit-Claudel wrote:
> On 31/10/2018 12.13, Eli Zaretskii wrote:
>>> Cc: emacs-devel@gnu.org
>>> From: Dmitry Gutov <dgutov@yandex.ru>
>>> Date: Wed, 31 Oct 2018 18:05:44 +0200
>>>
>>>> Can someone enlighten me regarding those "holes"?  What does that
>>>> allude to?
>>>
>>> I stole the term from Clement here: 
>>> http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html
>> 
>> Ah, the elements that are assigned by destructuring?  I indeed hoped
>> we could identify in some way the patterns which satisfy that
>> condition.  I didn't give up yet.
>
> Regarding the word "holes": I think these ","-prefixed symbols are
> typically called "pattern-matching variables", or "placeholders".
> "holes" is the more colloquial term, the idea being that if you "fill"
> the "holes" in the pattern with the appropriate values, you get the
> original data back (formally, you perform a "substitution" of the
> "placeholders").
>
> Regarding the term "destructuring pattern": I think it's perfect.  The
> only other decent alternative I can think of would be
> "variable-binding pattern".

So may we not define “destructuring pattern” as a “structure pattern
that use placeholders”, a “structure pattern” as a “pattern only
matching a structure, whose subpatterns match its subelements”, and a
“placeholder” as a “match-everything symbol that binds what it match to
its name”?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 19:54                                                                                                       ` Eli Zaretskii
  2018-10-30 20:44                                                                                                         ` Stefan Monnier
@ 2018-11-01  1:40                                                                                                         ` Garreau, Alexandre
  2018-11-01  4:10                                                                                                           ` Eli Zaretskii
  1 sibling, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01  1:40 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: Stefan Monnier, emacs-devel

On 2018-10-30 at 21:54, Eli Zaretskii wrote:
> No, I think "destructuring" is about right.  How about this text:
>
>   @dfn{Destructuring} of an object is an operation that extracts
>   multiple values stored in the object, e.g., the 2nd and the 3rd
>   element of a list or a vector.  @dfn{Destructuring binding} is
>   similar to a local binding (@pxref{Local Variables}), but it gives
>   values to multiple elements of a variable by extracting those values
>   from an object of compatible structure.

“(car list)” is extracting a value stored in an object, yet it’s not
destructuring (though a list is a structure).  Nor even is “(cons (car
list) (caddr list))” or “(setq a (nth 1 list) b (nth 2 list))”.

I’d say destructuring, like in python (so to stop referring ocaml) “a,b
= 2,3”, implies a “specification reflecting the structure”, so “a,b”
*has* to be a pair/two-elements array/list/whatever.  So how about:

  @dfn{Destructuring} of an object is an operation that extracts
  multiple values stored in the object, by speciying a structure
  reflecting it, e.g., the 2nd and the 3rd element of a 3-elements list
  or a vector.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01  1:40                                                                                                         ` Garreau, Alexandre
@ 2018-11-01  4:10                                                                                                           ` Eli Zaretskii
  2018-11-01  5:21                                                                                                             ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-01  4:10 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: monnier, emacs-devel

> From: "Garreau\, Alexandre" <galex-713@galex-713.eu>
> Cc: Stefan Monnier <monnier@iro.umontreal.ca>,  emacs-devel@gnu.org
> Date: Thu, 01 Nov 2018 02:40:23 +0100
> 
> On 2018-10-30 at 21:54, Eli Zaretskii wrote:
> > No, I think "destructuring" is about right.  How about this text:
> >
> >   @dfn{Destructuring} of an object is an operation that extracts
> >   multiple values stored in the object, e.g., the 2nd and the 3rd
> >   element of a list or a vector.  @dfn{Destructuring binding} is
> >   similar to a local binding (@pxref{Local Variables}), but it gives
> >   values to multiple elements of a variable by extracting those values
> >   from an object of compatible structure.
> 
> “(car list)” is extracting a value stored in an object, yet it’s not
> destructuring (though a list is a structure).  Nor even is “(cons (car
> list) (caddr list))” or “(setq a (nth 1 list) b (nth 2 list))”.

You forget the "multiple" part in the description.

"Destructuring" is not a term that Emacs invented.  You can look it up
on the Internet; I think you will find that the adopted definitions
are similar to what I wrote.  So we don't need to try too hard in this
case, as someone else already did that for us.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:41                                                                                                                               ` Michael Heerdegen
@ 2018-11-01  4:14                                                                                                                                 ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-01  4:14 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel, monnier, dgutov

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: dgutov@yandex.ru,  monnier@IRO.UMontreal.CA,  emacs-devel@gnu.org
> Date: Wed, 31 Oct 2018 21:41:01 +0100
> 
> (defun second-elt-is-positive-p (l)
>     (pcase l
>       (`(,_ ,(pred (< 0)) . ,_) t)))
> 
> (second-elt-is-positive-p (list 1 2 3))
> ==> t
> 
> (second-elt-is-positive-p (list 1 -2 3))
> ==> nil
> 
> Is the pattern `(,_ ,(pred (< 0)) . ,_) destructuring or does it
> additionally have to bind at least one variable to be called like that?

I think we have a destructuring here, since elements of a list are
extracted and assigned to the elements of the pattern.  What we do
with the extracted elements (ignore 2 of them and apply a predicate to
the 3rd) is not really important for the purposes of this discussion.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:31                                                                                               ` Michael Heerdegen
  2018-10-31 23:33                                                                                                 ` Garreau, Alexandre
  2018-10-31 23:44                                                                                                 ` Garreau, Alexandre
@ 2018-11-01  4:15                                                                                                 ` Eli Zaretskii
  2018-11-01 12:30                                                                                                 ` Stefan Monnier
  3 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-01  4:15 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Wed, 31 Oct 2018 21:31:55 +0100
> 
> > Not sure I follow: fixing _all_ of them will be _less_ work for you?
> 
> I mean less work in summa.
> 
> > I'm okay with only fixing pcase usage at this time, if you feel that
> > would be enough for one changeset.
> 
> It would be ok for me to do both at once if that's also ok for you.

It's fine.

> > Really?  Can you show a few examples?  Maybe there's something wrong
> > with our documentation if people make such mistakes.
> 
> Here is the result of a quick search.  As Stefan said, I don't say we
> should fix (all of) these.  But some really look strange.  There are
> many quoted strings - I wonder if these quotes change the behavior of
> the compiler or so?  I tiny fraction of the matches may be cases where
> the quote is significant, e.g. when located in a quoted structure, like
> in '('1).

I agree that we should fix those.  I'm surprised we have so many of
them.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01  4:10                                                                                                           ` Eli Zaretskii
@ 2018-11-01  5:21                                                                                                             ` Garreau, Alexandre
  2018-11-01 18:07                                                                                                               ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01  5:21 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

On 2018/11/01 at 06:10, Eli Zaretskii wrote:
>> From: "Garreau\, Alexandre" <galex-713@galex-713.eu>
>> Cc: Stefan Monnier <monnier@iro.umontreal.ca>,  emacs-devel@gnu.org
>> Date: Thu, 01 Nov 2018 02:40:23 +0100
>> 
>> On 2018-10-30 at 21:54, Eli Zaretskii wrote:
>> > No, I think "destructuring" is about right.  How about this text:
>> >
>> >   @dfn{Destructuring} of an object is an operation that extracts
>> >   multiple values stored in the object, e.g., the 2nd and the 3rd
>> >   element of a list or a vector.  @dfn{Destructuring binding} is
>> >   similar to a local binding (@pxref{Local Variables}), but it gives
>> >   values to multiple elements of a variable by extracting those values
>> >   from an object of compatible structure.
>> 
>> “(car list)” is extracting a value stored in an object, yet it’s not
>> destructuring (though a list is a structure).  Nor even is “(cons (car
>> list) (caddr list))” or “(setq a (nth 1 list) b (nth 2 list))”.
>
> You forget the "multiple" part in the description.

Then you forgot “(cons (car list) (caddr list))” which I proposed later.

> "Destructuring" is not a term that Emacs invented.

Yes, learnt it reading stuff about python and ocaml, afair.

> You can look it up on the Internet; I think you will find that the
> adopted definitions are similar to what I wrote.

Yes, and these are wrong.

> So we don't need to try too hard in this case, as someone else already
> did that for us.

Not “too hard”, nor “hard” at all, nor even correctly.  Or then, any
reference (hence extraction) to something inside a structure, when done
several time, is destructuring, and as this ought to be possible if
structures exist, any language with structures / compound data, does
destructuring all the time.  But when talking about destructuring such
as in cl-destructuring-bind, pcase, python/ml/js multiple-assignments,
this is different.

Wasn’t my definition attempt okay? it even defined three quite used and
intuitive terms.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:20                                                                                                                       ` Eli Zaretskii
@ 2018-11-01  8:36                                                                                                                         ` Achim Gratz
  2018-11-01 10:36                                                                                                                           ` Alan Mackenzie
  0 siblings, 1 reply; 375+ messages in thread
From: Achim Gratz @ 2018-11-01  8:36 UTC (permalink / raw)
  To: emacs-devel

Am 31.10.2018 um 17:20 schrieb Eli Zaretskii:
> I think we can do better in this part:
> 
>      Evaluate BODY with bindings made by matching PATTERN to each
>      element of LIST in turn.  PATTERN is a pcase pattern
> 
> I think using "matching" here is detrimental to understanding what's
> going on, which is a destructuring binding that uses pcase patterns.
> (The "matching" here is between the structures of PATTERN and elements
> of LIST, but the usual meaning of "matching" in Emacs is different,
> especially when "patterns" are mentioned nearby.  So we should not use
> "matching" here, at least not without significant qualifiers, like
> "structure matching" or somesuch.)
> 
> And this:
> 
>      Should the matching fail for any LIST element, the results are
>      undefined.
> 
> should be reworded to explain that elements of LIST should have a
> structure compatible with PATTERN, so that the destructuring works.

How about this:

PATTERN describes the expected structure of LIST and is used to 
establish bindings to corresponding elements of LIST during evaluation 
of BODY.  Undefined behaviour results if the structure of LIST is 
different from that described by PATTERN.


-- 
Achim.

(on the road :-)




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01  8:36                                                                                                                         ` Achim Gratz
@ 2018-11-01 10:36                                                                                                                           ` Alan Mackenzie
  2018-11-01 12:29                                                                                                                             ` Achim Gratz
  2018-11-01 14:19                                                                                                                             ` Michael Heerdegen
  0 siblings, 2 replies; 375+ messages in thread
From: Alan Mackenzie @ 2018-11-01 10:36 UTC (permalink / raw)
  To: Achim Gratz; +Cc: emacs-devel

Hello, Achim.

On Thu, Nov 01, 2018 at 09:36:54 +0100, Achim Gratz wrote:
> Am 31.10.2018 um 17:20 schrieb Eli Zaretskii:
> > I think we can do better in this part:

> >      Evaluate BODY with bindings made by matching PATTERN to each
> >      element of LIST in turn.  PATTERN is a pcase pattern

> > I think using "matching" here is detrimental to understanding what's
> > going on, which is a destructuring binding that uses pcase patterns.
> > (The "matching" here is between the structures of PATTERN and elements
> > of LIST, but the usual meaning of "matching" in Emacs is different,
> > especially when "patterns" are mentioned nearby.  So we should not use
> > "matching" here, at least not without significant qualifiers, like
> > "structure matching" or somesuch.)

> > And this:

> >      Should the matching fail for any LIST element, the results are
> >      undefined.

> > should be reworded to explain that elements of LIST should have a
> > structure compatible with PATTERN, so that the destructuring works.

> How about this:

> PATTERN describes the expected structure of LIST and is used to 
> establish bindings to corresponding elements of LIST during evaluation 
> of BODY.  Undefined behaviour results if the structure of LIST is 
> different from that described by PATTERN.

That doesn't say clearly that BODY is executed once for each LIST
element.

I would also go for "... the expected structure of each LIST element ..."
and "... bindings of the corresponding parts of the element during ....".
And one or two other changes.  That would give something like this:

    (pcase-dolist (PATTERN LIST) BODY...)

    Loop over a list, evaluating BODY for each element of LIST in turn.

    PATTERN describes the expected structure of each LIST element and is
    used to establish bindings to the corresponding parts of the element
    during the evaluation of BODY.  Undefined behavior results if the
    structure of any LIST element is different from PATTERN.

    For a description of PATTERNs, see `pcase'.  See also `dolist'.

What do you think?

> -- 
> Achim.

-- 
Alan Mackenzie (Nuremberg, Germany).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 10:36                                                                                                                           ` Alan Mackenzie
@ 2018-11-01 12:29                                                                                                                             ` Achim Gratz
  2018-11-01 14:19                                                                                                                             ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Achim Gratz @ 2018-11-01 12:29 UTC (permalink / raw)
  To: emacs-devel

Am 01.11.2018 um 11:36 schrieb Alan Mackenzie:
> I would also go for "... the expected structure of each LIST element ..."
> and "... bindings of the corresponding parts of the element during ....".
> And one or two other changes.  That would give something like this:
> 
>      (pcase-dolist (PATTERN LIST) BODY...)
> 
>      Loop over a list, evaluating BODY for each element of LIST in turn.
> 
>      PATTERN describes the expected structure of each LIST element and is
>      used to establish bindings to the corresponding parts of the element
>      during the evaluation of BODY.  Undefined behavior results if the
>      structure of any LIST element is different from PATTERN.
> 
>      For a description of PATTERNs, see `pcase'.  See also `dolist'.
> 
> What do you think?

I'd lose the plural "s" on "PATTERN" in the last sentence, but other 
than that I think it strikes the right balance between brevity and 
explaining the obvious.

-- 
Achim.

(on the road :-)




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 20:31                                                                                               ` Michael Heerdegen
                                                                                                                   ` (2 preceding siblings ...)
  2018-11-01  4:15                                                                                                 ` Eli Zaretskii
@ 2018-11-01 12:30                                                                                                 ` Stefan Monnier
  2018-11-01 14:14                                                                                                   ` Michael Heerdegen
  3 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-11-01 12:30 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, emacs-devel

> ;;; *** /home/micha/software/emacs/lisp/cus-load.el  (154 matches)

This is a generated file.


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-10-31 23:13                                                                                                   ` Garreau, Alexandre
@ 2018-11-01 13:22                                                                                                     ` Clément Pit-Claudel
  2018-11-01 14:11                                                                                                       ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-11-01 13:22 UTC (permalink / raw)
  To: emacs-devel

On 31/10/2018 19.13, Garreau, Alexandre wrote:
> In lisp I would have prefered to be able to directly quote each symbol,
> and have this to work, eg: “(pcase (list 1 2 3) (('a 'b 'c) t))” to
> return nil, and “(pcase (list 'a 'b 'c) (('a 'b 'c) t))” to return t
> (and this is like many other lisp pattern-matching implementations
> already work).  In current pcase, pattern “(a b c)” does *not* mean
> “with symbols 'a, 'b and 'c”.

But remember that this breaks the pattern-body symmetry:  
  (pcase (list 'a 'b 'c) (('a 'b 'c) ('a 'b 'c)))
would match, but the body would raise an error.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: pcase ` meaning
  2018-11-01 13:22                                                                                                     ` Clément Pit-Claudel
@ 2018-11-01 14:11                                                                                                       ` Garreau, Alexandre
  0 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01 14:11 UTC (permalink / raw)
  To: Clément Pit-Claudel; +Cc: emacs-devel

On 2018-11-01 at 09:22, Clément Pit-Claudel wrote:
> On 31/10/2018 19.13, Garreau, Alexandre wrote:
>> In lisp I would have prefered to be able to directly quote each symbol,
>> and have this to work, eg: “(pcase (list 1 2 3) (('a 'b 'c) t))” to
>> return nil, and “(pcase (list 'a 'b 'c) (('a 'b 'c) t))” to return t
>> (and this is like many other lisp pattern-matching implementations
>> already work).  In current pcase, pattern “(a b c)” does *not* mean
>> “with symbols 'a, 'b and 'c”.
>
> But remember that this breaks the pattern-body symmetry:  
>   (pcase (list 'a 'b 'c) (('a 'b 'c) ('a 'b 'c)))
> would match, but the body would raise an error.

Then if it’s important to you, don’t do that, it’s a question of tastes
and style.  Other implementations allow to do that.

You may as well quote the list, or, better imho, use a list constructor
(list 'a 'b 'c) as a pattern.  Which also exists in other
implementations.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 12:30                                                                                                 ` Stefan Monnier
@ 2018-11-01 14:14                                                                                                   ` Michael Heerdegen
  2018-11-01 14:18                                                                                                     ` Noam Postavsky
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-01 14:14 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: Eli Zaretskii, emacs-devel

Stefan Monnier <monnier@IRO.UMontreal.CA> writes:

> > ;;; *** /home/micha/software/emacs/lisp/cus-load.el  (154 matches)
>
> This is a generated file.

Did you check if it is the only one?  Should I just do git clean -xf
before preparing the patch?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 14:14                                                                                                   ` Michael Heerdegen
@ 2018-11-01 14:18                                                                                                     ` Noam Postavsky
  2018-11-01 14:20                                                                                                       ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Noam Postavsky @ 2018-11-01 14:18 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, Stefan Monnier, Emacs developers

On Thu, 1 Nov 2018 at 10:15, Michael Heerdegen <michael_heerdegen@web.de> wrote:
>
> Stefan Monnier <monnier@IRO.UMontreal.CA> writes:
>
> > > ;;; *** /home/micha/software/emacs/lisp/cus-load.el  (154 matches)
> >
> > This is a generated file.
>
> Did you check if it is the only one?  Should I just do git clean -xf
> before preparing the patch?

I'm pretty sure the *-loaddefs files are also generated.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 10:36                                                                                                                           ` Alan Mackenzie
  2018-11-01 12:29                                                                                                                             ` Achim Gratz
@ 2018-11-01 14:19                                                                                                                             ` Michael Heerdegen
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-01 14:19 UTC (permalink / raw)
  To: Alan Mackenzie; +Cc: Achim Gratz, emacs-devel

Alan Mackenzie <acm@muc.de> writes:

>     PATTERN describes the expected structure of each LIST element and is
>     used to establish bindings to the corresponding parts of the element
>     during the evaluation of BODY.  Undefined behavior results if the
>     structure of any LIST element is different from PATTERN.

Maybe leave out "expected"?  Since the PATTERN must match, it should
just match the structure, point.  The programmer should be sure about
that.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 14:18                                                                                                     ` Noam Postavsky
@ 2018-11-01 14:20                                                                                                       ` Michael Heerdegen
  2018-11-05  1:43                                                                                                         ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-01 14:20 UTC (permalink / raw)
  To: Noam Postavsky; +Cc: Eli Zaretskii, Stefan Monnier, Emacs developers

Noam Postavsky <npostavs@gmail.com> writes:

> I'm pretty sure the *-loaddefs files are also generated.

Oh, indeed.  But git clean -xf or so should all remove these - right?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:23                                                                                                         ` Clément Pit-Claudel
@ 2018-11-01 14:44                                                                                                           ` Andy Moreton
  2018-11-01 15:28                                                                                                             ` Clément Pit-Claudel
  0 siblings, 1 reply; 375+ messages in thread
From: Andy Moreton @ 2018-11-01 14:44 UTC (permalink / raw)
  To: emacs-devel

On Wed 31 Oct 2018, Clément Pit-Claudel wrote:

> On 30/10/2018 20.08, Andy Moreton wrote:
>> On Tue 30 Oct 2018, Clément Pit-Claudel wrote:
>> 
>>> On 30/10/2018 14.14, Alan Mackenzie wrote:
>>>> Hello, Clément.
>>>
>>> Hey Alan :)
>>>
>>>> On Tue, Oct 30, 2018 at 11:05:55 -0400, Clément Pit-Claudel wrote:
>>>>> On 30/10/2018 10.16, Andy Moreton wrote:
>>>>>> How are users meant to write reliable code using such constructs ?
>>>>
>>>>> Ensure that the pattern actually matches :)
>>>>
>>>> You mean, unless you can be 100% sure that the pattern will match, you
>>>> mustn't use pcase-... constructs.  That sounds equivalent to saying you
>>>> shouldn't use these constructs at all.
>>>
>>> That's an odd conclusion.
>> 
>> It is a perfectly reasonable conclusion. 
>
> Why? A large number of ELisp functions don't say what they do if their
> argument isn't of the expected type, or doesn't have the expected structure.
> If you're not 100% sure that the argument has the right type, you shouldn't
> use them (instead, you should do an appropriate check first). This is not
> equivalent to saying that they shouldn't be used at all.
>
> I don't understand what's so special about pcase-*. Functions like lookup-key
> or define-key don't tell you what happens if you pass something else that a
> keymap; does that mean you should never use them? Same for a function like
> `c-common-init' in cc-mode (the doc doesn't tell you what happens if you pass
> a symbol that isn't a mode; AFAICT, if you do, you get an error but the
> current buffer is left in a broken state.

The difference is that the non-pcase constructs can document exactly
which types are acceptable as arguments. For the pcase macros, the
acceptable argument types are not fixed by the pcase macro, but depend
on the patterns used. That is harder to explain clearly, and harder for
the user to reason about correctness of the code that they write.

    AndyM





^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 14:44                                                                                                           ` Andy Moreton
@ 2018-11-01 15:28                                                                                                             ` Clément Pit-Claudel
  0 siblings, 0 replies; 375+ messages in thread
From: Clément Pit-Claudel @ 2018-11-01 15:28 UTC (permalink / raw)
  To: emacs-devel

On 01/11/2018 10.44, Andy Moreton wrote:
> The difference is that the non-pcase constructs can document exactly
> which types are acceptable as arguments. For the pcase macros, the
> acceptable argument types are not fixed by the pcase macro, but depend
> on the patterns used. That is harder to explain clearly, and harder for
> the user to reason about correctness of the code that they write.

Thanks, I see what you mean (though it soujnds more like a general indictment of pcase, not just of the "fail silently" behavior of pcase-*). Conversely, though, you could argue that documenting exactly which data are acceptable is precisely what the patterns passed to pcase-let do: if I write `(pcase-let* ((`(,a . ,b) xyz)) …)`, I'm specifying that `xyz' should be a cons.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01  5:21                                                                                                             ` Garreau, Alexandre
@ 2018-11-01 18:07                                                                                                               ` Eli Zaretskii
  2018-11-01 19:35                                                                                                                 ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-01 18:07 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: monnier, emacs-devel

> From: "Garreau\, Alexandre" <galex-713@galex-713.eu>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Thu, 01 Nov 2018 06:21:49 +0100
> 
> >> >   @dfn{Destructuring} of an object is an operation that extracts
> >> >   multiple values stored in the object, e.g., the 2nd and the 3rd
> >> >   element of a list or a vector.  @dfn{Destructuring binding} is
> >> >   similar to a local binding (@pxref{Local Variables}), but it gives
> >> >   values to multiple elements of a variable by extracting those values
> >> >   from an object of compatible structure.
> >> 
> >> “(car list)” is extracting a value stored in an object, yet it’s not
> >> destructuring (though a list is a structure).  Nor even is “(cons (car
> >> list) (caddr list))” or “(setq a (nth 1 list) b (nth 2 list))”.
> >
> > You forget the "multiple" part in the description.
> 
> Then you forgot “(cons (car list) (caddr list))” which I proposed later.

The values need to be extracted in one go, so the above doesn't
qualify.

> > "Destructuring" is not a term that Emacs invented.
> 
> Yes, learnt it reading stuff about python and ocaml, afair.
> 
> > You can look it up on the Internet; I think you will find that the
> > adopted definitions are similar to what I wrote.
> 
> Yes, and these are wrong.

:-)

> Wasn’t my definition attempt okay? it even defined three quite used and
> intuitive terms.

It didn't look like a more clear description to me, no.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 18:07                                                                                                               ` Eli Zaretskii
@ 2018-11-01 19:35                                                                                                                 ` Garreau, Alexandre
  2018-11-01 19:49                                                                                                                   ` TEIRLLM
                                                                                                                                     ` (2 more replies)
  0 siblings, 3 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-01 19:35 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Le 01/11/2018 à 20h07, Eli Zaretskii a écrit :
>> From: "Garreau\, Alexandre" <galex-713@galex-713.eu>
>> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
>> Date: Thu, 01 Nov 2018 06:21:49 +0100
>> 
>> >> >   @dfn{Destructuring} of an object is an operation that extracts
>> >> >   multiple values stored in the object, e.g., the 2nd and the 3rd
>> >> >   element of a list or a vector.  @dfn{Destructuring binding} is
>> >> >   similar to a local binding (@pxref{Local Variables}), but it gives
>> >> >   values to multiple elements of a variable by extracting those values
>> >> >   from an object of compatible structure.
>> >> 
>> >> “(car list)” is extracting a value stored in an object, yet it’s not
>> >> destructuring (though a list is a structure).  Nor even is “(cons (car
>> >> list) (caddr list))” or “(setq a (nth 1 list) b (nth 2 list))”.
>> >
>> > You forget the "multiple" part in the description.
>> 
>> Then you forgot “(cons (car list) (caddr list))” which I proposed later.
>
> The values need to be extracted in one go, so the above doesn't
> qualify.

Let’s say this was in a language were arguments evaluation order is not
specified, and it is wrapped as macro/function set-two-vars-from-car-and-caddr,
how wouldn’t that match your definition?

After all this later form can be considered as atomic, or pcase as not
atomic (it will necessarily get one value before the other), to me
that’s no what’s relevant to the destructuring concept: pcase requires a
pattern to specify matched data structure (same for
cl-destructuring-bind).  That’s what makes “destructuring”.

Another example: the pcase and pcase-* forms are destructuring, but the
lambda pcase-* forms (full of car, cdr and other structure extraction
functions call) are not destructuring, because they don’t refer to
matched data structure, don’t specify it, and even ignore anything not
being related to what it needs to fetch.

>> Wasn’t my definition attempt okay? it even defined three quite used and
>> intuitive terms.
>
> It didn't look like a more clear description to me, no.

Do you have some more precise suggestion on why is not clear and how to
clearly phrase the concept of “specifying a matched data structure”, or
should I just give up and accept the rest of world is fine with a more
loose, large, less specific, and according to me, wrong, definition of
“destructuring”?



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 19:35                                                                                                                 ` Garreau, Alexandre
@ 2018-11-01 19:49                                                                                                                   ` TEIRLLM
  2018-11-03  2:53                                                                                                                     ` Richard Stallman
  2018-11-01 19:51                                                                                                                   ` TEIRLLM
  2018-11-01 20:02                                                                                                                   ` Eli Zaretskii
  2 siblings, 1 reply; 375+ messages in thread
From: TEIRLLM @ 2018-11-01 19:49 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: eliz, monnier, emacs-devel

After reading your question more carefully, I do not really remember
with certainty whether I launched firefox from venus or mars.  I
_believe_ to remember that it was mars.

Sincerely,

Luc.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 19:35                                                                                                                 ` Garreau, Alexandre
  2018-11-01 19:49                                                                                                                   ` TEIRLLM
@ 2018-11-01 19:51                                                                                                                   ` TEIRLLM
  2018-11-01 20:02                                                                                                                   ` Eli Zaretskii
  2 siblings, 0 replies; 375+ messages in thread
From: TEIRLLM @ 2018-11-01 19:51 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: eliz, monnier, emacs-devel

Sorry for my previous message.  I replied by error to the wrong message.
Had nothing to do with emacs-devel.

Sincerely,

Luc.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 19:35                                                                                                                 ` Garreau, Alexandre
  2018-11-01 19:49                                                                                                                   ` TEIRLLM
  2018-11-01 19:51                                                                                                                   ` TEIRLLM
@ 2018-11-01 20:02                                                                                                                   ` Eli Zaretskii
  2 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-01 20:02 UTC (permalink / raw)
  To: Garreau, Alexandre; +Cc: monnier, emacs-devel

> From: "Garreau\, Alexandre" <galex-713@galex-713.eu>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Thu, 01 Nov 2018 20:35:41 +0100
> 
> Let’s say this was in a language were arguments evaluation order is not
> specified, and it is wrapped as macro/function set-two-vars-from-car-and-caddr,
> how wouldn’t that match your definition?
> 
> After all this later form can be considered as atomic, or pcase as not
> atomic (it will necessarily get one value before the other)

That's implementation details.  We are talking about defining the
concept.

> > It didn't look like a more clear description to me, no.
> 
> Do you have some more precise suggestion on why is not clear and how to
> clearly phrase the concept of “specifying a matched data structure”

One problem with your suggestion is that destructuring itself doesn't
need specification of a matching structure to extract values into,
that's only needed for destructuring binding.

When explaining destructuring binding, I used "object of compatible
structure" because I deliberately wanted to avoid using the concept of
"matching", which can easily cause misinterpretation due to its other
meanings in the context of Emacs.

> should I just give up and accept the rest of world is fine with a more
> loose, large, less specific, and according to me, wrong, definition of
> “destructuring”?

That's also an option, of course.

Yet another option is to trust my experience in writing Emacs
documentation a little more.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 19:49                                                                                                                   ` TEIRLLM
@ 2018-11-03  2:53                                                                                                                     ` Richard Stallman
  2018-11-04 11:35                                                                                                                       ` Nix
  0 siblings, 1 reply; 375+ messages in thread
From: Richard Stallman @ 2018-11-03  2:53 UTC (permalink / raw)
  To: TEIRLLM; +Cc: eliz, monnier, galex-713, emacs-devel

[[[ To any NSA and FBI agents reading my email: please consider    ]]]
[[[ whether defending the US Constitution against all enemies,     ]]]
[[[ foreign or domestic, requires you to follow Snowden's example. ]]]

  > After reading your question more carefully, I do not really remember
  > with certainty whether I launched firefox from venus or mars.  I
  > _believe_ to remember that it was mars.

Do we have Emacs users on other planets now?  Wow!!

-- 
Dr Richard Stallman
President, Free Software Foundation (https://gnu.org, https://fsf.org)
Internet Hall-of-Famer (https://internethalloffame.org)





^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-30 18:58                                                                                                             ` Stefan Monnier
  2018-10-31 12:08                                                                                                               ` Alan Mackenzie
@ 2018-11-03 13:13                                                                                                               ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-03 13:13 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

> From: Stefan Monnier <monnier@IRO.UMontreal.CA>
> Cc: emacs-devel@gnu.org
> Date: Tue, 30 Oct 2018 14:58:58 -0400
> 
> >> matching doesn't assign any values to anything directly related to
> >> BODY, so the mechanism by which it affects execution of BODY needs
> >> to be described.
> >
> > Could you please fill that void?  This isn't a repetition of what
> > dolist does.
> 
> I don't know how to say it any better than with the patch I just
> installed into emacs-26.

I made what I think are minor improvements on that text.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 16:13                                                                                                                   ` Eli Zaretskii
  2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
  2018-10-31 17:48                                                                                                                     ` Clément Pit-Claudel
@ 2018-11-03 13:15                                                                                                                     ` Eli Zaretskii
  2 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-03 13:15 UTC (permalink / raw)
  To: dgutov, monnier; +Cc: emacs-devel

> Date: Wed, 31 Oct 2018 18:13:25 +0200
> From: Eli Zaretskii <eliz@gnu.org>
> Cc: monnier@IRO.UMontreal.CA, emacs-devel@gnu.org
> 
> > Cc: emacs-devel@gnu.org
> > From: Dmitry Gutov <dgutov@yandex.ru>
> > Date: Wed, 31 Oct 2018 18:05:44 +0200
> > 
> > > Can someone enlighten me regarding those "holes"?  What does that
> > > allude to?
> > 
> > I stole the term from Clement here: 
> > http://lists.gnu.org/archive/html/emacs-devel/2018-10/msg00590.html
> 
> Ah, the elements that are assigned by destructuring?  I indeed hoped
> we could identify in some way the patterns which satisfy that
> condition.  I didn't give up yet.

It turns out we already have a section for these patterns: "Backquote
Patterns".  So I just refereed to that section.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31 15:47                                                                                                                   ` Eli Zaretskii
  2018-10-31 16:07                                                                                                                     ` Alan Mackenzie
@ 2018-11-03 13:16                                                                                                                     ` Eli Zaretskii
  2018-11-03 15:45                                                                                                                       ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-03 13:16 UTC (permalink / raw)
  To: monnier; +Cc: emacs-devel

> Date: Wed, 31 Oct 2018 17:47:26 +0200
> From: Eli Zaretskii <eliz@gnu.org>
> Cc: emacs-devel@gnu.org
> 
> > From: Stefan Monnier <monnier@iro.umontreal.ca>
> > Date: Wed, 31 Oct 2018 08:33:42 -0400
> > 
> > > Are you willing to put these final touches onto pcase-dolist's doc
> > > string, or would you prefer somebody else to do it?
> > 
> > This is excrutiating for me.  Anyone else but me, please,
> 
> I will try, if no one beats me to it.

Done, I hope.

I would like to take this opportunity to thank everybody who
participated in this discussion.  I tried to use all the good ideas
mentioned here.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03 13:16                                                                                                                     ` Eli Zaretskii
@ 2018-11-03 15:45                                                                                                                       ` Michael Heerdegen
  2018-11-03 16:25                                                                                                                         ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-03 15:45 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> Done, I hope.

Great, thanks Eli.

Some comments/thoughts:

control.texi line 521 "is equals": typo.

| The pcase patterns that are useful for destructuring bindings are
| generally those described in @ref{Backquote Patterns}, since they
| express a specification of the structure of objects that will match.

I don't like that sentence for two reasons:

(1) ` is the pcase pattern for destructuring.  The "Backquote Patterns"
or "Backquote style Patterns" are not really "pcase patterns" since they
are part of the implicit semantics ``' defines.  They are _not_ pcase
patterns.  Your sentence confuses the both.

(2) We already have a lot other patterns for destructuring (eieio, seq,
map, cl-struct), and we probably will get even more in the future.

| @defmac pcase-let bindings body@dots{}
| Perform desctructuring binding of variables according to
| @var{bindings}, and then evaluate @var{body}.

and lots of similar:

`pcase-let', `pcase-dolist' and the like are very often used only for
destructuring, but they are not limited to destructuring.  Like in

(defun test (arg)
  (pcase-let (((or (and (pred stringp) s)
                   (and (pred numberp) (app number-to-string s)))
               arg))
    s))

(test "Hallo") => "Hallo"
(test 1)       => "1"

Also the docstrings give the impression that these are limited to
destructuring, which is not true.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03 15:45                                                                                                                       ` Michael Heerdegen
@ 2018-11-03 16:25                                                                                                                         ` Eli Zaretskii
  2018-11-03 17:12                                                                                                                           ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-03 16:25 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Sat, 03 Nov 2018 16:45:08 +0100
> 
> control.texi line 521 "is equals": typo.

Thanks, fixed.

> | The pcase patterns that are useful for destructuring bindings are
> | generally those described in @ref{Backquote Patterns}, since they
> | express a specification of the structure of objects that will match.
> 
> I don't like that sentence for two reasons:
> 
> (1) ` is the pcase pattern for destructuring.  The "Backquote Patterns"
> or "Backquote style Patterns" are not really "pcase patterns" since they
> are part of the implicit semantics ``' defines.  They are _not_ pcase
> patterns.  Your sentence confuses the both.

Sorry, you lost me here.  How can these not be pcase patterns, when
they are used with 'pcase', and "pcase patterns" are _defined_ as
those used with 'pcase'?

> (2) We already have a lot other patterns for destructuring (eieio, seq,
> map, cl-struct), and we probably will get even more in the future.

OK, but why is that a reason not to use what I wrote?  Note that it
talks about "destructuring binding", not just about destructuring.
Also please note that I made some changes in the description of
seq-let to say that is an alternative facility for destructuring
binding.

The text you quoted doesn't say that those pcase patterns are the
_only_ method of destructuring.  If that is the root cause of your
disliking, we could make this even more clear.

> | @defmac pcase-let bindings body@dots{}
> | Perform desctructuring binding of variables according to
> | @var{bindings}, and then evaluate @var{body}.
> 
> and lots of similar:
> 
> `pcase-let', `pcase-dolist' and the like are very often used only for
> destructuring, but they are not limited to destructuring.  Like in
> 
> (defun test (arg)
>   (pcase-let (((or (and (pred stringp) s)
>                    (and (pred numberp) (app number-to-string s)))
>                arg))
>     s))
> 
> (test "Hallo") => "Hallo"
> (test 1)       => "1"

OK, but why would I need pcase-let in this example?  Isn't the above
the same as

  (defun test (arg)
    (let ((s (cond ((stringp arg) arg)
                   ((numberp arg) (number-to-string arg)))))
      s))

(which is both simpler and shorter)?

> Also the docstrings give the impression that these are limited to
> destructuring, which is not true.

Can you tell where did you get that impression?  The doc strings talk
about destructuring bindings, when BINDINGS have the form specified,
and I believe that is true.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03 16:25                                                                                                                         ` Eli Zaretskii
@ 2018-11-03 17:12                                                                                                                           ` Michael Heerdegen
  2018-11-03 17:55                                                                                                                             ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-03 17:12 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > | The pcase patterns that are useful for destructuring bindings are
> > | generally those described in @ref{Backquote Patterns}, since they
> > | express a specification of the structure of objects that will match.
> > 
> > I don't like that sentence for two reasons:
> > 
> > (1) ` is the pcase pattern for destructuring.  The "Backquote Patterns"
> > or "Backquote style Patterns" are not really "pcase patterns" since
> > they
> > are part of the implicit semantics ``' defines.  They are _not_ pcase
> > patterns.  Your sentence confuses the both.
>
> Sorry, you lost me here.  How can these not be pcase patterns, when
> they are used with 'pcase', and "pcase patterns" are _defined_ as
> those used with 'pcase'?

We called these UPATS in the past btw.

Not every part of a pattern is also a pattern.

,a is not an expression since it's only valid as sexp inside a backquote
expression.  For a similar reason, ,a is not a pcase pattern because
it's only valid in a ` pattern.

(< 1) is also not a pcase pattern, although it's valid inside a pred:
(pred (< 1)).

A pcase pattern should only be called what is valid as PATTERN in a
pcase clause (PATTERN BODY).

> > (2) We already have a lot other patterns for destructuring (eieio, seq,
> > map, cl-struct), and we probably will get even more in the future.
>
> OK, but why is that a reason not to use what I wrote?  Note that it
> talks about "destructuring binding", not just about destructuring.

Well, for binding there is only one pattern, SYMBOL.  But you also write

| since they express a specification of the structure of objects that
| will match.

so this seems to speak about destructuring and not about binding.

> Also please note that I made some changes in the description of
> seq-let to say that is an alternative facility for destructuring
> binding.
>
> The text you quoted doesn't say that those pcase patterns are the
> _only_ method of destructuring.  If that is the root cause of your
> disliking, we could make this even more clear.

I didn't speak about other methods in Emacs, I spoke about other pcase
patterns also performing destructuring.  But

| The pcase patterns that are useful for destructuring bindings are
| generally those described in @ref{Backquote Patterns}

makes it sounds if ` is the only method to get destructuring bindings
with pcase.


> > | @defmac pcase-let bindings body@dots{}
> > | Perform desctructuring binding of variables according to
> > | @var{bindings}, and then evaluate @var{body}.
> > 
> > and lots of similar:
> > 
> > `pcase-let', `pcase-dolist' and the like are very often used only for
> > destructuring, but they are not limited to destructuring.  Like in
> > 
> > (defun test (arg)
> >   (pcase-let (((or (and (pred stringp) s)
> >                    (and (pred numberp) (app number-to-string s)))
> >                arg))
> >     s))
> > 
> > (test "Hallo") => "Hallo"
> > (test 1)       => "1"
>
> OK, but why would I need pcase-let in this example?  Isn't the above
> the same as
>
>   (defun test (arg)
>     (let ((s (cond ((stringp arg) arg)
>                    ((numberp arg) (number-to-string arg)))))
>       s))
>
> (which is both simpler and shorter)?

It was just an example.  And docstrings shouldn't tell restrictions that
don't exist just because you would prefer `cond' in such cases anyway.

> > Also the docstrings give the impression that these are limited to
> > destructuring, which is not true.
>
> Can you tell where did you get that impression?  The doc strings talk
> about destructuring bindings, when BINDINGS have the form specified,
> and I believe that is true.

You say

| Perform desctructuring binding of variables according to
| @var{bindings}, and then evaluate @var{body}.

Any pcase PATTERN can be used in BINDINGS, whether it performs
destructuring or not, the only assumption is that it should match.  You
can say that pcase-let is mostly useful for destructuring the bound
values, but as a summary of what `pcase-let' and the like is about it's
misleading.   It's misleading because I then wonder where the
restriction to destructuring comes from, and what's different to just
matching the patterns against the values as in `pcase'.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03 17:12                                                                                                                           ` Michael Heerdegen
@ 2018-11-03 17:55                                                                                                                             ` Eli Zaretskii
  2018-11-03 22:22                                                                                                                               ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-03 17:55 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Sat, 03 Nov 2018 18:12:43 +0100
> 
> > Sorry, you lost me here.  How can these not be pcase patterns, when
> > they are used with 'pcase', and "pcase patterns" are _defined_ as
> > those used with 'pcase'?
> 
> We called these UPATS in the past btw.
> 
> Not every part of a pattern is also a pattern.
> 
> ,a is not an expression since it's only valid as sexp inside a backquote
> expression.  For a similar reason, ,a is not a pcase pattern because
> it's only valid in a ` pattern.
> 
> (< 1) is also not a pcase pattern, although it's valid inside a pred:
> (pred (< 1)).
> 
> A pcase pattern should only be called what is valid as PATTERN in a
> pcase clause (PATTERN BODY).

Sorry, I'm still in the dark here.  The node I pointed to describes
"backquote-style patterns", and explains that these "ease structural
matching".  The same patterns are useful for destructuring binding,
precisely because destructuring binding needs a structural match.
That is all that I'm trying to convey.  Making that point will help
the reader to understand what subset of pcase patterns will be most
useful for destructuring.

> > > (2) We already have a lot other patterns for destructuring (eieio, seq,
> > > map, cl-struct), and we probably will get even more in the future.
> >
> > OK, but why is that a reason not to use what I wrote?  Note that it
> > talks about "destructuring binding", not just about destructuring.
> 
> Well, for binding there is only one pattern, SYMBOL.  But you also write
> 
> | since they express a specification of the structure of objects that
> | will match.
> 
> so this seems to speak about destructuring and not about binding.

Destructuring binding requires destructuring, that's all.

Again, I don't understand the nature of your objections to the text.

> | The pcase patterns that are useful for destructuring bindings are
> | generally those described in @ref{Backquote Patterns}
> 
> makes it sounds if ` is the only method to get destructuring bindings
> with pcase.

No, it says those are _useful_ for destructuring bindings, that's all.
I'm sure you realize that saying A doesn't say that there's nothing
but A.

> >   (defun test (arg)
> >     (let ((s (cond ((stringp arg) arg)
> >                    ((numberp arg) (number-to-string arg)))))
> >       s))
> >
> > (which is both simpler and shorter)?
> 
> It was just an example.

I submit that any other example, except the ones that follow my
description, will have the same property: they can be rewritten
cleaner, and in many cases also shorter, than using pcase-let etc.

> And docstrings shouldn't tell restrictions that don't exist just
> because you would prefer `cond' in such cases anyway.

So you seem to object to the doc string describing only part of the
possible uses?  If so, this argument was already voiced in the
discussion, and I already said that I think it's a mistake to make our
documentation more vague and therefore more confusing, for the benefit
of being 100% accurate.

IOW, it is quite clear that, knowing the way a macro is implemented,
one can tweak the macro into doing stuff it never was designed to do.
But we introduced pcase-let for a reason, and AFAIU that reason is to
allow destructuring binding.  It can also do other things, but nothing
important will be lost by making the documentation general enough, and
thus vague/abstract enough, to cover those other use cases.

> > > Also the docstrings give the impression that these are limited to
> > > destructuring, which is not true.
> >
> > Can you tell where did you get that impression?  The doc strings talk
> > about destructuring bindings, when BINDINGS have the form specified,
> > and I believe that is true.
> 
> You say
> 
> | Perform desctructuring binding of variables according to
> | @var{bindings}, and then evaluate @var{body}.
> 
> Any pcase PATTERN can be used in BINDINGS, whether it performs
> destructuring or not, the only assumption is that it should match.

But these macros were invented to support destructuring, don't you
agree?  Stefan's original text talked about extracting values (or
subfields), so it was clear to me that Stefan, too, alluded to
destructuring.  I think we should describe the intended usage of these
macros first and foremost.  If the other uses can be described without
losing clarity, fine; but that's not the case here, as the long
discussions seem to show -- people were unhappy with the original
abstract and general descriptions because they didn't tell them enough
about the main use case.

In any case, feel free to suggest modifications of the doc strings
that are more general without losing clarity, and let's take this from
there.

> You can say that pcase-let is mostly useful for destructuring the
> bound values, but as a summary of what `pcase-let' and the like is
> about it's misleading.  It's misleading because I then wonder where
> the restriction to destructuring comes from, and what's different to
> just matching the patterns against the values as in `pcase'.

I disagree that it's misleading.  If you care so much about the
restrictions, or lack thereof, you are welcome to study the code.  But
the doc string should explain how to use the macro to the rest of us.

We write our documentation to be useful in the main use cases, not to
be 110% accurate.  Favoring the latter at the price of obfuscating the
former is IME a serious mistake that produces inferior programming
docs.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03 17:55                                                                                                                             ` Eli Zaretskii
@ 2018-11-03 22:22                                                                                                                               ` Michael Heerdegen
  2018-11-04 14:16                                                                                                                                 ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-03 22:22 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > We called these UPATS in the past btw.

That should have been QPATs, sorry.

> Sorry, I'm still in the dark here.  The node I pointed to describes
> "backquote-style patterns", and explains that these "ease structural
> matching".  The same patterns are useful for destructuring binding,
> precisely because destructuring binding needs a structural match.
> That is all that I'm trying to convey.  Making that point will help
> the reader to understand what subset of pcase patterns will be most
> useful for destructuring.

So, I should read it as "the set of patterns that are of the form
`SOMETHING"?  I had read it as the set of what we call "QPATs".  So we
have probably talked about different things.

I find the wording used in (info "(elisp) Backquote Patterns")
confusing, especially the first sentence "This subsection describes
“backquote-style patterns”, a set of builtin patterns that eases
structural matching." which seems to introduce a whole set of builtin
patterns though it talks only about one macro, `.

You only refer to that in your change, using the same wording, so what
you changed is consistent with what we have, although I don't like it
that much.


> > > > (2) We already have a lot other patterns for destructuring
> > > > (eieio, seq, map, cl-struct), and we probably will get even more
> > > > in the future.
> > >
> > > OK, but why is that a reason not to use what I wrote?  Note that it
> > > talks about "destructuring binding", not just about destructuring.
> > 
> > Well, for binding there is only one pattern, SYMBOL.  But you also
> > write
> > 
> > | since they express a specification of the structure of objects that
> > | will match.
> > 
> > so this seems to speak about destructuring and not about binding.
>
> Destructuring binding requires destructuring, that's all.

"Destructuring binding" - pcase has nothing like that.  We have a
pattern type for binding, SYMBOL, and diverse for performing
destructuring, ``' being the main and most general one.  You can combine
these, but both are different things.

We talk about this paragraph:

| +The pcase patterns that are useful for destructuring bindings are
| +generally those described in @ref{Backquote Patterns}, since they
| +express a specification of the structure of objects that will match.

I would already be happy if you would leave out the word "bindings".
Establishing bindings is not the only use of `.

> Again, I don't understand the nature of your objections to the text.
>
> > | The pcase patterns that are useful for destructuring bindings are
> > | generally those described in @ref{Backquote Patterns}
> > 
> > makes it sounds if ` is the only method to get destructuring bindings
> > with pcase.
>
> No, it says those are _useful_ for destructuring bindings, that's all.
> I'm sure you realize that saying A doesn't say that there's nothing
> but A.

Sorry, I'm not an native English speaker.  But "are generally those"
sounds quite, well, generalizing to me ;-)

> I submit that any other example, except the ones that follow my
> description, will have the same property: they can be rewritten
> cleaner, and in many cases also shorter, than using pcase-let etc.

But that's personal preference.  I found at least one example of such a
`pcase-let' that doesn't use destructuring in the Emacs sources.  It
isn't wrong just because you would personally write it in a different
way, and it should be understandable after reading the docs.  All
occurrences should be understandable after reading the docs, not only
those that are main use cases or cases that the inventor had in mind
when the thing was created.

> > And docstrings shouldn't tell restrictions that don't exist just
> > because you would prefer `cond' in such cases anyway.
>
> So you seem to object to the doc string describing only part of the
> possible uses?  If so, this argument was already voiced in the
> discussion, and I already said that I think it's a mistake to make our
> documentation more vague and therefore more confusing, for the benefit
> of being 100% accurate.

I don't suggest to make it vague.  In my option, what you did in your
change makes it more vague, actually.  What we write in the docs should
be correct, at least.

> IOW, it is quite clear that, knowing the way a macro is implemented,
> one can tweak the macro into doing stuff it never was designed to do.

These are still valid use cases.

> But we introduced pcase-let for a reason, and AFAIU that reason is to
> allow destructuring binding.  It can also do other things, but nothing
> important will be lost by making the documentation general enough, and
> thus vague/abstract enough, to cover those other use cases.

I don't understand what this means in concrete.

> > > > Also the docstrings give the impression that these are limited to
> > > > destructuring, which is not true.
> > >
> > > Can you tell where did you get that impression?  The doc strings talk
> > > about destructuring bindings, when BINDINGS have the form specified,
> > > and I believe that is true.
> > 
> > You say
> > 
> > | Perform desctructuring binding of variables according to
> > | @var{bindings}, and then evaluate @var{body}.
> > 
> > Any pcase PATTERN can be used in BINDINGS, whether it performs
> > destructuring or not, the only assumption is that it should match.
>
> But these macros were invented to support destructuring, don't you
> agree?

To 100%.

> Stefan's original text talked about extracting values (or subfields),
> so it was clear to me that Stefan, too, alluded to destructuring.

It talked about "extracting data".  It didn't restrict to what data and
from where.  Destructuring comes to my mind when I read that, but
"extracting data" doesn't explicitly limit it to that case.  I wouldn't
have chosen that wording, however.  It was not the original docstring,
btw, but one Stefan had rewritten after he had been urged to by people
(like you) who were not happy with the original docstring.  The original
docstring was clearer in that regard, indeed.

> I think we should describe the intended usage of these macros first
> and foremost.  If the other uses can be described without losing
> clarity, fine; but that's not the case here, as the long discussions
> seem to show -- people were unhappy with the original abstract and
> general descriptions because they didn't tell them enough about the
> main use case.

I'm not against telling the main use cases.  But a thing isn't described
completely or even in a good way only by telling the main use cases.

> > You can say that pcase-let is mostly useful for destructuring the
> > bound values, but as a summary of what `pcase-let' and the like is
> > about it's misleading.  It's misleading because I then wonder where
> > the restriction to destructuring comes from, and what's different to
> > just matching the patterns against the values as in `pcase'.
>
> I disagree that it's misleading.  If you care so much about the
> restrictions, or lack thereof, you are welcome to study the code.  But
> the doc string should explain how to use the macro to the rest of us.

Say the "rest of us" is 50% of the people.  The other 50% don't matter?
The docs get more confusing for them.

What would you say if I would change the docstring of `cond' to say it's
limited to the cases where I would use it, just because I, and lots of
other people ("the rest of us") would prefer something more suited in
our eyes in these cases, like pcase?

Also, not only people write pcase/pcase-let expressions, but also code
can do that.  The documentation should make clear what is allowed and
what not also for that case.  After saying that you can write how the
main use cases look like.  FWIW, I always thought that the docstrings
tell how something works and what it does, and the manual is for
learning and telling use cases.

It's also a difference between "... is typically used for" (which I
would find ok) and "... does this and that" and it's not accurate.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03  2:53                                                                                                                     ` Richard Stallman
@ 2018-11-04 11:35                                                                                                                       ` Nix
  2018-11-04 12:40                                                                                                                         ` Garreau, Alexandre
  0 siblings, 1 reply; 375+ messages in thread
From: Nix @ 2018-11-04 11:35 UTC (permalink / raw)
  To: Richard Stallman; +Cc: galex-713, eliz, monnier, TEIRLLM, emacs-devel

On 3 Nov 2018, Richard Stallman told this:

> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
> [[[ whether defending the US Constitution against all enemies,     ]]]
> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
>
>   > After reading your question more carefully, I do not really remember
>   > with certainty whether I launched firefox from venus or mars.  I
>   > _believe_ to remember that it was mars.
>
> Do we have Emacs users on other planets now?  Wow!!

I thought this was implying that pcase is from Mars, cond is from Venus
(or vice versa). :)

-- 
NULL && (void)



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-04 11:35                                                                                                                       ` Nix
@ 2018-11-04 12:40                                                                                                                         ` Garreau, Alexandre
  0 siblings, 0 replies; 375+ messages in thread
From: Garreau, Alexandre @ 2018-11-04 12:40 UTC (permalink / raw)
  To: Nix; +Cc: eliz, emacs-devel, Richard Stallman, TEIRLLM, monnier

On 2018/11/04 at 11:35, Nix wrote:
> On 3 Nov 2018, Richard Stallman told this:
>
>> [[[ To any NSA and FBI agents reading my email: please consider    ]]]
>> [[[ whether defending the US Constitution against all enemies,     ]]]
>> [[[ foreign or domestic, requires you to follow Snowden's example. ]]]
>>
>>   > After reading your question more carefully, I do not really remember
>>   > with certainty whether I launched firefox from venus or mars.  I
>>   > _believe_ to remember that it was mars.
>>
>> Do we have Emacs users on other planets now?  Wow!!
>
> I thought this was implying that pcase is from Mars, cond is from Venus
> (or vice versa). :)

I assumed mars and venus were hostnames (unless it was part of a
(context-lacking, for us) joke), I don’t see the relationship between
firefox and elisp (yet there’s one between a such message and emacs
since it was posted on this list, implying the author uses emacs
anyway).



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-03 22:22                                                                                                                               ` Michael Heerdegen
@ 2018-11-04 14:16                                                                                                                                 ` Eli Zaretskii
  2018-11-06  0:00                                                                                                                                   ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-04 14:16 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Sat, 03 Nov 2018 23:22:02 +0100
> 
> >                                     The node I pointed to describes
> > "backquote-style patterns", and explains that these "ease structural
> > matching".  The same patterns are useful for destructuring binding,
> > precisely because destructuring binding needs a structural match.
> > That is all that I'm trying to convey.  Making that point will help
> > the reader to understand what subset of pcase patterns will be most
> > useful for destructuring.
> 
> So, I should read it as "the set of patterns that are of the form
> `SOMETHING"?  I had read it as the set of what we call "QPATs".  So we
> have probably talked about different things.

I refer to the patterns described in that section.  They are all
`SOMETHING, but not just any SOMETHING.  Does that answer your
question?  (Please don't talk about QPATs, that term no longer exists
in the manual, so using it is just making this discussion more
confusing than it already is.)

> I find the wording used in (info "(elisp) Backquote Patterns")
> confusing, especially the first sentence "This subsection describes
> “backquote-style patterns”, a set of builtin patterns that eases
> structural matching." which seems to introduce a whole set of builtin
> patterns though it talks only about one macro, `.
> 
> You only refer to that in your change, using the same wording, so what
> you changed is consistent with what we have, although I don't like it
> that much.

The current description of pcase uses took a lot of time and effort to
get to the current shape, so I'm going to trust those who labored on
it that they found the best balance between clarity and accuracy.

In any case, that's a separate issue, let's please not mix them.  I
didn't change anything in that section, only referred to it.

> > Destructuring binding requires destructuring, that's all.
> 
> "Destructuring binding" - pcase has nothing like that.

The section in question is not about pcase, it's about pcase-let,
pcase-let*, and pcase-dolist.

>                                                     We have a
> pattern type for binding, SYMBOL, and diverse for performing
> destructuring, ``' being the main and most general one.  You can combine
> these, but both are different things.

The macros described in the section we are talking about provide a
kind of binding.  I needed to describe how to use the combination of
the above, so I called that "destructuring binding", both to follow
terminology accepted in other languages and to provide a concise
description of this combination that doesn't require too many words.
Since you seem to agree that there is destructuring and there is
binding, I don't understand the nature of your objections to the term
"destructuring binding", as defined in this section.  Are you saying
that this description:

  [...] similar to a local binding (@pxref{Local Variables}), but
  gives values to multiple elements of a variable by extracting
  those values from an object of compatible structure.

is incorrect, or that pcase patterns don't allow them, or that
pcase-let etc. is not about using such bindings in the BODY?

> We talk about this paragraph:
> 
> | +The pcase patterns that are useful for destructuring bindings are
> | +generally those described in @ref{Backquote Patterns}, since they
> | +express a specification of the structure of objects that will match.
> 
> I would already be happy if you would leave out the word "bindings".
> Establishing bindings is not the only use of `.

The text doesn't say that the only use of ` is for establishing
bindings.  It says that destructuring bindings can be done by using
backquote-style patterns.  That's not the same, as you surely realize.
If A can be done by using B, it doesn't imply that B's only use is to
do A.  The text you quote says the former and never says anything to
imply the latter.  So I'm really surprised that you interpret it that
way.

> > > | The pcase patterns that are useful for destructuring bindings are
> > > | generally those described in @ref{Backquote Patterns}
> > > 
> > > makes it sounds if ` is the only method to get destructuring bindings
> > > with pcase.
> >
> > No, it says those are _useful_ for destructuring bindings, that's all.
> > I'm sure you realize that saying A doesn't say that there's nothing
> > but A.
> 
> Sorry, I'm not an native English speaker.  But "are generally those"
> sounds quite, well, generalizing to me ;-)

Would you be happier if the text said "typically" instead of
"generally"?  Because that's what it means.

> > Stefan's original text talked about extracting values (or subfields),
> > so it was clear to me that Stefan, too, alluded to destructuring.
> 
> It talked about "extracting data".

It talked about extracting subfields of objects.  Isn't that
destructuring?

> It's also a difference between "... is typically used for" (which I
> would find ok) and "... does this and that" and it's not accurate.

Could you please tell what concrete changes in the doc strings of
pcase-let etc. would make you happier?  I feel that we are trapped in
abstract discussions with no clear way out, and I think I'm at least
slightly confused what is it that you don't like about the current
docs.  Concrete proposals for changes might go a long way towards
dispersing the fog.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-01 14:20                                                                                                       ` Michael Heerdegen
@ 2018-11-05  1:43                                                                                                         ` Michael Heerdegen
  2018-11-05  1:46                                                                                                           ` Michael Heerdegen
  2018-11-05 16:06                                                                                                           ` Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-05  1:43 UTC (permalink / raw)
  To: Emacs developers; +Cc: Eli Zaretskii, Stefan Monnier, Noam Postavsky

Michael Heerdegen <michael_heerdegen@web.de> writes:

> > I'm pretty sure the *-loaddefs files are also generated.
>
> Oh, indeed.  But git clean -xf or so should all remove these - right?

Ok, I did that in my repo to exclude the generated files.  I also kept
in mind that some files are distributed via Gnu Elpa and 'SOMETHING may
not be used there as a pcase pattern.

I decided to not perform the 'DOESNT-HAVE-TO-BE-QUOTED replacement:
while browsing the matches, I found that this seems to touch personal
preferences and personal styles in too many cases.  I wouldn't want that
somebody would treat my code in such a way.

The `DOESNT-UNQUOTE thing is a bit different.  It also touches stylistic
reasoning, but OTOH confuses people because when the backquote is
followed by a list than it's not clear that it's actually just a
constant list and not something constructed.  Replacing the backquote
with a quote can improve readability.

OTOH, some people seem to prefer that the body of a macro is always a
backquote expression.  And that, also recursively in unquoted parts that
need to be quoted.  Likewise, there are lots of backquoted :type
defcustom expressions, and lots of backquoted menu specifications.  Of
course, lots were also pcase patterns.

I tried to filter out those very few cases that could not be replaced
with quotes.  Hope I found all.

For now, I attach a patch were I replaced nearly everything where it was
possible.  Comments welcome.  If we are sure which changes we want to
keep, I'll do the final fine-tuning (fixing indentation and comments, if
some were shifted, etc.)

BTW, some files use backquotes very excessively, mainly
lisp/progmodes/verilog-mode.el.  I guess verilog consists mainly of
backquotes?

There were some backquoted function names and lambdas.  I replaced the
backquote with #' (symbols), and most of the time nothing (lambdas in
lexical binding files).  I was very conservative with lambdas in files
that didn't use lexbind.

Finally, the thing I found in lisp/calendar/time-date.el looked like a
bug to me I found by accident.

I'm attaching the patch.


Michael.




^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-05  1:43                                                                                                         ` Michael Heerdegen
@ 2018-11-05  1:46                                                                                                           ` Michael Heerdegen
  2018-11-05 16:06                                                                                                           ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-05  1:46 UTC (permalink / raw)
  To: Emacs developers; +Cc: Eli Zaretskii, Stefan Monnier, Noam Postavsky

[-- Attachment #1: Type: text/plain, Size: 206 bytes --]

Michael Heerdegen <michael_heerdegen@web.de> writes:

> I'm attaching the patch.

Gnus refused the send the attachment, it complained about multibyte
characters.  Trying again with the patch in a tarball.


[-- Attachment #2: replace-backquote-patch.tar --]
[-- Type: application/x-tar, Size: 368640 bytes --]

^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-10-31  3:09                                                                                                 ` Stefan Monnier
@ 2018-11-05  2:01                                                                                                   ` Michael Heerdegen
  2018-11-05  4:49                                                                                                     ` Stefan Monnier
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-05  2:01 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Stefan Monnier <monnier@IRO.UMontreal.CA> writes:

> But some of the preds and guards of other branches (both before and
> after the one of BODY1) may also be run before getting to BODY1.

Does that imply that we also should remove sentences like these from the
manual (last line):

@item (and @var{pattern1}@dots{})
Attempts to match @var{pattern1}@dots{}, in order,
until one of them fails to match.
In that case, @code{and} likewise fails to match,
and the rest of the sub-patterns are not tested.


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-05  2:01                                                                                                   ` Michael Heerdegen
@ 2018-11-05  4:49                                                                                                     ` Stefan Monnier
  2018-11-05 23:06                                                                                                       ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Stefan Monnier @ 2018-11-05  4:49 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel

>> But some of the preds and guards of other branches (both before and
>> after the one of BODY1) may also be run before getting to BODY1.
>
> Does that imply that we also should remove sentences like these from the
> manual (last line):
>
> @item (and @var{pattern1}@dots{})
> Attempts to match @var{pattern1}@dots{}, in order,
> until one of them fails to match.
> In that case, @code{and} likewise fails to match,
> and the rest of the sub-patterns are not tested.

No, that one sounds fine.
Why do you think it's inconsistent with what I said?


        Stefan



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-05  1:43                                                                                                         ` Michael Heerdegen
  2018-11-05  1:46                                                                                                           ` Michael Heerdegen
@ 2018-11-05 16:06                                                                                                           ` Eli Zaretskii
  2018-11-06  1:04                                                                                                             ` Michael Heerdegen
  1 sibling, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-05 16:06 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: npostavs, monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Eli Zaretskii <eliz@gnu.org>,  Stefan Monnier <monnier@iro.umontreal.ca>,  Noam Postavsky <npostavs@gmail.com>
> Date: Mon, 05 Nov 2018 02:43:56 +0100
> 
> For now, I attach a patch were I replaced nearly everything where it was
> possible.  Comments welcome.  If we are sure which changes we want to
> keep, I'll do the final fine-tuning (fixing indentation and comments, if
> some were shifted, etc.)
> 
> BTW, some files use backquotes very excessively, mainly
> lisp/progmodes/verilog-mode.el.  I guess verilog consists mainly of
> backquotes?
> 
> There were some backquoted function names and lambdas.  I replaced the
> backquote with #' (symbols), and most of the time nothing (lambdas in
> lexical binding files).  I was very conservative with lambdas in files
> that didn't use lexbind.
> 
> Finally, the thing I found in lisp/calendar/time-date.el looked like a
> bug to me I found by accident.
> 
> I'm attaching the patch.

I obviously didn't proofread all of the changes, but what I did looked
good.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-05  4:49                                                                                                     ` Stefan Monnier
@ 2018-11-05 23:06                                                                                                       ` Michael Heerdegen
  0 siblings, 0 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-05 23:06 UTC (permalink / raw)
  To: Stefan Monnier; +Cc: emacs-devel

Stefan Monnier <monnier@IRO.UMontreal.CA> writes:

> >> But some of the preds and guards of other branches (both before and
> >> after the one of BODY1) may also be run before getting to BODY1.
> >
> > Does that imply that we also should remove sentences like these from
> > the manual (last line):
> >
> > @item (and @var{pattern1}@dots{})
> > Attempts to match @var{pattern1}@dots{}, in order,
> > until one of them fails to match.
> > In that case, @code{and} likewise fails to match,
> > and the rest of the sub-patterns are not tested.
>
> No, that one sounds fine.
> Why do you think it's inconsistent with what I said?

I wondered if what you said about the preds and guards of other branches
is also true about preds and guards in other "branches" in ors and ands.

With other words, I wonder when we say

> > In that case, @code{and} likewise fails to match,
> > and the rest of the sub-patterns are not tested.

if what users expects to be the "rest" of subpatterns is always the
patterns lexically following the one that failed.

Are patterns in or and and always tested in order?  And, if these
include preds or guards, always exactly once?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-04 14:16                                                                                                                                 ` Eli Zaretskii
@ 2018-11-06  0:00                                                                                                                                   ` Michael Heerdegen
  2018-11-06  3:30                                                                                                                                     ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-06  0:00 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> > > Destructuring binding requires destructuring, that's all.
> > 
> > "Destructuring binding" - pcase has nothing like that.
>
> The section in question is not about pcase, it's about pcase-let,
> pcase-let*, and pcase-dolist.

I only summarized these as `pcase' since they use the same pattern
matching mechanism from pcase.

> Would you be happier if the text said "typically" instead of
> "generally"?  Because that's what it means.

It's ok for me if it means that.

> Could you please tell what concrete changes in the doc strings of
> pcase-let etc. would make you happier?  I feel that we are trapped in
> abstract discussions with no clear way out, and I think I'm at least
> slightly confused what is it that you don't like about the current
> docs.

I'm also confused.

I found the old docstrings simple and clear (though they lacked some
details).  I find already reading the new docstrings in order to make
suggestions for improvements straining.

After I read your response, I see and can comprehend now that everything
makes sense from your point of view.  You have a totally different view
and understanding than I.  For example, for you

  `(,a ,b)

and

  `[,a ,b]

are two different patterns for destructuring binding that can be used in
pcase.

For me, I see SYMBOL as the trivial pattern thing to establish bindings,
and the ` macro which has a simple specification that fits into very few
lines, and above we have two examples of combining and using the two.

I can only say that I find the new docstrings more confusing and
complicated than before, and I find it a mistake to describe the
behavior using concepts like "destructuring binding" that neither have a
direct counterpart in the implementation nor in the specification.  I
agree it could help people when the manual uses such concepts to explain
things and make nice chapters, but I don't like it when docstrings use
such terms, terms that are not clearly defined and don't really fit to
how the thing actually works, instead of giving a clear description.  I
understand now that the new docstrings actually give a clear description
to you; for me, they are now harder to read and understand.

So I don't think I can be of much help, becauseprobably my suggestions
would not be acceptable for you.  I wonder if there is still a way to
provide the old docstrings, at least as comments in the sources?


Thanks,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-05 16:06                                                                                                           ` Eli Zaretskii
@ 2018-11-06  1:04                                                                                                             ` Michael Heerdegen
  2018-11-25 20:36                                                                                                               ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-06  1:04 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: npostavs, monnier, emacs-devel

Eli Zaretskii <eliz@gnu.org> writes:

> I obviously didn't proofread all of the changes, but what I did looked
> good.

Thanks.  I'll wait some more days to see whether there are more
comments.

BTW, I think I'll revert the apparent fix in

diff --git a/lisp/calendar/time-date.el b/lisp/calendar/time-date.el
index c3898e0257..bb54ad46e3 100644
--- a/lisp/calendar/time-date.el
+++ b/lisp/calendar/time-date.el
@@ -109,7 +109,7 @@ with-decoded-time-value
 				  ,(append `(setq ,pico 0)
 					   (when type `(,type 2)))))
 			      (type
-			       `(setq type 2))))
+			       `(setq ,type 2))))
 		   ,(append `(setq ,micro 0)
 			    (when pico `(,pico 0))
 			    (when type `(,type 1)))))

The affected macro 'with-decoded-time-value' has been obsolete since
25.1, so I would prefer to just leave it as is.  It's not used anywhere
in Emacs.


Michael.



^ permalink raw reply related	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-06  0:00                                                                                                                                   ` Michael Heerdegen
@ 2018-11-06  3:30                                                                                                                                     ` Eli Zaretskii
  0 siblings, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-06  3:30 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  emacs-devel@gnu.org
> Date: Tue, 06 Nov 2018 01:00:56 +0100
> 
> I wonder if there is still a way to provide the old docstrings, at
> least as comments in the sources?

If you show a patch to do that, we can discuss that.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-06  1:04                                                                                                             ` Michael Heerdegen
@ 2018-11-25 20:36                                                                                                               ` Michael Heerdegen
  2018-11-25 20:42                                                                                                                 ` Nicolas Goaziou
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-25 20:36 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel, npostavs, monnier

Michael Heerdegen <michael_heerdegen@web.de> writes:

> Thanks.  I'll wait some more days to see whether there are more
> comments.

I installed the commit into master.

Is there anything else here for me to do?

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-25 20:36                                                                                                               ` Michael Heerdegen
@ 2018-11-25 20:42                                                                                                                 ` Nicolas Goaziou
  2018-11-25 21:46                                                                                                                   ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Nicolas Goaziou @ 2018-11-25 20:42 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, npostavs, monnier, emacs-devel

Hello,

Michael Heerdegen <michael_heerdegen@web.de> writes:

> Michael Heerdegen <michael_heerdegen@web.de> writes:
>
>> Thanks.  I'll wait some more days to see whether there are more
>> comments.
>
> I installed the commit into master.
>
> Is there anything else here for me to do?

I though you said you were not going to change Org since it was
developed out of tree. 

The problem here is that we still support Emacs 24.4, and correct me if
I'm wrong, it still requires ` instead of '. If I'm correct, would it be
possible to discard changes made to the Org base?

Thank you.

Regards,

-- 
Nicolas Goaziou



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-25 20:42                                                                                                                 ` Nicolas Goaziou
@ 2018-11-25 21:46                                                                                                                   ` Michael Heerdegen
  2018-11-26  3:35                                                                                                                     ` Eli Zaretskii
  0 siblings, 1 reply; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-25 21:46 UTC (permalink / raw)
  To: Nicolas Goaziou; +Cc: Eli Zaretskii, npostavs, monnier, emacs-devel

Nicolas Goaziou <mail@nicolasgoaziou.fr> writes:

> I though you said you were not going to change Org since it was
> developed out of tree.

AFAIR I asked but got no answer, so I thought I was wrong.

> The problem here is that we still support Emacs 24.4, and correct me
> if I'm wrong, it still requires ` instead of '. If I'm correct, would
> it be possible to discard changes made to the Org base?

Do all agree that I should revert change for the affected org files?


Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-25 21:46                                                                                                                   ` Michael Heerdegen
@ 2018-11-26  3:35                                                                                                                     ` Eli Zaretskii
  2018-11-26 20:57                                                                                                                       ` Michael Heerdegen
  0 siblings, 1 reply; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-26  3:35 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: monnier, npostavs, mail, emacs-devel

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: Eli Zaretskii <eliz@gnu.org>,  emacs-devel@gnu.org,  npostavs@gmail.com,  monnier@iro.umontreal.ca
> Date: Sun, 25 Nov 2018 22:46:42 +0100
> 
> > The problem here is that we still support Emacs 24.4, and correct me
> > if I'm wrong, it still requires ` instead of '. If I'm correct, would
> > it be possible to discard changes made to the Org base?
> 
> Do all agree that I should revert change for the affected org files?

If that will cause problems in Emacs 24, yes.

Thanks.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-26  3:35                                                                                                                     ` Eli Zaretskii
@ 2018-11-26 20:57                                                                                                                       ` Michael Heerdegen
  2018-11-26 22:05                                                                                                                         ` Nicolas Goaziou
  2018-11-27  5:35                                                                                                                         ` Eli Zaretskii
  0 siblings, 2 replies; 375+ messages in thread
From: Michael Heerdegen @ 2018-11-26 20:57 UTC (permalink / raw)
  To: Eli Zaretskii; +Cc: emacs-devel, monnier, mail, npostavs

Eli Zaretskii <eliz@gnu.org> writes:

> > Do all agree that I should revert change for the affected org files?
>
> If that will cause problems in Emacs 24, yes.

Ok, done in d28118940c "Revert "Replace insignificant backquotes" for
Org files".


Thanks,

Michael.



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-26 20:57                                                                                                                       ` Michael Heerdegen
@ 2018-11-26 22:05                                                                                                                         ` Nicolas Goaziou
  2018-11-27  5:35                                                                                                                         ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: Nicolas Goaziou @ 2018-11-26 22:05 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: Eli Zaretskii, npostavs, monnier, emacs-devel

Hello,

Michael Heerdegen <michael_heerdegen@web.de> writes:

> Eli Zaretskii <eliz@gnu.org> writes:
>
>> > Do all agree that I should revert change for the affected org files?
>>
>> If that will cause problems in Emacs 24, yes.
>
> Ok, done in d28118940c "Revert "Replace insignificant backquotes" for
> Org files".

Thank you.

Regards,

-- 
Nicolas Goaziou



^ permalink raw reply	[flat|nested] 375+ messages in thread

* Re: Replace trivial pcase occurrences in the Emacs sources
  2018-11-26 20:57                                                                                                                       ` Michael Heerdegen
  2018-11-26 22:05                                                                                                                         ` Nicolas Goaziou
@ 2018-11-27  5:35                                                                                                                         ` Eli Zaretskii
  1 sibling, 0 replies; 375+ messages in thread
From: Eli Zaretskii @ 2018-11-27  5:35 UTC (permalink / raw)
  To: Michael Heerdegen; +Cc: emacs-devel, monnier, mail, npostavs

> From: Michael Heerdegen <michael_heerdegen@web.de>
> Cc: monnier@iro.umontreal.ca,  npostavs@gmail.com,  mail@nicolasgoaziou.fr,  emacs-devel@gnu.org
> Date: Mon, 26 Nov 2018 21:57:15 +0100
> 
> Eli Zaretskii <eliz@gnu.org> writes:
> 
> > > Do all agree that I should revert change for the affected org files?
> >
> > If that will cause problems in Emacs 24, yes.
> 
> Ok, done in d28118940c "Revert "Replace insignificant backquotes" for
> Org files".

Thanks, and thanks again for working on these cleanups.



^ permalink raw reply	[flat|nested] 375+ messages in thread

end of thread, other threads:[~2018-11-27  5:35 UTC | newest]

Thread overview: 375+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-12-16 20:26 The poor state of documentation of pcase like things Alan Mackenzie
2015-12-16 20:53 ` Kaushal Modi
2015-12-17 16:34   ` John Wiegley
2015-12-17 19:22     ` Kaushal Modi
2015-12-17 21:16     ` Phillip Lord
2015-12-17 21:56       ` Drew Adams
2015-12-17 22:22         ` Phillip Lord
2015-12-18  7:15       ` Eli Zaretskii
2015-12-18  9:12         ` Rasmus
2015-12-18  9:21           ` Eli Zaretskii
2015-12-18  9:57             ` Rasmus
2015-12-18 10:13             ` David Kastrup
2015-12-18 10:47               ` Eli Zaretskii
2015-12-18 16:44                 ` Phillip Lord
2015-12-18 17:17                   ` Eli Zaretskii
2015-12-18 17:24                     ` David Kastrup
2015-12-18 18:47                       ` Eli Zaretskii
2015-12-19 11:23                     ` Eli Zaretskii
2015-12-19 11:39                       ` David Kastrup
2015-12-19 12:15                         ` Eli Zaretskii
2015-12-19 20:35                           ` Phillip Lord
2015-12-19 20:58                             ` Eli Zaretskii
2015-12-19 22:23                               ` Phillip Lord
2015-12-20  3:38                                 ` Eli Zaretskii
2015-12-20 22:54                                   ` Phillip Lord
2015-12-20 14:16                                 ` Michael Heerdegen
2015-12-18 12:23             ` Marcin Borkowski
2015-12-18 10:30         ` Phillip Lord
2015-12-18 12:21         ` Marcin Borkowski
2015-12-22  5:20         ` John Wiegley
2015-12-17 21:26     ` Alan Mackenzie
2015-12-17 23:34       ` John Wiegley
2015-12-18  7:16       ` Eli Zaretskii
2015-12-19 15:31     ` Michael Heerdegen
2015-12-22  5:25       ` John Wiegley
2015-12-22 13:16         ` Michael Heerdegen
2015-12-18  0:42   ` John Wiegley
2015-12-18  4:07     ` Richard Stallman
2015-12-18 10:39       ` Phillip Lord
2015-12-19 15:14         ` Michael Heerdegen
2015-12-19 19:23           ` Phillip Lord
2015-12-19 21:09             ` Michael Heerdegen
2015-12-19 21:57               ` Phillip Lord
2015-12-20  5:13                 ` Richard Stallman
2015-12-20  9:25                   ` Phillip Lord
2015-12-21  5:04                     ` Richard Stallman
2015-12-21 10:15                       ` Phillip Lord
2015-12-22  5:18                       ` John Wiegley
2015-12-20 13:45                   ` Michael Heerdegen
2015-12-20 13:33                 ` Michael Heerdegen
2015-12-20 18:51                   ` Phillip Lord
2015-12-24 17:46                     ` Michael Heerdegen
2015-12-24 17:51                       ` John Wiegley
2015-12-24 19:10                         ` Michael Heerdegen
2015-12-19 19:24           ` Phillip Lord
2015-12-18  8:55     ` Eli Zaretskii
2015-12-19 15:18       ` Michael Heerdegen
2015-12-22  5:22         ` John Wiegley
2015-12-19 15:55       ` Michael Heerdegen
2015-12-19 17:08         ` Eli Zaretskii
2015-12-19 17:19           ` Eli Zaretskii
2015-12-19 21:03             ` Michael Heerdegen
2015-12-19 17:40           ` Michael Heerdegen
2015-12-22  5:21             ` John Wiegley
2015-12-19 15:44     ` Michael Heerdegen
2015-12-19 17:02       ` Eli Zaretskii
2015-12-19 20:58         ` Michael Heerdegen
2015-12-22  5:28         ` John Wiegley
2015-12-19 20:31       ` Phillip Lord
2015-12-19 21:16         ` Michael Heerdegen
2015-12-19 22:11           ` Phillip Lord
2015-12-20 12:45             ` Michael Heerdegen
2015-12-24  5:49     ` Richard Stallman
2015-12-24  6:15       ` John Wiegley
2015-12-25  5:49         ` Richard Stallman
2015-12-25 14:59           ` Michael Heerdegen
2015-12-25 16:55             ` John Wiegley
2015-12-26  6:13             ` Richard Stallman
2015-12-26 17:10               ` Michael Heerdegen
2015-12-26 20:52                 ` Aaron Ecay
2015-12-26 23:17                   ` Michael Heerdegen
2016-01-01  7:57                     ` Eli Zaretskii
2016-01-01 17:46                       ` John Wiegley
2016-01-01 18:39                         ` David Kastrup
2016-01-01 19:05                           ` Daniel Colascione
2016-01-02  8:16                             ` Eli Zaretskii
2016-01-02  8:35                               ` David Kastrup
2016-01-03  0:19                                 ` Michael Heerdegen
2016-01-03  2:47                                   ` Drew Adams
2016-01-03  3:21                                     ` Michael Heerdegen
2016-01-03  3:46                                       ` Drew Adams
2016-01-03  5:17                                         ` Michael Heerdegen
2016-01-03  3:45                                   ` Eli Zaretskii
2016-01-03  4:21                                     ` Michael Heerdegen
2016-01-03  9:13                                       ` David Kastrup
2016-01-03 16:52                                         ` Clément Pit--Claudel
2016-01-04  1:28                                         ` Michael Heerdegen
2016-01-03 15:29                                       ` Eli Zaretskii
2016-01-04  2:05                                         ` Michael Heerdegen
2016-01-03  9:03                                   ` David Kastrup
2016-01-04  2:08                                     ` Michael Heerdegen
2016-01-04 22:05                                       ` John Wiegley
2016-01-03  0:41                               ` Dmitry Gutov
2016-01-03  1:07                                 ` Lars Magne Ingebrigtsen
2016-01-03  1:21                                   ` Dmitry Gutov
2016-01-03  2:49                                     ` Drew Adams
2016-01-03 10:49                                       ` David Kastrup
2016-01-03  1:32                                   ` Michael Heerdegen
2016-01-03  2:48                                   ` Drew Adams
2016-01-03  3:11                                     ` Noam Postavsky
2016-01-03  3:18                                       ` Dmitry Gutov
2016-01-03  3:55                                         ` John Wiegley
2016-01-03  3:45                                       ` Drew Adams
2016-01-03  3:47                                 ` Eli Zaretskii
     [not found]                                   ` <56889EC3.3040108@yandex.ru>
     [not found]                                     ` <877fjrkpdf.fsf@fencepost.gnu.org>
     [not found]                                       ` <56892334.4000106@yandex.ru>
     [not found]                                         ` <8760zakb7q.fsf@fencepost.gnu.org>
     [not found]                                           ` <56892BDA.6060103@dancol.org>
     [not found]                                             ` <871t9yk98g.fsf@fencepost.gnu.org>
     [not found]                                               ` <568936F0.3060505@yandex.ru>
     [not found]                                                 ` <87wprqitj5.fsf@fencepost.gnu.org>
     [not found]                                                   ` <56893C8C.3060200@yandex.ru>
2016-01-03 15:52                                                     ` David Kastrup
2016-01-03 15:59                                                       ` Dmitry Gutov
2016-01-03 17:15                                                         ` David Kastrup
2016-01-03 17:52                                                           ` Dmitry Gutov
2016-01-03 18:17                                                             ` David Kastrup
2016-01-04  2:34                                                               ` Michael Heerdegen
2016-01-04  6:19                                                                 ` Drew Adams
2016-01-04 22:07                                                                   ` John Wiegley
2016-01-04 15:52                                                                 ` Eli Zaretskii
2018-10-23 13:04                                                                 ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Michael Heerdegen
2018-10-23 14:43                                                                   ` Clément Pit-Claudel
2018-10-23 14:46                                                                     ` Replace trivial pcase occurrences in the Emacs sources Michael Heerdegen
2018-10-23 14:57                                                                       ` Clément Pit-Claudel
2018-10-23 15:16                                                                         ` Michael Heerdegen
2018-10-23 15:07                                                                       ` Noam Postavsky
2018-10-23 15:24                                                                         ` Michael Heerdegen
2018-10-23 15:31                                                                           ` Noam Postavsky
2018-10-24 13:15                                                                             ` Michael Heerdegen
2018-10-23 15:17                                                                   ` Replace trivial pcase occurrences in the Emacs sources (was: The poor state of documentation of pcase like things.) Eli Zaretskii
2018-10-23 17:14                                                                     ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
2018-10-23 17:24                                                                       ` Michael Heerdegen
2018-10-23 18:12                                                                         ` Stefan Monnier
2018-10-23 19:52                                                                           ` pcase vs. case (where it could also be used) [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
2018-10-23 20:19                                                                             ` Stefan Monnier
2018-10-23 22:24                                                                               ` Garreau, Alexandre
2018-10-24 15:03                                                                           ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
2018-10-24 15:30                                                                             ` Michael Heerdegen
2018-10-24 15:40                                                                               ` Eli Zaretskii
2018-10-24 15:48                                                                                 ` Michael Heerdegen
2018-10-24 17:35                                                                                   ` Eli Zaretskii
2018-10-24 17:55                                                                                     ` Michael Heerdegen
2018-10-24 18:32                                                                                       ` Eli Zaretskii
2018-10-24 18:47                                                                               ` Garreau, Alexandre
2018-10-27 15:19                                                                               ` Michael Heerdegen
2018-10-27 16:56                                                                                 ` Garreau, Alexandre
2018-10-27 22:37                                                                                 ` Dmitry Gutov
2018-10-28  0:21                                                                                   ` Michael Heerdegen
2018-10-28  2:07                                                                                     ` Garreau, Alexandre
2018-10-28  2:44                                                                                       ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
2018-10-28  4:45                                                                                         ` How other pattern-matching lisps do [Was: Re: pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources]] Garreau, Alexandre
2018-10-28 13:44                                                                                           ` Stefan Monnier
2018-10-28 17:57                                                                                             ` Garreau, Alexandre
2018-10-28 23:16                                                                                           ` Michael Heerdegen
2018-10-28 22:54                                                                                         ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Michael Heerdegen
2018-10-28 23:09                                                                                           ` Garreau, Alexandre
2018-10-28 23:57                                                                                             ` Michael Heerdegen
2018-10-29 10:22                                                                                               ` Garreau, Alexandre
2018-10-29 21:33                                                                                                 ` Michael Heerdegen
2018-10-29 23:00                                                                                                   ` pcase ` meaning Garreau, Alexandre
2018-10-29 23:57                                                                                                     ` Michael Heerdegen
2018-10-30  0:17                                                                                                       ` Garreau, Alexandre
2018-10-30  1:40                                                                                                         ` Michael Heerdegen
2018-10-30 16:05                                                                                                         ` Yuri Khan
2018-10-29 17:26                                                                                             ` pcase ` meaning [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Clément Pit-Claudel
2018-10-30  0:27                                                                                               ` pcase ` meaning Garreau, Alexandre
2018-10-30 13:14                                                                                                 ` Stefan Monnier
2018-10-31 23:13                                                                                                   ` Garreau, Alexandre
2018-11-01 13:22                                                                                                     ` Clément Pit-Claudel
2018-11-01 14:11                                                                                                       ` Garreau, Alexandre
2018-10-29  3:26                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
2018-10-29 21:46                                                                                   ` Michael Heerdegen
2018-10-30  0:36                                                                                     ` What `case' have done you? [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
2018-10-30  1:45                                                                                       ` Michael Heerdegen
2018-10-30  6:31                                                                                     ` Replace trivial pcase occurrences in the Emacs sources Eli Zaretskii
2018-10-30 15:47                                                                                       ` Michael Heerdegen
2018-10-30 17:29                                                                                         ` Eli Zaretskii
2018-10-30 22:09                                                                                           ` Michael Heerdegen
2018-10-31 15:59                                                                                             ` Eli Zaretskii
2018-10-31 19:37                                                                                               ` Stefan Monnier
2018-10-31 20:31                                                                                               ` Michael Heerdegen
2018-10-31 23:33                                                                                                 ` Garreau, Alexandre
2018-10-31 23:44                                                                                                 ` Garreau, Alexandre
2018-10-31 23:58                                                                                                   ` Michael Heerdegen
2018-11-01  4:15                                                                                                 ` Eli Zaretskii
2018-11-01 12:30                                                                                                 ` Stefan Monnier
2018-11-01 14:14                                                                                                   ` Michael Heerdegen
2018-11-01 14:18                                                                                                     ` Noam Postavsky
2018-11-01 14:20                                                                                                       ` Michael Heerdegen
2018-11-05  1:43                                                                                                         ` Michael Heerdegen
2018-11-05  1:46                                                                                                           ` Michael Heerdegen
2018-11-05 16:06                                                                                                           ` Eli Zaretskii
2018-11-06  1:04                                                                                                             ` Michael Heerdegen
2018-11-25 20:36                                                                                                               ` Michael Heerdegen
2018-11-25 20:42                                                                                                                 ` Nicolas Goaziou
2018-11-25 21:46                                                                                                                   ` Michael Heerdegen
2018-11-26  3:35                                                                                                                     ` Eli Zaretskii
2018-11-26 20:57                                                                                                                       ` Michael Heerdegen
2018-11-26 22:05                                                                                                                         ` Nicolas Goaziou
2018-11-27  5:35                                                                                                                         ` Eli Zaretskii
2018-10-24 15:47                                                                             ` Clément Pit-Claudel
2018-10-24 16:00                                                                               ` Eli Zaretskii
2018-10-24 19:00                                                                                 ` Clément Pit-Claudel
2018-10-24 19:09                                                                                   ` Eli Zaretskii
2018-10-24 16:12                                                                             ` Alan Mackenzie
2018-10-24 20:52                                                                             ` Stefan Monnier
2018-10-25  7:17                                                                               ` Stephen Berman
2018-10-25 14:47                                                                               ` Eli Zaretskii
2018-10-25 15:32                                                                                 ` Stefan Monnier
2018-10-26 15:34                                                                                   ` Stefan Monnier
2018-10-27 17:48                                                                                 ` Garreau, Alexandre
2018-10-24  4:51                                                                       ` Richard Stallman
2018-10-24  8:34                                                                         ` Joost Kremers
2018-10-24 12:37                                                                           ` Stefan Monnier
2018-10-24 13:08                                                                             ` Daniel Pittman
2018-10-24 14:35                                                                               ` Stefan Monnier
2018-10-24 13:03                                                                           ` pcase pattern syntax (was: Replace trivial pcase occurrences in the Emacs sources) Stefan Monnier
2018-10-26  7:16                                                                             ` Joost Kremers
2018-10-24 10:16                                                                         ` Replace trivial pcase occurrences in the Emacs sources João Távora
2018-10-24 13:05                                                                           ` Stefan Monnier
2018-10-25  3:11                                                                           ` Richard Stallman
2018-10-25 12:42                                                                             ` Stefan Monnier
2018-10-25 23:53                                                                               ` Andy Moreton
2018-10-26 14:59                                                                                 ` Stefan Monnier
2018-10-26 15:44                                                                                   ` Garreau, Alexandre
2018-10-27 12:09                                                                                   ` Andy Moreton
2018-10-28 21:44                                                                                 ` Stefan Monnier
2018-10-29 13:01                                                                                   ` Alan Mackenzie
2018-10-29 13:28                                                                                     ` Stefan Monnier
2018-10-29 13:47                                                                                       ` Alan Mackenzie
2018-10-29 21:08                                                                                         ` Stefan Monnier
2018-10-29 21:53                                                                                           ` Michael Heerdegen
2018-10-29 23:12                                                                                             ` Eric Abrahamsen
2018-10-29 23:18                                                                                               ` Eric Abrahamsen
2018-10-30  0:50                                                                                                 ` `pcase'/`case' implementation [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
2018-10-30 13:07                                                                                                 ` Replace trivial pcase occurrences in the Emacs sources Stefan Monnier
2018-10-30 23:30                                                                                                   ` Eric Abrahamsen
2018-11-01  0:16                                                                                                   ` Garreau, Alexandre
2018-10-30 12:30                                                                                               ` Stefan Monnier
2018-10-30 17:16                                                                                                 ` Stefan Monnier
2018-10-30 19:03                                                                                                   ` Eli Zaretskii
2018-10-30 19:21                                                                                                     ` Stefan Monnier
2018-10-30 19:54                                                                                                       ` Eli Zaretskii
2018-10-30 20:44                                                                                                         ` Stefan Monnier
2018-10-31 15:57                                                                                                           ` Eli Zaretskii
2018-10-31 19:35                                                                                                             ` Stefan Monnier
2018-11-01  1:40                                                                                                         ` Garreau, Alexandre
2018-11-01  4:10                                                                                                           ` Eli Zaretskii
2018-11-01  5:21                                                                                                             ` Garreau, Alexandre
2018-11-01 18:07                                                                                                               ` Eli Zaretskii
2018-11-01 19:35                                                                                                                 ` Garreau, Alexandre
2018-11-01 19:49                                                                                                                   ` TEIRLLM
2018-11-03  2:53                                                                                                                     ` Richard Stallman
2018-11-04 11:35                                                                                                                       ` Nix
2018-11-04 12:40                                                                                                                         ` Garreau, Alexandre
2018-11-01 19:51                                                                                                                   ` TEIRLLM
2018-11-01 20:02                                                                                                                   ` Eli Zaretskii
2018-10-30 20:04                                                                                                       ` Dmitry Gutov
2018-10-30 20:46                                                                                                         ` Stefan Monnier
2018-10-31 13:41                                                                                                           ` Dmitry Gutov
2018-10-31 13:52                                                                                                             ` Stefan Monnier
2018-10-31 15:50                                                                                                               ` Eli Zaretskii
2018-10-31 16:05                                                                                                                 ` Dmitry Gutov
2018-10-31 16:13                                                                                                                   ` Eli Zaretskii
2018-10-31 16:27                                                                                                                     ` Dmitry Gutov
2018-10-31 16:33                                                                                                                       ` Dmitry Gutov
2018-10-31 16:54                                                                                                                         ` Eli Zaretskii
2018-10-31 16:58                                                                                                                           ` Dmitry Gutov
2018-10-31 16:52                                                                                                                       ` Eli Zaretskii
2018-10-31 18:55                                                                                                                       ` Michael Heerdegen
2018-10-31 19:23                                                                                                                         ` Eli Zaretskii
2018-10-31 19:50                                                                                                                           ` Michael Heerdegen
2018-10-31 20:05                                                                                                                             ` Eli Zaretskii
2018-10-31 20:41                                                                                                                               ` Michael Heerdegen
2018-11-01  4:14                                                                                                                                 ` Eli Zaretskii
2018-10-31 20:06                                                                                                                             ` Stefan Monnier
2018-10-31 20:12                                                                                                                               ` Eli Zaretskii
2018-10-31 17:48                                                                                                                     ` Clément Pit-Claudel
2018-10-31 18:11                                                                                                                       ` Eli Zaretskii
2018-10-31 18:28                                                                                                                         ` Clément Pit-Claudel
2018-10-31 18:33                                                                                                                           ` Eli Zaretskii
2018-10-31 19:00                                                                                                                             ` Yuri Khan
2018-10-31 19:20                                                                                                                               ` Eli Zaretskii
2018-11-01  0:11                                                                                                                                 ` Dmitry Gutov
2018-10-31 19:21                                                                                                                             ` Clément Pit-Claudel
2018-10-31 19:29                                                                                                                               ` Eli Zaretskii
2018-10-31 19:31                                                                                                                                 ` Clément Pit-Claudel
2018-10-31 20:36                                                                                                                                   ` Eli Zaretskii
2018-11-01  0:13                                                                                                                                 ` Dmitry Gutov
2018-11-01  1:31                                                                                                                                 ` Garreau, Alexandre
2018-10-31 20:03                                                                                                                             ` Stefan Monnier
2018-11-01  0:07                                                                                                                               ` Dmitry Gutov
2018-11-01  1:34                                                                                                                       ` Garreau, Alexandre
2018-11-03 13:15                                                                                                                     ` Eli Zaretskii
2018-10-30  1:15                                                                                           ` Garreau, Alexandre
2018-10-30  6:17                                                                                           ` Eli Zaretskii
2018-10-30 12:15                                                                                             ` Stefan Monnier
2018-10-30 12:38                                                                                               ` Eli Zaretskii
2018-10-30 15:00                                                                                                 ` Stefan Monnier
2018-10-30 17:00                                                                                                   ` Eli Zaretskii
2018-10-30 17:27                                                                                                     ` Stefan Monnier
2018-10-30 17:36                                                                                                       ` Eli Zaretskii
2018-10-30 18:09                                                                                                         ` Stefan Monnier
2018-10-30 18:42                                                                                                           ` Eli Zaretskii
2018-10-30 18:58                                                                                                             ` Stefan Monnier
2018-10-31 12:08                                                                                                               ` Alan Mackenzie
2018-10-31 12:33                                                                                                                 ` Stefan Monnier
2018-10-31 15:47                                                                                                                   ` Eli Zaretskii
2018-10-31 16:07                                                                                                                     ` Alan Mackenzie
2018-10-31 16:20                                                                                                                       ` Eli Zaretskii
2018-11-01  8:36                                                                                                                         ` Achim Gratz
2018-11-01 10:36                                                                                                                           ` Alan Mackenzie
2018-11-01 12:29                                                                                                                             ` Achim Gratz
2018-11-01 14:19                                                                                                                             ` Michael Heerdegen
2018-11-03 13:16                                                                                                                     ` Eli Zaretskii
2018-11-03 15:45                                                                                                                       ` Michael Heerdegen
2018-11-03 16:25                                                                                                                         ` Eli Zaretskii
2018-11-03 17:12                                                                                                                           ` Michael Heerdegen
2018-11-03 17:55                                                                                                                             ` Eli Zaretskii
2018-11-03 22:22                                                                                                                               ` Michael Heerdegen
2018-11-04 14:16                                                                                                                                 ` Eli Zaretskii
2018-11-06  0:00                                                                                                                                   ` Michael Heerdegen
2018-11-06  3:30                                                                                                                                     ` Eli Zaretskii
2018-11-03 13:13                                                                                                               ` Eli Zaretskii
2018-10-30 18:24                                                                                                         ` Alan Mackenzie
2018-10-30 14:16                                                                                               ` Andy Moreton
2018-10-30 15:05                                                                                                 ` Clément Pit-Claudel
2018-10-30 18:14                                                                                                   ` Alan Mackenzie
2018-10-30 19:56                                                                                                     ` Clément Pit-Claudel
2018-10-31  0:08                                                                                                       ` Andy Moreton
2018-10-31  3:19                                                                                                         ` Stefan Monnier
2018-10-31 16:23                                                                                                         ` Clément Pit-Claudel
2018-11-01 14:44                                                                                                           ` Andy Moreton
2018-11-01 15:28                                                                                                             ` Clément Pit-Claudel
2018-10-30 17:22                                                                                           ` Michael Heerdegen
2018-10-30 17:31                                                                                             ` Stefan Monnier
2018-10-30 23:08                                                                                               ` Michael Heerdegen
2018-10-31  3:09                                                                                                 ` Stefan Monnier
2018-11-05  2:01                                                                                                   ` Michael Heerdegen
2018-11-05  4:49                                                                                                     ` Stefan Monnier
2018-11-05 23:06                                                                                                       ` Michael Heerdegen
2018-10-30 18:09                                                                                           ` Alan Mackenzie
2018-10-30 18:17                                                                                             ` Stefan Monnier
2018-10-30 19:00                                                                                               ` Alan Mackenzie
2018-10-31  0:21                                                                                                 ` Andy Moreton
2018-10-29 14:47                                                                                   ` Andy Moreton
2018-10-29 18:49                                                                                     ` pcase-lambda usage [Was: Re: Replace trivial pcase occurrences in the Emacs sources] Garreau, Alexandre
2018-10-30 23:34                                                                                   ` Replace trivial pcase occurrences in the Emacs sources Van L
2018-10-31  3:14                                                                                     ` Stefan Monnier
2018-10-23 17:22                                                                     ` John Wiegley
2018-10-23 17:16                                                                   ` Stefan Monnier
2016-01-04  2:54                                                       ` The poor state of documentation of pcase like things Michael Heerdegen
2016-01-02  1:15                           ` Richard Copley
2016-01-02  3:50                             ` Drew Adams
2016-01-02  3:51                         ` Drew Adams
     [not found]                     ` <<83y4c9ag06.fsf@gnu.org>
2016-01-01 15:18                       ` Drew Adams
2015-12-27  2:53                 ` Richard Stallman
2015-12-16 21:01 ` Drew Adams
2015-12-17 13:59 ` Phillip Lord
2015-12-17 17:06   ` Alan Mackenzie
2015-12-19 15:26 ` Michael Heerdegen
2015-12-19 16:04   ` Michael Heerdegen
2015-12-19 19:29     ` Phillip Lord
2015-12-19 21:14       ` Michael Heerdegen
2015-12-19 22:06         ` Phillip Lord
2015-12-19 16:47   ` Eli Zaretskii
2015-12-19 17:24     ` Michael Heerdegen
2015-12-22  5:25     ` John Wiegley
2015-12-19 18:30   ` Alan Mackenzie
2015-12-19 20:42     ` Michael Heerdegen
2015-12-19 22:25       ` Alan Mackenzie
2015-12-20 13:11         ` Michael Heerdegen

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).