If we make call constructors static and inherited, then maybe the name call constructor becomes a bit odd.
-
The best alternative I could come up with is
static constructor:class Base { static constructor() { return new this(); } }
| // Sketch for exposing [[Call]] and [[Construct]] machinery to JavaScript | |
| // 1. First, let's add the ability to make any object callable with a __call__ | |
| // property (using double underscores for some quick strawman syntax). | |
| // Let __target__ be the object that is being called. | |
| var container = { obj: {} }; | |
| container.obj.__call__ = function() { | |
| console.log('this = ' + this + ', __target__ = ' + __target__); |
If we make call constructors static and inherited, then maybe the name call constructor becomes a bit odd.
The best alternative I could come up with is static constructor:
class Base {
static constructor() { return new this(); }
}
I'd like to argue that call constructors should behave like static methods and be inherited, because it would be surprising if they didn't.
Here's a use case:
We can currently use static methods to instantiate classes, as an alternative
to new:
| #include <iostream> | |
| class A { | |
| public: | |
| static void do_something() { std::cout << "yay\n"; } | |
| }; | |
| class B : public A { | |
| }; |
| class A | |
| def self.do_something | |
| p 'yay' | |
| end | |
| end | |
| class B < A | |
| end | |
| B.do_something |
Re https://github.com/nikomatsakis/typed-objects-explainer/blob/master/valuetypes.md (recent TC39 notes):
I wonder if the immutability requirement can be dropped. To make this work, assignment of value types (color2 = color1) would need to always copy, never be by-reference.
In C++ for example, the complex number class has value semantics (assignment creates a copy, equality compares its constituent values), and yet you can mutate it with c.real(5.0) (sets real part). Similar for vector, which can be mutated with v.push_back(10). This is really no different than int having value semantics but also being mutable (++n). I'm a big fan of C++'s semantics, as they allow you to construct complex objects by repeatedly mutating them and still get value s
JavaScript is currently lacking user-defined types with "value semantics", by which I mean
Map/Set), andSome use cases not yet covered by Niko's ValueType proposal:
Value semantics for mutable types (https://gist.github.com/joliss/7ca89af5947ddf7c9f57)
Value semantics for variable-sized (heap-allocated) objects. Examples:
| var rootNode = require('broccoli-root-node'); | |
| var Watched = rootNode.Watched, Unwatched = rootNode.Unwatched; | |
| // Refers to the ./lib directory on disk, and watches it. | |
| var lib = new Watched('lib'); | |
| // Refers to the ./bower_components/jquery directory, but does not watch it. | |
| var jquery = new Unwatched('bower_components/jquery'); | |
| function CachingWriter(inputTrees, options) { | |
| if (Array.isArray(inputTrees)) { | |
| if (this.enforceSingleInputTree) { // <---- in ES6, `this` is not defined before super | |
| throw new Error('You passed an array of input trees, but only a single tree is allowed.'); | |
| } | |
| inputTrees = inputTrees; | |
| } else { | |
| inputTrees = [inputTrees]; | |
| } | |
| Plugin.call(this, inputTrees); |
| glog() { | |
| # requires git 1.8.3 for %C(auto) syntax | |
| git log --graph --date=short --pretty="%Cblue%ad%Creset %C(auto)%h %Cblue%an%Creset%C(auto) %s __REFS:%d" "$@" \ | |
| | perl -pe 's/__REFS:[^(]*\(([^)]+)\).*/$refs=$1; $refs=~s{, }{ }g; $refs=~s{tag: }{}g; $refs/e' \ | |
| | less; | |
| } | |
| gl() { | |
| glog "$@" | head -n 10; | |
| } |