The Ruby Object Model and Metaprogramming

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hi this is Dave Thomas I wanted to show you some samples from the screencasts on the Ruby object model and metaprogramming the first extract comes from episode 2 where we're talking about different ways of sharing behavior in Ruby now you're probably familiar with inheritance and maybe you've used mix-ins but possibly you haven't come across prototype based upon them before in prototype based development we don't have classes explicitly instead we just use objects to share both state and behavior have a look in prototype based programming we do away with that distinction classes and objects are all the same thing some people argue this is actually a pure form of Allah than class-based and there are entire languages based around this paradigm including JavaScript itself let's play around and see what it looks like the key to doing prototype based development in Ruby is the clone method let's go to our editor to see how that works in practice now we've seen this code before in Episode one it defines a singleton method speak on the string that's held in the animal variable and we can call that by saying animal dot speak and out comes me out now if we take this animal object and clone it we can then invoke the speak method on that cloned object as well because clone copies the singleton class of an object that's one of the things that makes it different from dupe if we instead we'd used dupe here we get an error undefined method speak because the singleton isn't copied across so using clone we can copy an object and all of its singleton methods across and we can use that as the basis of our prototype based programming let's start again but this time let's try and define a hierarchy of animals now if we're doing based programming we may well have some kind of parent class animal than subclasses for maybe carnivals or whatever else in prototype based programming we attack it slightly differently first we'll create an object they'll represent the base functionality of all animals and we'll just do that by creating a brand new Ruby object now what we want our animals to have well maybe we'd like to have some attributes for example the number of feet they have or what they had what they eat we can do that simply by defining methods on that particular object by defining an animal we're defining methods that apply to all animals in future so we can say def animal dot number of feet will create the setter method here so we'll pass in a parameter number of feet equals feet and we'll define an accessor method as well and given that obviously we can now set the attribute on those on an animal so you can say animal dot number of feet equals four put this animal dot number of feet and not surprisingly we get four but that's not particularly interesting what's more interesting is if we get rid of this code and let's create a new kind of animal maybe a cat and by creating our cat we can say cat equals animal klum that gives us a brand new object that has all of the attributes and all of the behaviors of an animal so we can also now say can't dot number of feet equals four okay nothing too exciting there but now we can construct a particular cat so maybe we can say felix equals this cat now because we've cloned the object not only have we cloned the methods we've also cloned the state and because of that Felix will automatically have four feet so what we have here is the ability to have inheritance both of behavior and also of state in a way it's more powerful than class-based inheritance the second extract comes from episode 3 where we look at different ways of creating code dynamically this is the first time that we've looked at defined method a really useful tool in the meta programming Arsenal and yes I know I misspelled the class multiplier let's create for ourselves a new class and inside that class self is going to be the class instance multiplier so defined method is available let's define the simplest kind of method we'll say define method it takes us a parameter the name of the method define in this case times 2 and it takes a block and that block becomes the body of the method if we give that block any parameters then our method will take parameters so here we're actually defining a method called times 2 that takes a single parameter and what will it do well we'll just have it return valve times 2 so as our class definition gets executed the defined method a call will create a method called times 2 and we can verify that by saying M equals multiplier new put s m dot times 2 3 and sure enough that comes back with 6 but that's nothing special we could do exactly the same thing with death what makes define method intro thing is we can actually put it inside other methods so for example here I'm going to find our class method self dot create multiplier and now our defined method will only get invoked if I call create multiplier so I'm going to say here create multiplier and our code still runs but now I'll create multiplier method can itself take parameters so for example I could pass the number I want to multiply through as a parameter to create multiplier so now I have to take a parameter here so now we have to rename our method dynamically based on that multiplier so rather than passing in a symbol now I'm going to pass in a string and rather than using a literal - I'm going to substitute in the value of our parameters that could be - 399 whatever it is also now I'm now going to multiply by 2 but instead I'm going to multiply by our parameter now why does that work well it works because define method takes a block and that block is a closure and therefore n is going to be available throughout the lifetime of the existence of that block and so when I multiply by n in here I'm actually going to be multiplied by whatever I passed in to my create multiplier method so now I can just call that and it's still output six but now I can create a new multiplier say by three and then down here I should have a method called times three and sure enough three times three is nine that's pretty cool I can even go further than that I could say something like 10 times create multiplier I and now I'll have created x 0 x 1 x 2 x 3 all the way up to x 9 and now we start to see the real power of the real dynamic nature of this kind of metaprogramming with a single line of code here plus some support code at the top here I can add 10 methods to my class this particular pattern of using defined method occurs all over the place when we measure programming so it's worth studying it will create a class method that in turn calls defined method and typically the parameters of that class method will actually be used either inside the body of the method we define or to help name the method with we define or both I'm really having a blast putting these screencasts together I hope you have as much fun watching them
Info
Channel: PragProg
Views: 10,405
Rating: undefined out of 5
Keywords: Ruby, metaprogramming, Rails, programming, coding, how-to
Id: io34q2G4eOU
Channel Id: undefined
Length: 9min 21sec (561 seconds)
Published: Tue Sep 14 2010
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.