Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add "square bracket list literal" to grammar #1981

Closed
Tracked by #1492
edwardalee opened this issue Aug 31, 2023 · 3 comments · Fixed by #2003
Closed
Tracked by #1492

Add "square bracket list literal" to grammar #1981

edwardalee opened this issue Aug 31, 2023 · 3 comments · Fixed by #2003
Labels
enhancement Enhancement of existing feature language Related to the syntax and semantics of LF python Related to the Python target
Milestone

Comments

@edwardalee
Copy link
Collaborator

I'm not sure to whom to assign this. Please help.

I'm trying to update Expressions.md for Python, and I have found several problems. Consider the following program:

target Python

reactor Foo(param(1, 2, 3)) {
  state x(1, 2, 3)

  reaction(startup) {=
    print("parameter param = ", self.param);
    print("type is ", type(self.param));
    print("state x = ", self.x);
    print("type is ", type(self.x));
  =}
}

main reactor {
  f = new Foo(param(3, 4, 5))
}

According to the documentation, param is supposed to be a tuple and x is supposed to be a list. But they are both lists. The output is:

parameter param =  [3, 4, 5]
type is  <class 'list'>
state x =  [1, 2, 3]
type is  <class 'list'>

The formatter also messes up with the above code. It gives these warnings:

3 | reactor Foo(param(1, 2, 3)) {
  |                  ^ This syntax is deprecated in the Python target, use an equal sign instead of parentheses for assignment.
  |
4 |   state x(1, 2, 3)

lfc: warning: This syntax is deprecated in the Python target, use an equal sign instead of parentheses for assignment.
--> code/c/src/Junk.lf:4:10
  |
3 | reactor Foo(param(1, 2, 3)) {]
4 |   state x(1, 2, 3)
  |          ^ This syntax is deprecated in the Python target, use an equal sign instead of parentheses for assignment.
  |
5 | 

lfc: warning: This syntax is deprecated in the Python target, use an equal sign instead of parentheses for assignment.
 --> code/c/src/Junk.lf:15:20
   |
14 | main reactor {
15 |   f = new Foo(param(3, 4, 5))
   |                    ^ This syntax is deprecated in the Python target, use an equal sign instead of parentheses for assignment.
   |
16 | }

I try to fix the syntax, and the formatter changes it right back! (in VS code, it does this when I save the file).

If I fix the syntax in another editor to get this:

target Python

reactor Foo(param = (1, 2, 3)) {
  state x = (1, 2, 3)

  reaction(startup) {=
    print("parameter param = ", self.param);
    print("type is ", type(self.param));
    print("state x = ", self.x);
    print("type is ", type(self.x));
  =}
}

main reactor {
  f = new Foo(param = (3, 4, 5))
}

then the compilation fails:

> Task :cli:lff:run FAILED
lff: error: no viable alternative at input '('
--> code/c/src/Junk.lf:3:21
  |
2 | 
3 | reactor Foo(param = (1, 2, 3)) {
  |                     ^ no viable alternative at input '('
  |
4 |   state x = (1, 2, 3)

lff: error: mismatched input '2' expecting RULE_ID
--> code/c/src/Junk.lf:3:25
  |
2 | 
3 | reactor Foo(param = (1, 2, 3)) {
  |                         ^ mismatched input '2' expecting RULE_ID
  |
4 |   state x = (1, 2, 3)

lff: error: mismatched input '3' expecting RULE_ID
--> code/c/src/Junk.lf:3:28
  |
2 | 
3 | reactor Foo(param = (1, 2, 3)) {
  |                            ^ mismatched input '3' expecting RULE_ID
  |
4 |   state x = (1, 2, 3)

lff: error: extraneous input ')' expecting '{'
--> code/c/src/Junk.lf:3:30
  |
2 | 
3 | reactor Foo(param = (1, 2, 3)) {
  |                              ^ extraneous input ')' expecting '{'
  |
4 |   state x = (1, 2, 3)

lff: error: no viable alternative at input '('
--> code/c/src/Junk.lf:4:13
  |
3 | reactor Foo(param = (1, 2, 3)) {
4 |   state x = (1, 2, 3)
  |             ^ no viable alternative at input '('
  |
5 | 

lff: error: no viable alternative at input '1'
--> code/c/src/Junk.lf:4:14
  |
3 | reactor Foo(param = (1, 2, 3)) {
4 |   state x = (1, 2, 3)
  |              ^ no viable alternative at input '1'
  |
5 | 

lff: error: no viable alternative at input '2'
--> code/c/src/Junk.lf:4:17
  |
3 | reactor Foo(param = (1, 2, 3)) {
4 |   state x = (1, 2, 3)
  |                 ^ no viable alternative at input '2'
  |
5 | 

lff: error: no viable alternative at input '3'
--> code/c/src/Junk.lf:4:20
  |
3 | reactor Foo(param = (1, 2, 3)) {
4 |   state x = (1, 2, 3)
  |                    ^ no viable alternative at input '3'
  |
5 | 

lff: error: 'reaction' is a reserved keyword which cannot be used as an identifier.
--> code/c/src/Junk.lf:6:3
  |
5 | 
6 |   reaction(startup) {=
  |   ^^^^^^^^ 'reaction' is a reserved keyword which cannot be used as an identifier.
  |
7 |     print("parameter param = ", self.param);

lff: fatal error: Aborting due to 9 previous errors.

FAILURE: Build failed with an exception.
@edwardalee edwardalee added bug Something isn't working python Related to the Python target formatter labels Aug 31, 2023
@lhstrh
Copy link
Member

lhstrh commented Aug 31, 2023

I think this has to do with #1580. Maybe @oowekyala can comment on this? It seems like a problem with the grammar not allowing tuple initialization syntax (which looks a lot like our deprecated list syntax sans equal sign).

@edwardalee
Copy link
Collaborator Author

I tried also initializing with curly braces:

reactor Foo(param = {1, 2, 3}) { ... }

but this gives:

2 | 
3 | reactor Foo(param = {1, 2, 3}) {
  |                     ^^^^^^^^^ Braced expression lists are not a valid expression for the Python target.

So currently, it is not possible to have array-valued parameters or state variables in Python except by using the deprecated syntax and tolerating warnings.

So I'm not sure how to update the docs for the 0.5 release.

@oowekyala
Copy link
Collaborator

Hi, so one of #1580's goals was to stop interpreting eg name(1,2) differently depending on whether it's a parameter or a state variable, so yes the doc is outdated there. We don't create tuple instances anymore, only lists.

The PR did not try to implement new syntax apart from the braced array initializer. From the PR description:

the braced list syntax is not available in Python or TS, so if you were declaring a python list/tuple with a(1,2), you can convert it to a = {= [1, 2] =} to remove the warning, or just wait until we allow writing a = [1, 2] directly.

The long term ideal solution would be to add a "square bracket list literal" to the grammar, that would be avaiable in Python and TS (and therefore allow writing a = [1, 2]).

I think we should recommend using funny braces to fix this situation.

@lhstrh lhstrh changed the title Array parameters and state not working in Python Add "square bracket list literal" to grammar Sep 1, 2023
@lhstrh lhstrh added this to the 0.6.0 milestone Sep 1, 2023
@cmnrd cmnrd added enhancement Enhancement of existing feature language Related to the syntax and semantics of LF and removed bug Something isn't working formatter labels Sep 11, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement Enhancement of existing feature language Related to the syntax and semantics of LF python Related to the Python target
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants