Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why do '::' and '->' work (sort of) interchangeably when calling methods from Perl modules?

Tags:

oop

module

perl

I keep getting :: confused with -> when calling subroutines from modules. I know that :: is more related to paths and where the module/subroutine is and -> is used for objects, but I don't really understand why I can seemingly interchange both and it not come up with immediate errors. I have perl modules which are part of a larger package, e.g. FullProgram::Part1

I'm just about getting to grips with modules, but still am on wobbly grounds when it comes to Perl objects, but I've been accidentally doing this:

FullProgram::Part1::subroutine1();

instead of

FullProgram::Part1->subroutine1();

so when I've been passing a hash ref to subroutine1 and been careful about using $class/$self to deal with the object reference and accidentally use :: I end up pulling my hair out wondering why my hash ref seems to disappear. I have learnt my lesson, but would really like an explanation of the difference. I have read the perldocs and various websites on these but I haven't seen any comparisons between the two (quite hard to google...) All help appreciated - always good to understand what I'm doing!

like image 563
dgBP Avatar asked Nov 20 '12 17:11

dgBP


1 Answers

There's no inherent difference between a vanilla sub and one's that's a method. It's all in how you call it.


Class::foo('a');

This will call Class::foo. If Class::foo doesn't exist, the inheritance tree will not be checked. Class::foo will be passed only the provided arguments ('a').

It's roughly the same as: my $sub = \&Class::foo; $sub->('a');


Class->foo('a');

This will call Class::foo, or foo in one of its base classes if Class::foo doesn't exist. The invocant (what's on the left of the ->) will be passed as an argument.

It's roughly the same as: my $sub = Class->can('foo'); $sub->('Class', 'a');

like image 131
ikegami Avatar answered Sep 30 '22 04:09

ikegami