Let's say it again. Ruby is a genuine object-oriented language.
Everything you manipulate is an object, and the results of those
manipulations are themselves objects. However, many languages make the
same claim, and they often have a different interpretation of what
object-oriented means and a different terminology for the concepts
they employ.
So, before we get too far into the details, let's briefly look at the
terms and notation that
we'll be using.
When you write object-oriented code, you're normally looking to model
concepts from the real world in your code. Typically during this modeling
process you'll discover categories of things that need to be
represented in code. In a jukebox, the concept of a ``song'' might be
such a category. In Ruby, you'd define a
class to represent
each of these entities. A class is a combination of state (for
example, the name of the song) and methods that use that state (perhaps
a method to play the song).
Once you have these classes, you'll typically want to create a number
of
instances of each. For the jukebox system containing a class
called
Song
, you'd have separate instances for popular hits such
as ``Ruby Tuesday,'' ``Enveloped in Python,'' ``String of Pearls,''
``Small talk,'' and so on. The word
object is used
interchangeably with class instance (and being lazy typists, we'll
probably be using the word ``object'' more frequently).
In Ruby, these objects are created by calling a constructor, a special
method associated with a class. The standard constructor is called
new
.
song1 = Song.new("Ruby Tuesday")
song2 = Song.new("Enveloped in Python")
# and so on
|
These instances are both derived from the same class, but they have
unique characteristics. First, every object has a unique
object
identifier (abbreviated as
object id). Second, you can
define
instance variables,
variables with values that are
unique to each instance. These instance variables hold an object's
state. Each of our songs, for example, will probably have an instance
variable that holds the song title.
Within each class, you can define
instance methods.
Each method
is a chunk of functionality which may be called from within the class
and (depending on accessibility constraints) from outside. These
instance methods in turn have access to the object's instance
variables, and hence to the object's state.
Methods are invoked by sending a message to an object.
The message
contains the method's name, along with any parameters the method may
need.
[This idea of expressing method calls in the form of
messages comes from Smalltalk.] When an object receives a message,
it looks into its own class for a corresponding method. If found, that
method is executed. If the method
isn't found, ... well,
we'll get to that later.
This business of methods and messages may sound complicated, but in
practice it is very natural. Let's look at some method calls.
(Remember that the arrows in the code examples show the values
returned by the corresponding expressions.)
"gin joint".length
|
� |
9
|
"Rick".index("c")
|
� |
2
|
-1942.abs
|
� |
1942
|
sam.play(aSong)
|
� |
"duh dum, da dum de dum ..."
|
Here, the thing before the period is called the
receiver, and
the name after the period is the method to be invoked.
The first
example asks a string for its length, and the second asks a different
string to find the index of the letter ``c.'' The third line has a
number calculate its absolute value. Finally, we ask Sam to play us
a song.
It's worth noting here a major difference between Ruby and most other
languages. In (say) Java, you'd find the absolute value of some number
by calling a separate function and passing in that number. You might
write
number = Math.abs(number) // Java code
|
In Ruby, the ability to determine an absolute value is built into
numbers---they take care of the details internally. You simply send
the message
abs
to a number object and let it do the work.
The same applies to all Ruby objects: in C you'd write
strlen(name)
, while in Ruby it's
name.length
, and so
on. This is part of what we mean when we say that Ruby is a genuine OO
language.