all messages for Emacs-related lists mirrored at yhetil.org
 help / color / mirror / code / Atom feed
From: Stefan Monnier <monnier@iro.umontreal.ca>
To: Eli Zaretskii <eliz@gnu.org>
Cc: emacs-devel@gnu.org
Subject: Re: Update of pcase docs for the elisp manual
Date: Mon, 25 Jan 2016 20:40:12 -0500	[thread overview]
Message-ID: <jwvk2mxws02.fsf-monnier+Inbox@gnu.org> (raw)
In-Reply-To: <83egd53acg.fsf@gnu.org> (Eli Zaretskii's message of "Mon, 25 Jan 2016 18:14:23 +0200")

> What I wrote in the manual uses the reverse notation: QPatterns
> _include_ the backquote.

Then these are UPatterns (the subset of them that is prefixed with `).
And then you can use the notion of "QPattern" to describe what can
appear *inside* a backquoted pattern.

E.g. you say "QPatterns can have one of the following forms:" and then
list some examples but this list is not exhaustive since it doesn't
include cases such as:

    `(foo ,bar baz)
or
    `(foo (bar ,baz) (,titi toto))

Additionally, you say

    `(@var{qpattern1} . @var{qpattern2})

is a valid qpattern, which could lead people to try and use things like

    `(`(a . b) . `(c . d))

which are not invalid but probably don't do what was intended
(this will test
    (equal x '(`(a . b) . `(c . d)))
 rather than
    (equal x '((a . b) . (c . d)))
)

Also it says that @var{atom} and ,@var{upattern} are "qpatterns", which
would literally mean that you can write

   (pcase foo
     (,toto blabla))

which is not valid.

I've appended a suggested patch to try and correct those inaccuracies.
I'm afraid the result is too "dry" (too hard to understand), tho.

>> Agreed.  Not needed for the docstring (which is more meant as
>> a reference for people who already know how it works, and needs to be
>> both exhaustive and concise), but useful for the manual.
> My quotation was not from the doc string, but from Michael's tutorial.

Ah, that explains why you used "UPattern" (I used this in the Emacs-24
version of pcase where the ` pattern was hardcoded, but in the Emacs-25
code I've switched to using just Pattern instead).

>> > Unless, that is, there are important scenarios where using (quote FOO)
>> > in a pattern is required where it isn't a trivial replacement
>> > for 'FOO.
>> A macro (such as pcase) can never distinguish 'A from (quote A) since
>> the reader returns exactly the same result either way.
> Sorry, is that a no?

It's not just a "no", it's a "no, because it's impossible".
I thought that would be obvious to a seasoned Lisper like you, but
clearly it isn't so we need to say it more explicitly.


        Stefan


diff --git a/doc/lispref/control.texi b/doc/lispref/control.texi
index 6fa802d..cf65d3e 100644
--- a/doc/lispref/control.texi
+++ b/doc/lispref/control.texi
@@ -319,16 +319,11 @@ Pattern matching case statement
 and returns the value of the last of @var{body-forms}.  Any remaining
 @var{clauses} are ignored.
 
-The @var{pattern} part of a clause can be of one of two types:
-@dfn{QPattern}, a pattern quoted with a backquote; or a
-@dfn{UPattern}, which is not quoted.  UPatterns are simpler, so we
-describe them first.
-
 Note: In the description of the patterns below, we use ``the value
 being matched'' to refer to the value of the @var{expression} that is
 the first argument of @code{pcase}.
 
-A UPattern can have one of the following forms:
+A UPattern can have the following forms:
 
 @table @code
 
@@ -407,24 +402,29 @@ Pattern matching case statement
   (code           (message "Unknown return code %S" code)))
 @end example
 
-The QPatterns are more powerful.  They allow matching the value of the
-@var{expression} that is the first argument of @code{pcase} against
-specifications of its @emph{structure}.  For example, you can specify
-that the value must be a list of 2 elements whose first element is a
-string and the second element is a number.  QPatterns can have one of
-the following forms:
+@node Pcase with backquotes
+@subsubsection Pcase with backquotes
+
+Additionally to the above patterns, one can also use a backquoted
+pattern.  This facility is designed with the idea that a backquoted
+pattern should match all values that could be constructed
+by a similarly backquoted expression.  For example, you can specify
+that the value must be a list of 2 elements whose first element is the
+string @code{"first"} with a pattern like @code{`("first" ,elem)}.
+
+Backquoted patterns are written @code{`@var{qpattern}} where
+@var{qpattern} can have the following forms:
 
 @table @code
-@item `(@var{qpattern1} . @var{qpattern2})
+@item (@var{qpattern1} . @var{qpattern2})
 Matches if the value being matched is a cons cell whose @code{car}
 matches @var{qpattern1} and whose @code{cdr} matches @var{qpattern2}.
-@item `[@var{qpattern1} @var{qpattern2} @dots{} @var{qpatternm}]
+This generalizes to (@var{qpattern1} @var{qpattern2} @dots{}
+@var{qpatternn}), of course.
+@item [@var{qpattern1} @var{qpattern2} @dots{} @var{qpatternm}]
 Matches if the value being matched is a vector of length @var{m} whose
 @code{0}..@code{(@var{m}-1)}th elements match @var{qpattern1},
 @var{qpattern2} @dots{} @var{qpatternm}, respectively.
-@item `(,@var{upattern1} ,@var{upattern2} @dots{})
-Matches if the value being matched is a list whose elements match the
-corresponding @var{upattern1}, @var{upattern2}, etc.
 @item @var{atom}
 Matches if corresponding element of the value being matched is
 @code{equal} to the specified @var{atom}.
@@ -435,6 +435,9 @@ Pattern matching case statement
 
 @end defmac
 
+@node Pcase example
+@subsubsection Pcase example
+
 Here is an example of using @code{pcase} to implement a simple
 interpreter for a little expression language (note that this example
 requires lexical binding, @pxref{Lexical Binding}):
@@ -472,12 +475,20 @@ Pattern matching case statement
 (evaluate '(sub 1 2) nil)                 ;=> error
 @end example
 
+@node Pcase macros
+@subsubsection Pcase macros
+
 Additional UPatterns can be defined using the @code{pcase-defmacro}
 macro.
 
 @defmac pcase-defmacro name args &rest body
-Define a new UPattern for @code{pcase}.  The UPattern will have the
-form @code{(@var{name} @var{args})}.
+Define a new kind of UPattern for @code{pcase} by describing how to
+rewrite it into some other UPattern.
+
+More specifically, this definition states that any UPattern of the
+form @code{(@var{name} @var{actual-args})} will be rewritten into the
+UPattern obtained by evaluating @var{body} in an environment where
+@var{args} are bound to @var{actual-args}.
 @end defmac
 
 @node Combining Conditions



  reply	other threads:[~2016-01-26  1:40 UTC|newest]

Thread overview: 28+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <m2fuxq6pb0.fsf@newartisans.com>
     [not found] ` <87d1stznc6.fsf@web.de>
     [not found]   ` <m2si1p8r31.fsf@newartisans.com>
     [not found]     ` <m2powt5w50.fsf@newartisans.com>
2016-01-23 11:17       ` Update of pcase docs for the elisp manual Eli Zaretskii
2016-01-24  4:40         ` Stefan Monnier
2016-01-24 14:33           ` Eli Zaretskii
2016-01-24 23:17             ` Stefan Monnier
2016-01-25 16:14               ` Eli Zaretskii
2016-01-26  1:40                 ` Stefan Monnier [this message]
2016-01-26 15:38                   ` Eli Zaretskii
2016-01-26 16:23                     ` Stefan Monnier
2016-01-25 14:22             ` Michael Heerdegen
2016-01-25 14:15         ` Michael Heerdegen
2016-01-25 16:33           ` Eli Zaretskii
2016-01-28 18:37             ` Michael Heerdegen
2016-01-29  3:06               ` Stefan Monnier
2016-01-29  9:45               ` Eli Zaretskii
2016-01-29 14:51                 ` Michael Heerdegen
2016-01-26 16:59         ` John Wiegley
2016-01-26 18:10           ` Stefan Monnier
2016-01-26 18:41           ` Eli Zaretskii
2016-01-26 19:35             ` John Wiegley
2016-01-26 20:28               ` Eli Zaretskii
2016-01-29  1:28                 ` John Wiegley
2016-01-29  8:30                   ` Eli Zaretskii
2016-01-29 13:39                     ` Andy Moreton
2016-01-29 14:21                       ` Eli Zaretskii
2016-01-29 15:14                         ` Andy Moreton
2016-01-29 15:37                           ` Eli Zaretskii
2016-01-26 19:58             ` Andy Moreton
2016-01-26 20:19               ` Eli Zaretskii

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=jwvk2mxws02.fsf-monnier+Inbox@gnu.org \
    --to=monnier@iro.umontreal.ca \
    --cc=eliz@gnu.org \
    --cc=emacs-devel@gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this external index

	https://git.savannah.gnu.org/cgit/emacs.git
	https://git.savannah.gnu.org/cgit/emacs/org-mode.git

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.