refactor: replace Foo.new constructor syntax with new Foo and simplify superclass constructor calls
Remove the `this new` constructor declaration syntax in favor of a `new` keyword that creates instances directly. Superclass constructors are now invoked via bare `super(args)` instead of `super.new(args)`, eliminating the semantic weirdness of calling a constructor on a partially-constructed instance. Update the compiler to treat `new` as a keyword token, replace the `isMethod` flag with `methodName`/`methodLength` fields, and change the VM's `NEW` opcode to pop the class from the stack before creating the instance. Add a default `new` native method on Object that returns `this`. Update all benchmarks and tests to use the new syntax.
This commit is contained in:
@@ -3,7 +3,7 @@ class Foo {
|
||||
}
|
||||
|
||||
// A class with no constructors gets an argument-less "new" one by default.
|
||||
var foo = Foo.new
|
||||
var foo = new Foo
|
||||
io.write(foo is Foo) // expect: true
|
||||
io.write(foo.toString) // expect: Foo
|
||||
|
||||
|
||||
@@ -1,20 +0,0 @@
|
||||
class Foo {
|
||||
this bar { io.write("this bar") }
|
||||
this baz { io.write("this baz") }
|
||||
this bar(arg) { io.write("this bar " + arg) }
|
||||
|
||||
toString { return "Foo" }
|
||||
}
|
||||
|
||||
// Different names.
|
||||
Foo.bar // expect: this bar
|
||||
Foo.baz // expect: this baz
|
||||
|
||||
// Can overload by arity.
|
||||
Foo.bar // expect: this bar
|
||||
Foo.bar("one") // expect: this bar one
|
||||
|
||||
// Returns the new instance.
|
||||
var foo = Foo.bar // expect: this bar
|
||||
io.write(foo is Foo) // expect: true
|
||||
io.write(foo.toString) // expect: Foo
|
||||
@@ -1,18 +1,17 @@
|
||||
class Foo {
|
||||
// TODO: Do we want to require an explicit "new" here?
|
||||
this new { io.write("zero") }
|
||||
this new(a) { io.write(a) }
|
||||
this new(a, b) { io.write(a + b) }
|
||||
new { io.write("zero") }
|
||||
new(a) { io.write(a) }
|
||||
new(a, b) { io.write(a + b) }
|
||||
|
||||
toString { return "Foo" }
|
||||
}
|
||||
|
||||
// Can overload by arity.
|
||||
Foo.new // expect: zero
|
||||
Foo.new("one") // expect: one
|
||||
Foo.new("one", "two") // expect: onetwo
|
||||
new Foo // expect: zero
|
||||
new Foo("one") // expect: one
|
||||
new Foo("one", "two") // expect: onetwo
|
||||
|
||||
// Returns the new instance.
|
||||
var foo = Foo.new // expect: zero
|
||||
var foo = new Foo // expect: zero
|
||||
io.write(foo is Foo) // expect: true
|
||||
io.write(foo.toString) // expect: Foo
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
class A {
|
||||
this new(arg) {
|
||||
io.write("A.new " + arg)
|
||||
new(arg) {
|
||||
io.write("new A " + arg)
|
||||
_field = arg
|
||||
}
|
||||
|
||||
@@ -8,8 +8,9 @@ class A {
|
||||
}
|
||||
|
||||
class B is A {
|
||||
this otherName(arg1, arg2) super.new(arg2) {
|
||||
io.write("B.otherName " + arg1)
|
||||
new(arg1, arg2) {
|
||||
super(arg2)
|
||||
io.write("new B " + arg1)
|
||||
_field = arg1
|
||||
}
|
||||
|
||||
@@ -17,18 +18,19 @@ class B is A {
|
||||
}
|
||||
|
||||
class C is B {
|
||||
this create super.otherName("one", "two") {
|
||||
io.write("C.create")
|
||||
new {
|
||||
super("one", "two")
|
||||
io.write("new C")
|
||||
_field = "c"
|
||||
}
|
||||
|
||||
cField { return _field }
|
||||
}
|
||||
|
||||
var c = C.create
|
||||
// expect: A.new two
|
||||
// expect: B.otherName one
|
||||
// expect: C.create
|
||||
var c = new C
|
||||
// expect: new A two
|
||||
// expect: new B one
|
||||
// expect: new C
|
||||
io.write(c is A) // expect: true
|
||||
io.write(c is B) // expect: true
|
||||
io.write(c is C) // expect: true
|
||||
|
||||
Reference in New Issue
Block a user