From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.org!not-for-mail From: Stefan Monnier Newsgroups: gmane.emacs.devel Subject: Re: smie-next-sexp vs associative operators Date: Sun, 14 Oct 2012 21:47:14 -0400 Message-ID: References: <85lif9e7m8.fsf@member.fsf.org> <851uh0x59u.fsf@stephe-leake.org> NNTP-Posting-Host: plane.gmane.org Mime-Version: 1.0 Content-Type: text/plain X-Trace: ger.gmane.org 1350265646 9702 80.91.229.3 (15 Oct 2012 01:47:26 GMT) X-Complaints-To: usenet@ger.gmane.org NNTP-Posting-Date: Mon, 15 Oct 2012 01:47:26 +0000 (UTC) Cc: emacs-devel@gnu.org To: Stephen Leake Original-X-From: emacs-devel-bounces+ged-emacs-devel=m.gmane.org@gnu.org Mon Oct 15 03:47:33 2012 Return-path: Envelope-to: ged-emacs-devel@m.gmane.org Original-Received: from lists.gnu.org ([208.118.235.17]) by plane.gmane.org with esmtp (Exim 4.69) (envelope-from ) id 1TNZmB-0000Ta-9E for ged-emacs-devel@m.gmane.org; Mon, 15 Oct 2012 03:47:27 +0200 Original-Received: from localhost ([::1]:35041 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1TNZm4-00005p-KE for ged-emacs-devel@m.gmane.org; Sun, 14 Oct 2012 21:47:20 -0400 Original-Received: from eggs.gnu.org ([208.118.235.92]:54695) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1TNZm1-00005i-GZ for emacs-devel@gnu.org; Sun, 14 Oct 2012 21:47:18 -0400 Original-Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1TNZm0-0005kb-8C for emacs-devel@gnu.org; Sun, 14 Oct 2012 21:47:17 -0400 Original-Received: from ironport2-out.teksavvy.com ([206.248.154.182]:20743) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1TNZm0-0005kX-3F for emacs-devel@gnu.org; Sun, 14 Oct 2012 21:47:16 -0400 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: Av0EAG6Zu0/O+LCG/2dsb2JhbABEtBGBCIIVAQEEAVYjBQsLNBIUGA0kiBwFugmQRAOjM4FYgwU X-IronPort-AV: E=Sophos;i="4.75,637,1330923600"; d="scan'208";a="201589736" Original-Received: from 206-248-176-134.dsl.teksavvy.com (HELO fmsmemgm.homelinux.net) ([206.248.176.134]) by ironport2-out.teksavvy.com with ESMTP/TLS/ADH-AES256-SHA; 14 Oct 2012 21:47:14 -0400 Original-Received: by fmsmemgm.homelinux.net (Postfix, from userid 20848) id 97F6BAE5BD; Sun, 14 Oct 2012 21:47:14 -0400 (EDT) In-Reply-To: <851uh0x59u.fsf@stephe-leake.org> (Stephen Leake's message of "Sun, 14 Oct 2012 14:44:29 -0400") User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.2.50 (gnu/linux) X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 206.248.154.182 X-BeenThere: emacs-devel@gnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: "Emacs development discussions." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: emacs-devel-bounces+ged-emacs-devel=m.gmane.org@gnu.org Original-Sender: emacs-devel-bounces+ged-emacs-devel=m.gmane.org@gnu.org Xref: news.gmane.org gmane.emacs.devel:154342 Archived-At: >>> I'm indenting "accept LILLY". It should be indented relative to >>> "select". >> That's odd. I'd expect it to be indented relative to "or". > The reason is that's how "if/then/else" works: That's not a good reason: the indentation of an expression that follows a keyword should almost always be relative to that keyword. > if A then > B; > elsif C then > D; > elsif > E then > F; > else > G; > end if; I'm not completely sure how to interpret the above. Is it an example of good indentation, or does it present a problem case? In which way is it related to the select...do case? > Here the internal keywords "then", "elsif" are not transitive; "else" is > transitive. That doesn't sound right. "then" should not be associative, but "elseif" should be. More specifically, with point right after an "elsif", I'd expect C-M-b to stop right after the previous "elsif". > Here we are assuming "E" is a complex multi-line expression, > so we can't use it as an indentation reference; we have to get back to > "if" or "elsif". We call (smie-backward-sexp "then") to do that; it > stops at "if". I'm not sure of which "then" you're talking, but when point is just before F, C-M-b should stop with point in front of E (and returning the previous "elsif"'s data, relative to which it should be indented). If it doesn't, your grammar is wrong. > In the analogous situation with "select or", (smie-backward-sexp "or") > stops at the previous "or". The "or" in select should largely behave like the "elsif" above. > However, what determines whether an operator is "transitive" in this > SMIE sense is more subtle; it depends on what the surrounding > non-terminals are. When the two non-terminals are the same, the operator > is transitive. When they are different, it is not. No, an operator is associative simply if it has the same left and right precedence. What is more subtle is the choice of when to stop, which depends on where we come from. > For Ada, we have: > "if" expression "then" statements "elsif" expression "then" statements > "end" "if" > "declare" declarations "begin" statements "end" > These keywords are all non-transitive, because they have different > non-terminals to the right and left; declarations, expressions, and > statements are all distinct. "else" above is transitive because it has > 'statements' on both sides. No: the precedence depends on the preceding/next terminal. I.e. the left precedence of "then" will be equal to the right precedence of "elsif" because of the above rule. You might like to use rules like: (exp ("if" expthenexp "end") ("if" expthenexp "else" exp "end") ("if" expthenexp "elsif" expthenexp "end") ("if" expthenexp "elsif" expthenexp "end") (expthenexp (exp "then" exp)) So as to make it clear, that when jumping backward from an "elsif" (or "else") you want to skip the "then" and stop at the previous "if" or "elsif". > Which suggests another way to state my core complaint; since > smie-next-sexp will skip an arbitrary number of "transitive pairs", That's annoying. > it should also skip an arbitrary number of "transitive singles". Or at > least, provide an option to do so. No, you got it backwards: you want indentation to walk back as little as possible. E.g. you don't want to walk all the way back to "if" if you can indent relative to the closest "elsif". > These "elseif" are transitive. But again, it is the surrounding > non-terminals that determine this. In a language that distinguishes > between expressions and statements, "elsif" will never be transitive, > but "elsif expression then" will be. What was the reason for separating expressions from instructions in your grammar? Maybe removing this distinction will help (tho it might introduce other problems, of course). Of course the grammar below will still "distinguish" expressions and instructions while giving you an associative "elsif": (exp ("if" exptheninst "end") ("if" exptheninst "else" inst "end") ("if" exptheninst "elsif" exptheninst "end") ("if" exptheninst "elsif" exptheninst "end") (exptheninst (exp "then" inst)) > And with the equivalent sequence in a C-like language that doesn't > have "then", it would stop at the second elsif. I don't see why Ada and > C-like should be different in this. Hence the "expthenexp" non-terminal. > As usual, this conversation has been educational - I learned more about > what "transitive" means in SMIE :). Including the difference between transitive and associative? Stefan