develooper Front page | perl.perl6.language | Postings from June 2006

[svn:perl6-synopsis] r9680 - doc/trunk/design/syn

From:
larry
Date:
June 16, 2006 15:07
Subject:
[svn:perl6-synopsis] r9680 - doc/trunk/design/syn
Message ID:
20060616220646.3EB4FCBA87@x12.develooper.com
Author: larry
Date: Fri Jun 16 15:06:45 2006
New Revision: 9680

Modified:
   doc/trunk/design/syn/S03.pod

Log:
Further decoupling of assignment parsing policy from behavior.


Modified: doc/trunk/design/syn/S03.pod
==============================================================================
--- doc/trunk/design/syn/S03.pod	(original)
+++ doc/trunk/design/syn/S03.pod	Fri Jun 16 15:06:45 2006
@@ -14,7 +14,7 @@
   Date: 8 Mar 2004
   Last Modified: 16 Jun 2006
   Number: 3
-  Version: 40
+  Version: 41
 
 =head1 Changes to existing operators
 
@@ -111,10 +111,10 @@
 
     loop ($a = 1, $b = 2; ; $a++, $b++) {...}
 
-still works fine.  The distinction between scalar and list
-assignment is similar to the way Perl 5 does it, but has to be a
+still works fine.  The syntactic distinction between scalar and list
+assignment is similar to the way Perl 5 defines it, but has to be a
 little different because we can no longer decide on the basis of
-the sigil.  The following forms are defined as "simple lvalues",
+the sigil.  The following forms are parsed as "simple lvalues",
 and imply scalar assignment:
 
     $a		# simple scalar variable
@@ -138,6 +138,10 @@
     !TERM	# any single term coerced to boolean
     (SIMPLE)	# any simple expression in circumfix parens
 
+Note that circumfix parens are considered simple only when used as
+part of a subscript.  Putting parens around the entire lvalue still
+implies list context as in Perl 5.
+
 We also include:
 
     OP SIMPLE	
@@ -154,24 +158,64 @@
 also excluded, but post-assigment forms such as C<SIMPLE += SIMPLE>
 are allowed.
 
-All other forms imply list assignment, and will evaluate both sides
-of the assignment in list context at runtime.  However, this is
-primarily a syntactic distinction, and no semantic or type information
+All other forms imply parsing as a list assignment, which may or may not
+result in a list assignment at run time.  (See below.) However, this is
+exclusively a syntactic distinction, and no semantic or type information
 is used, since it influences subsequent parsing.  In particular, even
 if a function is known to return a scalar value from its declaration,
-you must use C<+> or or C<~> to use it as a scalar within a subscript:
+you must use C<+> or or C<~> if you wish to force scalar parsing from
+within a subscript:
 
     @a[foo()] = bar();		# foo() and bar() called in list context
     @a[+foo()] = bar();		# foo() and bar() called in scalar context
 
-(But note that the first form still works fine if C<foo()> and C<bar()>
+But note that the first form still works fine if C<foo()> and C<bar()>
 are scalar functions that are not context sensitive.  The difference
 in parsing is only an issue if C<bar()> is followed by a comma or
-some such.)
+some such.
 
-Note that circumfix parens are considered simple only when used as
-part of a subscript.  Putting parens around the entire lvalue still
-implies list context as in Perl 5.
+For non-simple lvalues, at run time, both sides are evaluated in list
+context, but if the left side results in a single non-list scalar,
+the right side is treated as a single scalar value, as if the right
+side had been evaluated in list context (which is indeed the case)
+but coerced into scalar context.
+
+If the left side returns a list, however, then regardless of whether the
+list contains a single or multiple values, the right side is bound
+as in a list assignment, and any extra values are discarded.  To force
+list assignment even if the function returns a non-list, either put
+parens around the entire lvalue, or use a comma within the subscript.
+
+Assuming
+
+    sub bar { return <a b c> }
+
+then we have:
+
+    sub foo { return 1,2,3 }
+    @a[foo()] = bar();		# (@a[1,2,3]) = <a b c>
+
+    sub foo { return 1 }
+    @a[foo()] = bar();		# @a[1] = [<a b c>]
+
+    sub foo { return(1) }
+    @a[foo()] = bar();		# @a[1] = [<a b c>]
+
+    sub foo { return (1) }
+    @a[foo()] = bar();		# (@a[1,2,3]) = <a b c>
+
+    sub foo { return 1 }
+    @a[foo(),] = bar();		# (@a[1,2,3]) = <a b c>
+
+    sub foo { return 1 }
+    (@a[foo()]) = bar();	# (@a[1,2,3]) = <a b c>
+
+Those are all parsed as list assignments, but we get different run-time
+behaviors based on the run-time type of the left side.
+
+In general, this will all just do what the user expects most of the time.
+The rest of the time scalar or list behavior can be forced with minimal
+syntax.
 
 =item * List operators are all parsed consistently.  As in Perl 5,
 to the left they look like terms, while to the right they look like



nntp.perl.org: Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at ask@perl.org | Group listing | About