Hi,

I know this is my first post on this list and that I'm relatively new to =
the Ruby community, and that this can be a somewhat controversial topic =
(as I've found by asking about it on the #ruby-lang channel).=20

First off, I want to explain who I am. I've been an Objective-C =
developer for the past 6 years on the Mac and iOS and have used various =
languages such as PHP, Python, Java etc. In the past year I've been =
trying to get into Ruby. After several false starts where I've simply =
not had time I've managed to make some pretty good progress. I love =
Ruby's functionality and how dynamic it is, as it is very close to how =
I've worked the past 6 years with my Objective-C development. As with =
any language there are some things that I want to see in other languages =
(symbols, mixins, almost any character in method names etc) and some =
things I would like to see brought from other languages.

I give this suggestion, not because I don't want to do things the "ruby" =
way, but because I genuinely believe that it can help make ruby better, =
by aiding in the development of tools that in turn aid developers in =
writing code faster and with fewer mistakes.


If any of you have used Objective-C, you will have likely encountered =
two things. In terms of objects it is duck typed, yet it also offers =
static typing. Now there are many differing opinions on static typing. =
Some believe everything should be statically typed and to do otherwise =
is to allow for errors in your code. Some believe everything should be =
duck typed and that with careful coding and testing you can have lots of =
flexibility with few, if any errors. To a very large degree I am in the =
latter camp. However, I also see the benefits of static typing and how =
it can help developers explicitly state assumptions and as such help =
developers test those assumptions.

For those who haven't used Objective-C, I'll give a quick overview of =
how it handles typing. Due to its C heritage it is largely statically, =
but weakly typed. If you use any C types then you obviously need to type =
them as int, float etc. Objective-C adds a few other types to this, but =
the key one is the id type. The id type essentially means "anything that =
is an object". The reason this exists is because you can have non-object =
types, so there needs to be differentiation. In a sense, in Ruby =
everything is of the data type "object", and so there is no need to =
explicitly state this.

But Objective-C also has optional static typing for objects. This is =
used by the compiler and other tools to perform checks and warn you if =
something may be wrong. It is thrown away afterwards and doesn't exist =
in the runtime. Much like Ruby, the only way to find out the type of an =
object at runtime is to ask it for its class. If you don't want to use =
this you can just write everything as id and treat id almost as a =
keyword for declaring a variable, sort of like var in javascript.

So why should Ruby get this? Well the best way to answer that is to =
describe some of things that languages with some degree of static typing =
have. The first off is pre-runtime checking of code. Have you misspelt a =
method or a variable? Did you call a method on an object but forget to =
implement it? These things can be warned of before you run your code, =
and they can also be run over your entire code. Related to this is =
general static analysis, where while not only checking for syntax =
errors, it can also check for common bugs and inform you about code =
paths that are never run, either because they aren't needed and you =
haven't yet removed them or because you're not doing something =
correctly.

Then you have editing tools such as refactoring and autocomplete. =
Refactoring can be much more reliable if it knows what types it is =
dealing with. If you wanted to rename a method for example, there may be =
similarly named methods on multiple classes which are called throughout =
your code, but you only want to rename the calls on instances of your =
object. And autocomplete becomes more than filtering a list of method =
names that have the same prefix as what you have currently typed, if it =
knows the class of the object you're calling the method on then it can =
severely narrow that down, and often provide you the correct result =
first time, meaning less typing.


There were some questions that were asked on #ruby-lang and I thought I =
would answer them here as you may also have the same questions:

1. What if I don't want typing?
The idea would be that this is completely optional, like much of Ruby's =
syntax. In Ruby if you don't want () around your method arguments you =
don't need them, if you do you can add them in. In this case, if you =
want to write these types you can do, if not then you don't. You can =
also use typing up until the point where it gets in the way, at which =
point you ignore it. Much like with Objective-C, except the general =
object type is implied by default in Ruby.

2. Why not just use Diamondback Ruby or Mirah or some other similar =
system?
These are interesting projects, but they have downsides. For one, I want =
to use Ruby and all of the APIs that come with it. Rather than an =
entirely new language and runtime, I'm talking about adding one thing to =
the language grammar. I also don't want to add any sort of runtime =
checking. Code would run exactly the same, as type information would be =
discarded when the code is compiled, but it would allow for useful =
information for other tools at development time. Lastly, I'd like to see =
it as a full language construct rather than comments.

3. Why not use comments?
It could be done via comments, but then a standard comment format has to =
be required and it is putting language data into what should be =
documentation. By doing this as a language feature it sets a standard =
way of writing them and keeps code separate from comments.

4. What is the point given that there is no full compilation before =
hand?
If all you do is write code and run it, none. While this is often how =
people write small scripts, it isn't how people write applications. They =
also have test suites that they run against it their application and =
text editors and IDEs that they use to code this. The benefit is that =
the type information can be used to create tools that run some tests for =
you and help you write code. To give an example from elsewhere in life, =
when things are constructed in remote places, such as dams or wind =
turbines, roads need to be built up to them. They aren't actually part =
of the construction, but they're needed to help the tools such as =
diggers, cranes and workers get there quickly and safely.

5. What help is it if you can choose not to use it when static typing =
gets in the way?
Yes, in cases where you don't use the typing then there is limited help =
from auto complete or refactoring or static analysis. Autocomplete would =
default to offering a basic filtered list, static analysis could take a =
guess but may be wrong and refactoring may have to resort to asking you =
to confirm. However, you find that the times that static analysis really =
gets in the way are relatively few. Just because 5% of the time =
something doesn't work doesn't mean that it may not be well worth it for =
the 95% of the time it can.

6. How would you implement it in the language?
This is the trickiest part: what does the syntax look like. As someone =
pointed out in #ruby-lang, C style typing is out as 'String foo =3D =
"bar"' is another way of writing 'String(foo =3D "bar")'. I have come up =
with an idea for the syntax, which from what I can tell wouldn't clash =
with any existing syntax. I demonstrate it below by creating a variable =
and defining a method (note that you would only have to type a variable =
once):

<Integer> my_integer =3D "42".to_i

def <Integer> to_i(<Integer> base =3D 10)
end

Now the above would be absolutely no different at runtime to the Ruby =
today of:

my_integer =3D "42".to_i

def to_i(base =3D 10)
end

If you wanted you could mix and match:

my_integer =3D "42".to_i

def <Integer> to_i(<Integer> base =3D 10)
end

And to give an example of where static typing gets in the way, take =
returning the first object of an array. The array can hold any objects =
so you can't know the type but the first method generally takes an =
integer argument, so could be defined as:

def first(<Integer> n)
end

So any tool can check the input is in fact an integer, but there is no =
return type given so it assumes it can be any type. Now in cases like =
this it can be combined with a variable with a type, so while the tools =
can't say what you're assigning is the correct type of object, they can =
work on the assumption that it is the type of object you said and so it =
can make sure that you aren't doing anything 'wrong' with that object =
later on. For example:

<Array> my_array =3D ["foo", "bar", "baz"] 	#Can check the =
assignment of myArray
<String> my_string =3D my_array.first			#Can check that =
myArray responds to first but not that it returns a string
my_string.map {|item| item.do_something}	#As we are assuming =
aString is in fact a string, we can tell it may not respond to map =
(given the nature of message sending we can't be 100% sure, but in the =
vast majority of occasions it will be the case) and warn the user

Of course, this is just my suggestion for the syntax, there are others =
out there who have different ideas for a type syntax for ruby and there =
may be others on this list.


A final question some of you may be thinking, but which wasn't asked on =
#ruby-lang:

7. Do you have a vested interest?
Yes. I want to invest time in learning Ruby so that I can write software =
with it. I've not got masses of experience with it yet, but I know =
already it is as fun to use as my current staple language, Objective-C. =
There's also that I want to invest time in becoming part of a community =
that to some degree has wildly differing opinions on software =
development to what I'm used to, so hopefully some of those opinions =
will rub off on me and I can apply what I think makes sense to coding =
elsewhere. Finally, if I'm going to invest time in a platform then I =
want to be able to invest in great tools, whether that means buying =
and/or learning existing ones, or writing new ones myself. It is this =
last point which is why I'm writing this email as I believe what I've =
proposed could help me or others create these great tools.


Hopefully I've at least given you something to think about. If you do =
have any questions I'd be happy to answer them. And thanks for spending =
your time reading this.

Martin Pilkington=