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

[PoC] Intoroduce parameterizing rules with conditional statement #418

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

ydah
Copy link
Collaborator

@ydah ydah commented May 9, 2024

I would like to propose a new grammar in this PR.
I believe that more parameterizing rules can handle more abstract rules if we can switch between rules and actions that are expanded by conditions in order to make rules common.

DesignDoc: https://gist.github.com/ydah/62008655a6f6c3118ab01134dc91da6f

Syntax is as follows:

%rule defined_rule(X, condition): /* empty */
                                | X { $$ = $1; } %if(condition) /* 1 */
                                | %if(condition) X %endif X { $$ = $1; } /* 2 */
                                ;

%%

r_true        : defined_rule(number, %true)
              ;

r_false       : defined_rule(number, %false)
              ;
  1. It's like a postfix if in Ruby. If condition is false, it is equivalent to missing this line.
  2. If statementIf condition is false, it is equivalent to missing RHS between %if and% endif.
❯ exe/lrama --trace=rules spec/fixtures/parameterizing_rules/user_defined/if.y
Grammar rules:
$accept -> r_true YYEOF
defined_rule_number_true -> ε
defined_rule_number_true -> number
defined_rule_number_true -> number number
r_true -> defined_rule_number_true
defined_rule_number_false -> ε
defined_rule_number_false -> number
r_false -> defined_rule_number_false

Motivation

I believe it will solve the problem mentioned in the article below with the tight coupling with Lexer "to disable certain generation rules under certain conditions" and I would like to propose this feature to solve this problem.
https://yui-knk.hatenablog.com/entry/2023/04/04/190413

We can trace the RHS to f_args > args_tail > args_forward, where f_args is the RHS of both the lambda argument (f_larglist) and the method definition argument (f_arglist).
So if we can switch between RHS and actions by passing parameters, we can break up the Lexer/Parser coupling here.

@ydah ydah marked this pull request as draft May 9, 2024 12:20
@ydah ydah force-pushed the parameterizing-rules-meets-conditonal branch from 2cb042d to c15c765 Compare May 9, 2024 13:46
@ydah ydah changed the title [WIP] [PoC] Intoroduce parameterizing rules with conditonal [PoC] Intoroduce parameterizing rules with conditonal May 9, 2024
@ydah ydah marked this pull request as ready for review May 9, 2024 13:46
@ydah ydah force-pushed the parameterizing-rules-meets-conditonal branch from c15c765 to 9a48181 Compare May 13, 2024 02:37
I would like to propose a new grammar in this PR.
I believe that more parameterizing rules can handle more abstract rules if we can switch between rules and actions that are expanded by conditions in order to make rules common.

Syntax is as follows:
```
%rule defined_rule(X, condition): /* empty */
                                | X { $$ = $1; } %if(condition) /* 1 */
                                | %if(condition) X %endif X { $$ = $1; } /* 2 */
                                ;

%%

r_true        : defined_rule(number, %true)
              ;

r_false       : defined_rule(number, %false)
              ;
```

1. It's like a postfix if in Ruby. If condition is false, it is equivalent to missing this line.
2. If statementIf condition is false, it is equivalent to missing RHS between `%if` and`% endif`.

I believe it will solve the problem mentioned in the article below with the tight coupling with Lexer "to disable certain generation rules under certain conditions" and I would like to propose this feature to solve this problem.
https://yui-knk.hatenablog.com/entry/2023/04/04/190413

We can trace the RHS to [f_args](https://github.com/ruby/ruby/blob/2f916812a9b818b432ee7c299e021ec62d4727fb/parse.y#L5523-L5575) > [args_tail](https://github.com/ruby/ruby/blob/2f916812a9b818b432ee7c299e021ec62d4727fb/parse.y#L5487-L5503) > [args_forward](https://github.com/ruby/ruby/blob/2f916812a9b818b432ee7c299e021ec62d4727fb/parse.y#L5586-L5597), where f_args is the RHS of both the lambda argument (f_larglist) and the method definition argument (f_arglist).
So if we can switch between RHS and actions by passing parameters, we can break up the Lexer/Parser coupling here.
@ydah ydah force-pushed the parameterizing-rules-meets-conditonal branch from 9a48181 to 6ba14f2 Compare May 13, 2024 02:51
@ydah ydah changed the title [PoC] Intoroduce parameterizing rules with conditonal [PoC] Intoroduce parameterizing rules with conditional statement May 13, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

1 participant