Skip to content

Commit

Permalink
添加了switch的case编号省略
Browse files Browse the repository at this point in the history
  • Loading branch information
A4-Tacks committed Dec 1, 2023
1 parent 1899d0c commit 269b533
Show file tree
Hide file tree
Showing 5 changed files with 101 additions and 11 deletions.
2 changes: 1 addition & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "mindustry_logic_bang_lang"
version = "0.13.1"
version = "0.13.2"
edition = "2021"

authors = ["A4-Tacks <[email protected]>"]
Expand Down
9 changes: 8 additions & 1 deletion examples/switch.mdtlbl
Original file line number Diff line number Diff line change
@@ -1,10 +1,17 @@
#**
* 一种在常量时间内直接跳转至第不小于零的整数代码段的分支选择方式
*
* case后面接的是id, 表明了第几段代码, 可以写多个
* 如果不写的话, 则为上一段代码的id+1, 没有上一段代码的话则为0
*#

i = 4;
switch i {
case 1 2:
print "1 or 2\n";
print "foo";
break;
case 3:
case: # 省略
print "3\n";
break;
case 5:
Expand Down
26 changes: 18 additions & 8 deletions src/syntax/def.lalrpop
Original file line number Diff line number Diff line change
Expand Up @@ -759,7 +759,7 @@ pub Control: LogicLine = {
)*>
<( // cases
"case"
<LiteralUInt+>
<LiteralUInt*>
":"
<Expand>
)+>
Expand All @@ -769,17 +769,23 @@ pub Control: LogicLine = {
let (append, catchs, cases) = cases;
let catchs_is_empty = catchs.is_empty();

let mut next_case_num = 0;
let case_num_max = cases
.iter()
.map(
|(nums, _)| *nums
.iter()
.max()
.unwrap()
|(nums, _)| {
let num = nums
.iter()
.max()
.copied()
.unwrap_or(next_case_num);
next_case_num = num + 1;
num
}
)
.max()
.unwrap();
let mut cases_res = Vec::with_capacity(case_num_max);
let mut cases_res = Vec::with_capacity(case_num_max + 1);

// 用于填充填充case的行, 如果有追加在末尾的行则将其封装并替换填充
let mut fill_line = append
Expand Down Expand Up @@ -835,18 +841,22 @@ pub Control: LogicLine = {
catch_lines.push(Expand(out_block).into())
}

for (nums, mut expand) in cases {
let mut next_ignored_num = 0;
for (mut nums, mut expand) in cases {
if let Some(append) = &append {
expand.push(append.clone())
}
if nums.is_empty() { nums.push(next_ignored_num) }
for num in nums {
for _ in cases_res.len()..=num {
cases_res.push(fill_line.clone())
}
cases_res[num] = expand.clone().into()
cases_res[num] = expand.clone().into();
next_ignored_num = num + 1;
}
}
debug_assert_eq!(cases_res.len(), case_num_max + 1);
debug_assert_eq!(cases_res.len(), cases_res.capacity());

let (break_lab, continue_lab) = ctrl;
if catchs_is_empty {
Expand Down
73 changes: 73 additions & 0 deletions src/syntax/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3594,3 +3594,76 @@ fn mul_consts_test() {
"#).unwrap(),
);
}

#[test]
fn switch_ignored_id_test() {
let parser = TopLevelParser::new();

assert_eq!(
parse!(parser, r#"
switch x {
case: foo;
case: bar;
case: baz;
}
"#).unwrap(),
parse!(parser, r#"
switch x {
case 0: foo;
case 1: bar;
case 2: baz;
}
"#).unwrap(),
);

assert_eq!(
parse!(parser, r#"
switch x {
case 1: foo;
case: bar;
case: baz;
}
"#).unwrap(),
parse!(parser, r#"
switch x {
case 1: foo;
case 2: bar;
case 3: baz;
}
"#).unwrap(),
);

assert_eq!(
parse!(parser, r#"
switch x {
case: foo;
case 2: bar;
case: baz;
}
"#).unwrap(),
parse!(parser, r#"
switch x {
case 0: foo;
case 2: bar;
case 3: baz;
}
"#).unwrap(),
);

assert_eq!(
parse!(parser, r#"
switch x {
case 0 2 4: foo;
case: bar;
case: baz;
}
"#).unwrap(),
parse!(parser, r#"
switch x {
case 0 2 4: foo;
case 5: bar;
case 6: baz;
}
"#).unwrap(),
);
}

0 comments on commit 269b533

Please sign in to comment.