How do you loop over all the methods of a class in Perl? Are there any good online references to Perl introspection or reflection?
相关问题
- C# how to invoke a field initializer using reflect
- $ENV{$variable} in perl
- Is it possible to pass command-line arguments to @
- Redirecting STDOUT and STDERR to a file, except fo
- Get all classes of a package
相关文章
- Are GetCallingAssembly() and GetExecutingAssembly(
- Running a perl script on windows without extension
- Comparing speed of non-matching regexp
- Can NOT List directory including space using Perl
- Why doesn't reflections.getSubTypesOf(Object.c
- Extracting columns from text file using Perl one-l
- Load a .NET assembly from the application's re
- Get list of classes in namespace in C# [duplicate]
I'll just leave this here for when I forget it. This is extremely powerful; too bad it is so out of the way that most Perl programmers never get to experience it.
In the general case, you'll have to inspect the symbol table (unless you use Moose). For example, to list the methods defined in the
IO::File
package:The hash
%{IO::File::}
is the symbol table of theIO::File package
, and thegrep
filters out non-subroutine entries (e.g. package variables).To extend this to include inherited methods, you have to recursively search the symbol tables of the parent classes (
@IO::File::ISA
).Here is a complete example:
For more info on packages and symbol tables, see the perlmod man page.
The recommendation Todd Gardner gave to use Moose is a good one, but the example code he chose isn't very helpful.
If you're inspecting a non-Moose using class, you'd do something like this:
See the Class::MOP::Class docs for more details on how to do introspection.
You'll also note that I used Class::MOP instead of Moose. Class::MOP (MOP = Meta-Object Protocol) is the base on which Moose builds. If you're working with non-Moose classes, using Moose to introspect doesn't gain you anything.
If you wanted, you could
use Moose ()
andMoose::Meta::Class->initialize
instead of CMOP.Depends if you mean, any class, or if you were implementing your own. For the latter, I use Moose, which offers a very clean syntax for these features. From the cookbook:
You probably want Class::Inspector->methods('Your::Class').
Nuff said.
You can easily get a list of the defined methods of a class using the answers already provided. However, Perl is a dynamic language, which means more methods may be defined later. There really isn't a way to get a list of all of the methods to which any particular class will handle. For a lot more detail on this sort of stuff, I have a few chapters in Mastering Perl.
People are giving you (and upvoting) answers without telling you about the limitations.
Adam mentions his Class::Inspector, but it doesn't really work because it's trying to do something a dynamic language doesn't do (and that's be static :) For instance, here's a snippet where Class::Inspector returns no methods, but I can still call the
VERSION
method (as well asisa
andcan
):Here's another case where I can call any method I like, but Class::Inspector only returns
AUTOLOAD
(and still missingVERSION
,isa
, andcan
):Curiously, everyone seems to ignore UNIVERSAL, probably because they don't explicitly handle it since it's only virtually in @ISA. I can add a
debug
method to every class, and Class::Inspector still misses it even though it's a defined method:Class::MOP has the same limitations.
Not every module is going to use AUTOLOAD, but it's not an obscure or rare feature either. If you don't mind that you are going to miss some of the methods then Class::Inspector or Class::MOP might be okay. It's just not going to give you a list of every method you can call on a class or an object in every case.
If you have a class or an object and you want to know if you can call a particular method, use can(). Wrap it in an eval block so can can call can() on things that aren't even objects to still get back false, instead of death, in those cases: