in reply to Re: Perl 6, Object Orientation and Melting Brains
in thread Perl 6, Object Orientation and Melting Brains

I wrote:

I've been trying to get my head around OO for 15 years and made no progress ... how do I learn OO without melting my brain?

And revdiablo responded:

I am not sure whether you are talking about creating object oriented code, or using object oriented APIs. What you mean can have a lot of implications on the answer.

A good question. I think that the answer is that I wish to be able to a) understand and b) create OO code. I have indeed used OO API's, but my experience with them has been like a scene from "A Fish Called Wanda":

Otto: Apes don't read philosophy!
Wanda: Yes, they do, they just don't understand it!

Where I think I get lost is that I can learn syntax, but I don't see the point, the reason the syntax is designed to reflect a structure that is, thusfar, beyond my grasp.

  • Comment on Re^2: Perl 6, Object Orientation and Melting Brains

Replies are listed 'Best First'.
Re^3: Perl 6, Object Orientation and Melting Brains
by dragonchild (Archbishop) on Mar 28, 2005 at 14:07 UTC
    The differences between procedural programming and OO (or functional or logical) programming are all about who is responsible for what. In procedural programming, The Programmer is responsible for everything. It is He who determines when everything happens, what data structures are used, what algorithms, etc. If there is a bit-shifting or memory allocation, He has made it so.

    The other styles are about sharing this rather awesome responsibility. It's a lot easier to see in logical programming - makefiles, for example. When you program a makefile, you're saying "X transforms to Y in this fashion" a whole bunch of times. You then say "I need to get this to Z" and the program figures the rest out. It figures out where you are, where you want to go, and how to get there. All the programmer has done is to provide the rules for getting from X to Y. It's kinda like have a butler in charge of your servants.

    In OO, it's kinda the same thing, except that you don't have a butler - you are the butler. Each of the objects is a servant. "Hey you! Please get this done." Now, you really couldn't care less how the maid cleans the living room, just so long as the living room is clean when you get back. You don't care if one person did it or if that maid hired a cleaning service to come in and do it. All you care about is that you have a person who is responsible for cleaning the room. If the room isn't clean, you know who to get mad at. :-)

    Functional is a little weird - you have a butler that will create the servants it needs on-demand, based on a set of templates. It doesn't really work with this analogy. *grins*

    Being right, does not endow the right to be rude; politeness costs nothing.
    Being unknowing, is not the same as being stupid.
    Expressing a contrary opinion, whether to the individual or the group, is more often a sign of deeper thought than of cantankerous belligerence.
    Do not mistake your goals as the only goals; your opinion as the only opinion; your confidence as correctness. Saying you know better is not the same as explaining you know better.

Re^3: Perl 6, Object Orientation and Melting Brains
by BrentDax (Hermit) on Mar 28, 2005 at 23:56 UTC

    Imagine for a moment that you're writing the billing component of an online store. Now, there are several ways a customer can pay: they can use a credit card, a debit card, a check, etc. You could use a switch statement (or an if/elsif chain in Perl 5) to do it:

    given ($payment_method) { # All code samples are Perl 6 when 'credit' { do_credit_card($num, $exp) } when 'debit' { do_debit_card($num, $exp) } when 'check' { do_check() } default { die } }

    But maybe there are several steps involved--early in the process you have to authorize, then later you have to execute the transaction, and perhaps you need to store the info in a database so crackers can steal it. That requires three switch statements in different areas of the code. And then six months down the road, you want to add PayPal support, so you have to change three different switch statements, but in one of them you accidentally put 'payapl', but it's already gone into production so the company loses five thousand dollars and fires you.

    You don't want to get fired.

    So instead, you write an object to represent a payment method, and a subclass for each specific way of paying:

    class MyStore::PayMethod { # A submethod is a method that isn't inherited. submethod new { die "Create a subclass, silly." } method authorize($price) { ... } method execute($price) { ... } method store($dbh) { ... } } class MyStore::PayMethod::CreditCard is MyStore::PayMethod { # Colon means private--only code in this class can see # it. has ($:ccnum, $:ccexp, $:ccname); submethod BUILD($:ccname, $:ccnum, $:ccexp) {} method authorize($price) { (code to authorize) } method execute($price) { (code to execute) } method store($dbh) { (code to store) } }

    Now you can create the appropriate object exactly once:

    my $class; given($payment_method) { when 'credit' { $class=MyStore::PayMethod::CreditCard } when 'debit' { $class=MyStore::PayMethod::DebitCard } when 'check' { $class=MyStore::PayMethod::Check } } my $payobj=$*%params);

    And then later on, when it's time to authorize, all you need to do is put the statement $payobj.authorize()--no nasty switch required.

    In essence, an object is a way to make tasks with different data look the same to the outside world, even if the exact algorithm used to do that task to that data is radically different. It's a little like passing around a table of functions, only cleverer.

    Edit: a friendly elder reminded me that has requires parens when declaring multiple attributes, just like my and our in Perl 5.

    --Brent Dax
    There is no sig.

      Wow, thanks BrentDax, that's a very thorough answer. I'm going to have to look at your code (and look up what some of the syntax means) a bit more, but the reason behind the division of the code this way makes sense, which is a good sign. The only other thing I notice is that if I'm going to adopt Perl 6's OO syntax I'm going to spend a lot of time on the Shift key :-)
        Just so you know, BrentDax is explaining polymorphism. That is one aspect of OO programming that many people (and it seems BrentDax is one of those many) think is a killer feature. Personally, while I think polymorphism is very powerful and useful, it is the bundling of data and code (known as encapsulation) that I find more compelling. If you re-read my earlier response in that light, you will notice that's what I'm talking about. Hopefully between these two posts you will begin to understand the fundamentals of OO. :-)
Re^3: Perl 6, Object Orientation and Melting Brains
by Mugatu (Monk) on Mar 28, 2005 at 18:57 UTC

    The main difference between object oriented programming and procedural programming can be boiled down to where the data is stored. If the data is stored by the main program, and passed in to the functions, that's usually procedural code. If the data is stored by the functions themselves, and the main code just asks the functions to do things, that is usually object oriented.

    As dragonchild said, this moves the responsibility of that data away from the person writing the main code, and onto the the person writing the object itself. Even if that person is the same person, the two different areas of code can be written in different frames of mind. I think it helps create clean separation of concerns. Also, it's often just darn convenient. Passing the same data structures around constantly can be a real pain. Objects are a solution to that problem.