I'm not quite sure the uses for the different variables in CoffeeScript
class Cow
@utters = 1
constructor: (@name) ->
mutate:->
alert @utters
heads: 1
feet = 9
c = new Cow
From my investigation, it seems heads
is public and feet
is private. My confusion comes in when figuring out name
and utters
. For name
it more or less compiles to this.name = name
and for utters
it compiles to Cow.utters = 1
.
So my questions are. What is the scope of utters
and how should it be accessed? What is the scope of name
and how should it be accessed?
Let us look at these one by one.
For the first one:
class Cow
@utters = 1
this
is the class itself when you hit @utters = 1
so this @utters
is sort of a class variable. The JavaScript version is this:
var Cow = (function() {
function Cow() {}
Cow.utters = 1;
return Cow;
})();
Subclasses will be able to see this but they'll have their own copy of it; so, for this:
class CowCow extends Cow
m: ->
CowCow.utters = 11
CowCow.utters
starts out as 1 but will be 11 after (new CowCow).m()
and Cow.utters
will stay at 1 all the way through.
The second one:
class Cow
heads: 1
is essentially a default instance variable; the JavaScript version looks like this:
var Cow = (function() {
function Cow() {}
Cow.prototype.heads = 1;
return Cow;
})();
The Cow.prototype.heads = 1;
part means that heads
is inherited and attached to instances rather than classes.
The result is that this:
class Cow
heads: 1
class CowCow extends Cow
m: ->
alert @heads
@heads = 11
(new CowCow).m()
alert (new Cow).heads
alerts 1 twice.
The third one:
class Cow
feet = 9
m: -> alert feet
is another sort of class variable but this one is very private: feet
is not inherited, not visible to subclasses, and not visible to the outside world. The JavaScript version is this:
var Cow = (function() {
var feet = 9;
function Cow() {}
Cow.prototype.m = function() { return alert(feet) };
return Cow;
})();
so you can see that:
feet
will be visible to all Cow
methods.
- All
Cow
instances will share the same feet
.
feet
is not public in that you can't get at it without calling a Cow
method (class or instance, either will do).
feet
is not visible to subclasses since it isn't a property of the class and it isn't in the prototype
(and thus it isn't inherited by instances of subclasses).
Summary: @utters
is sort of a traditional class variable, heads
is a public instance variable with a default value, and feet
is sort of a private class variable.