adding conditional while loops with while ... when
This commit is contained in:
parent
4d146bacb1
commit
4eeb8c4bd2
|
@ -414,13 +414,20 @@
|
||||||
return new ParentheticalNode($2);
|
return new ParentheticalNode($2);
|
||||||
})
|
})
|
||||||
],
|
],
|
||||||
|
// The condition for a while loop.
|
||||||
|
WhileSource: [o("WHILE Expression", function() {
|
||||||
|
return new WhileNode($2);
|
||||||
|
}), o("WHILE Expression WHEN Expression", function() {
|
||||||
|
return new WhileNode($2, {
|
||||||
|
filter: $4
|
||||||
|
});
|
||||||
|
})
|
||||||
|
],
|
||||||
// The while loop. (there is no do..while).
|
// The while loop. (there is no do..while).
|
||||||
While: [o("WHILE Expression Block", function() {
|
While: [o("WhileSource Block", function() {
|
||||||
return new WhileNode($2, $3);
|
return $1.add_body($2);
|
||||||
}), o("WHILE Expression", function() {
|
}), o("Expression WhileSource", function() {
|
||||||
return new WhileNode($2, null);
|
return $2.add_body($1);
|
||||||
}), o("Expression WHILE Expression", function() {
|
|
||||||
return new WhileNode($3, Expressions.wrap([$1]));
|
|
||||||
})
|
})
|
||||||
],
|
],
|
||||||
// Array comprehensions, including guard and current index.
|
// Array comprehensions, including guard and current index.
|
||||||
|
|
16
lib/nodes.js
16
lib/nodes.js
|
@ -891,8 +891,13 @@
|
||||||
// it, all other loops can be manufactured.
|
// it, all other loops can be manufactured.
|
||||||
WhileNode = (exports.WhileNode = inherit(Node, {
|
WhileNode = (exports.WhileNode = inherit(Node, {
|
||||||
type: 'While',
|
type: 'While',
|
||||||
constructor: function constructor(condition, body) {
|
constructor: function constructor(condition, opts) {
|
||||||
this.children = [(this.condition = condition), (this.body = body)];
|
this.children = [(this.condition = condition)];
|
||||||
|
this.filter = opts && opts.filter;
|
||||||
|
return this;
|
||||||
|
},
|
||||||
|
add_body: function add_body(body) {
|
||||||
|
this.children.push((this.body = body));
|
||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
top_sensitive: function top_sensitive() {
|
top_sensitive: function top_sensitive() {
|
||||||
|
@ -909,13 +914,18 @@
|
||||||
if (!top) {
|
if (!top) {
|
||||||
rvar = o.scope.free_variable();
|
rvar = o.scope.free_variable();
|
||||||
set = this.idt() + rvar + ' = [];\n';
|
set = this.idt() + rvar + ' = [];\n';
|
||||||
this.body = PushNode.wrap(rvar, this.body);
|
if (this.body) {
|
||||||
|
this.body = PushNode.wrap(rvar, this.body);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
post = returns ? '\n' + this.idt() + 'return ' + rvar + ';' : '';
|
post = returns ? '\n' + this.idt() + 'return ' + rvar + ';' : '';
|
||||||
pre = set + this.idt() + 'while (' + cond + ')';
|
pre = set + this.idt() + 'while (' + cond + ')';
|
||||||
if (!this.body) {
|
if (!this.body) {
|
||||||
return pre + ' null;' + post;
|
return pre + ' null;' + post;
|
||||||
}
|
}
|
||||||
|
if (this.filter) {
|
||||||
|
this.body = Expressions.wrap([new IfNode(this.filter, this.body)]);
|
||||||
|
}
|
||||||
return pre + ' {\n' + this.body.compile(o) + '\n' + this.idt() + '}' + post;
|
return pre + ' {\n' + this.body.compile(o) + '\n' + this.idt() + '}' + post;
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
|
|
File diff suppressed because one or more lines are too long
|
@ -360,11 +360,16 @@ grammar: {
|
||||||
o "( Expression )", -> new ParentheticalNode($2)
|
o "( Expression )", -> new ParentheticalNode($2)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
# The condition for a while loop.
|
||||||
|
WhileSource: [
|
||||||
|
o "WHILE Expression", -> new WhileNode($2)
|
||||||
|
o "WHILE Expression WHEN Expression", -> new WhileNode($2, {filter : $4})
|
||||||
|
]
|
||||||
|
|
||||||
# The while loop. (there is no do..while).
|
# The while loop. (there is no do..while).
|
||||||
While: [
|
While: [
|
||||||
o "WHILE Expression Block", -> new WhileNode($2, $3)
|
o "WhileSource Block", -> $1.add_body $2
|
||||||
o "WHILE Expression", -> new WhileNode($2, null)
|
o "Expression WhileSource", -> $2.add_body $1
|
||||||
o "Expression WHILE Expression", -> new WhileNode($3, Expressions.wrap([$1]))
|
|
||||||
]
|
]
|
||||||
|
|
||||||
# Array comprehensions, including guard and current index.
|
# Array comprehensions, including guard and current index.
|
||||||
|
@ -384,10 +389,8 @@ grammar: {
|
||||||
ForSource: [
|
ForSource: [
|
||||||
o "IN Expression", -> {source: $2}
|
o "IN Expression", -> {source: $2}
|
||||||
o "OF Expression", -> {source: $2, object: true}
|
o "OF Expression", -> {source: $2, object: true}
|
||||||
o "ForSource WHEN Expression", ->
|
o "ForSource WHEN Expression", -> $1.filter: $3; $1
|
||||||
$1.filter: $3; $1
|
o "ForSource BY Expression", -> $1.step: $3; $1
|
||||||
o "ForSource BY Expression", ->
|
|
||||||
$1.step: $3; $1
|
|
||||||
]
|
]
|
||||||
|
|
||||||
# Switch/When blocks.
|
# Switch/When blocks.
|
||||||
|
@ -406,8 +409,7 @@ grammar: {
|
||||||
When: [
|
When: [
|
||||||
o "LEADING_WHEN SimpleArgs Block", -> new IfNode($2, $3, null, {statement: true})
|
o "LEADING_WHEN SimpleArgs Block", -> new IfNode($2, $3, null, {statement: true})
|
||||||
o "LEADING_WHEN SimpleArgs Block TERMINATOR", -> new IfNode($2, $3, null, {statement: true})
|
o "LEADING_WHEN SimpleArgs Block TERMINATOR", -> new IfNode($2, $3, null, {statement: true})
|
||||||
o "Comment TERMINATOR When", ->
|
o "Comment TERMINATOR When", -> $3.comment: $1; $3
|
||||||
$3.comment: $1; $3
|
|
||||||
]
|
]
|
||||||
|
|
||||||
# The most basic form of "if".
|
# The most basic form of "if".
|
||||||
|
|
|
@ -701,8 +701,13 @@ SplatNode: exports.SplatNode: inherit Node, {
|
||||||
WhileNode: exports.WhileNode: inherit Node, {
|
WhileNode: exports.WhileNode: inherit Node, {
|
||||||
type: 'While'
|
type: 'While'
|
||||||
|
|
||||||
constructor: (condition, body) ->
|
constructor: (condition, opts) ->
|
||||||
@children:[@condition: condition, @body: body]
|
@children:[@condition: condition]
|
||||||
|
@filter: opts and opts.filter
|
||||||
|
this
|
||||||
|
|
||||||
|
add_body: (body) ->
|
||||||
|
@children.push @body: body
|
||||||
this
|
this
|
||||||
|
|
||||||
top_sensitive: ->
|
top_sensitive: ->
|
||||||
|
@ -718,10 +723,11 @@ WhileNode: exports.WhileNode: inherit Node, {
|
||||||
if not top
|
if not top
|
||||||
rvar: o.scope.free_variable()
|
rvar: o.scope.free_variable()
|
||||||
set: @idt() + rvar + ' = [];\n'
|
set: @idt() + rvar + ' = [];\n'
|
||||||
@body: PushNode.wrap(rvar, @body)
|
@body: PushNode.wrap(rvar, @body) if @body
|
||||||
post: if returns then '\n' + @idt() + 'return ' + rvar + ';' else ''
|
post: if returns then '\n' + @idt() + 'return ' + rvar + ';' else ''
|
||||||
pre: set + @idt() + 'while (' + cond + ')'
|
pre: set + @idt() + 'while (' + cond + ')'
|
||||||
return pre + ' null;' + post if not @body
|
return pre + ' null;' + post if not @body
|
||||||
|
@body: Expressions.wrap([new IfNode(@filter, @body)]) if @filter
|
||||||
pre + ' {\n' + @body.compile(o) + '\n' + @idt() + '}' + post
|
pre + ' {\n' + @body.compile(o) + '\n' + @idt() + '}' + post
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,12 +26,6 @@ reg: /\\/
|
||||||
ok reg(str) and str is '\\'
|
ok reg(str) and str is '\\'
|
||||||
|
|
||||||
|
|
||||||
i: 10
|
|
||||||
while i -= 1
|
|
||||||
|
|
||||||
ok i is 0
|
|
||||||
|
|
||||||
|
|
||||||
money$: 'dollars'
|
money$: 'dollars'
|
||||||
|
|
||||||
ok money$ is 'dollars'
|
ok money$ is 'dollars'
|
||||||
|
|
|
@ -1,9 +1,3 @@
|
||||||
i: 100
|
|
||||||
while i -= 1
|
|
||||||
|
|
||||||
ok i is 0
|
|
||||||
|
|
||||||
|
|
||||||
i: 5
|
i: 5
|
||||||
list: while i -= 1
|
list: while i -= 1
|
||||||
i * 2
|
i * 2
|
||||||
|
@ -25,4 +19,12 @@ results: while func 1
|
||||||
assert()
|
assert()
|
||||||
i
|
i
|
||||||
|
|
||||||
ok results.join(' ') is '4 3 2 1'
|
ok results.join(' ') is '4 3 2 1'
|
||||||
|
|
||||||
|
|
||||||
|
i: 10
|
||||||
|
results: while i -= 1 when i % 2 is 0
|
||||||
|
i * 2
|
||||||
|
|
||||||
|
ok results.join(' ') is '16 12 8 4'
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue