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

two regular expressions in the same comprehension breaks #101

Open
jurgenvinju opened this issue Jan 14, 2013 · 12 comments
Open

two regular expressions in the same comprehension breaks #101

jurgenvinju opened this issue Jan 14, 2013 · 12 comments
Assignees
Labels

Comments

@jurgenvinju
Copy link
Member

In the code below Rascal complains about a redeclared variable n, but only if the second regular expression is there (/rascal/ := f). A nested comprehension for the same computation works nicely.

rascal>{ <toInt(n), f> | /\s*<n:[0-9]+>\s*<f:\S+>/ <- raw, /rascal/ := f}
|stdin:///|(64,1,<1,64>,<1,65>): Redeclared variable: n

rascal>{<x,y> | <x,y> <- { <toInt(n), f> | /\s*<n:[0-9]+>\s*<f:\S+>/ <- raw}, /rascal/ := y}
rel[int, str]: {
  <1,"/unstable-updates/plugins/rascal_eclipse_0.5.2.201209211516.jar">,
@ghost ghost assigned PaulKlint Jan 14, 2013
@DavyLandman
Copy link
Member

This works now:

rascal>{ <toInt(n), f> | /\s*<n:[0-9]+>\s*<f:\S+>/ := "99srascal", /rascal/ := f}
rel[int,str]: {<99,"srascal">}

@menego
Copy link

menego commented Dec 5, 2019

I've just noticed a similar behaviour with the if statement that generates the same error

if (/<pre:.*>\/\*/ := line && /\S/ := pre && /"(\w|\s)*/ !:= pre)
					commentLinesToIgnore +=1;

image

@jurgenvinju
Copy link
Member Author

This reproduces the bug:

module RegexBug

import IO;

void main() {
  line = "\"bla   /* hello */\"  ";
  ii = 0;
  
  if (/<pre:.*>\/\*/ := line && /\S/ := pre && /"(\w|\s)*/ !:= pre)
                    ii +=1;
                    
  println(ii);                    

}

@jurgenvinju jurgenvinju reopened this Dec 6, 2019
@jurgenvinju
Copy link
Member Author

This does not have the bug, even though it should be functionality equivalent (replaced && by ,):

module RegexBug

import IO;

void main() {
  line = "\"bla   /* hello */\"  ";
  ii = 0;
  
  if (/<pre:.*>\/\*/ := line, /\S/ := pre, /"(\w|\s)*/ !:= pre)
                    ii +=1;
                    
  println(ii);                    

}

@jurgenvinju
Copy link
Member Author

@menego that gives you a workaround for today, and we have an hypothesis for the cause of the bug: an buggy interaction between the backtracking behavior of the && connective and the declaration behavior of regexps.

@menego
Copy link

menego commented Dec 6, 2019

Thank you very much, always super responsive :-)
I already solved that by nesting the if statements but this is waaay cleaner and elegant.

@jurgenvinju
Copy link
Member Author

void d() {
  pre = "\"";
  if (_ <- [1,2] && /"(.)*/ !:= pre)
     println("ok");     
}

simplified.

@jurgenvinju
Copy link
Member Author

another delta gives some insight (replace implicit group by explicit group):

void d() {
  pre = "\"";
  if (_ <- [1,2] && /"<xxx:.>*/ !:= pre)
     println("ok");     
}

gives:

rascal>d()
Reloading module RegexBug
|project://rascal-test-project/src/RegexBug.rsc|(86,3,<7,32>,<7,35>): Redeclared variable: _1
Advice: |http://tutor.rascal-mpl.org/Errors/Static/RedeclaredVariable/RedeclaredVariable.html|
ok
rascal>d()
Reloading module RegexBug
|project://rascal-test-project/src/RegexBug.rsc|(90,3,<7,36>,<7,39>): Redeclared variable: xxx
Advice: |http://tutor.rascal-mpl.org/Errors/Static/RedeclaredVariable/RedeclaredVariable.html|
ok

@jurgenvinju
Copy link
Member Author

jurgenvinju commented Dec 6, 2019

Flip the conditional and change the match:

void d() {
  pre = "\'";
  if (_ <- [1,2] && /"<xxx:.>*/ := pre)
     println("ok");     
}

still produces:

rascal>d()
|project://rascal-test-project/src/RegexBug.rsc|(89,3,<7,35>,<7,38>): Redeclared variable: xxx

means that the difference between !:= and := is irrelevant.

@jurgenvinju
Copy link
Member Author

Ok, this is a complex issue. The difference is still made by replacing && with , and it seems that a variable scope is not properly cleaned up before the second match is tried, and the second instance of xxx is declared again in the same scope.

The trouble with fixing this issue is that the code around && is brittle and highly dependent on the semantics and implementation details of binding patterns such as the ListPattern, the SetPattern and the basic TypedVariablePattern.

So this requires some further study.

@jurgenvinju jurgenvinju assigned jurgenvinju and unassigned PaulKlint Dec 6, 2019
@jurgenvinju jurgenvinju added this to the stable release march 2020 milestone Feb 9, 2020
@DavyLandman
Copy link
Member

DavyLandman commented Dec 4, 2023

rascal>  if (_ <- [1,2] && /"<xxx2:.>*/ !:= "\"") println("ok");
|prompt:///|(37,3,<1,37>,<1,40>): Redeclared variable: xxx2
Advice: |https://www.rascal-mpl.org/docs/Rascal/Errors/CompileTimeErrors/RedeclaredVariable|

this is still an issue.

@jurgenvinju
Copy link
Member Author

See #1900 for progress; that fix is not correct yet.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

4 participants