Simplistic Subroutines - Page 162
March 19, 2001
Generally speaking, a well designed program in Perl, assuming
it's longer than a handful of lines, isn't simply one large
linear beast. Programs include subroutines, sometimes many, that
your main code calls to handle themed or repeated tasks. Along
these lines, one generally wants to avoid global variables, and
subroutines tend to work on variables within their own little
mental space. Thus, we typically pass values into subroutines
— the values they need to know — and subroutines can
return values back to the calling expressions. You scratch their
back, they scratch yours.
Put bluntly, passing values into Perl subroutines is a pain,
because it's such an unsophisticated mechanism. When you call a
subroutine, you can provide a list of parameters. Generally these
should be scalar values, although that includes references to
non-scalar values such as lists and hashes. For instance:
returnVal=&mySub ($value,\@list,\%hash);
The routine mySub will simply receive these values
in an ordered list, named @_. So, to use them in
your subroutine you probably need to get them out of the list
into some meaningful variables:
sub mySub {
my ($value,$list,$hash)=@_;
...etc...
}
So, the first problem with this approach is that it requires the
programmer to dig the subroutine parameters out of one big list.
Second, what if you wanted to pass an arbitrary or unordered list
of parameters to a subroutine? Perhaps you sometimes want to
supply a particular parameter on some subroutine calls, but not
others. Ideally, you should be able to pass key value pairs to a
subroutine, so that you can pass arbitrary value lists and assign
their variable names at the same time. Sure, one could pass a
reference to a hash with these key value pairs, and then decode
the hash inside the subroutine. Again, this is asking the
programmer to do what the language should intrinsically
understand: in essence, to code around the language.
From a legibility standpoint, we once again encounter an
obstacle, as you can't glean immediately from each subroutine
definition what sorts of parameters the routine accepts. Rather,
you need to read the code of the subroutine itself to see how it
handles the incoming parameter list. Messy, and impossible to
automate documenting the input structures for large numbers of
subroutines.
Modules and Project Deployment
The Comprehensive Perl Archive
Network, or CPAN, is a testament to the power of using
modules with Perl. As a successful open-source project,
developers from around the world have contributed Perl modules
that save you from having to re-invent the wheel. Modules that
let you "plug-in" capabilities into your scripts can range from
simple to complex, and make programming large projects much
easier. Need a module to retrieve Web pages from the Internet?
Get LWP::Simple. Need a module to make it easy to
calculate dates? Pick up Date::Parse.
Unfortunately, though, the module system has limitations that can
significantly effect just the types of projects you're likely use
lots of modules for. Say you develop a nifty Perl application
that uses five modules. Two of these are included in the base
Perl distribution, but you had to compile and install the three
others. This even assumes that you could compile and
install them — a task made less easy when you don't have
administration privileges to the Perl installation on the server
you're working on. It can be done, but the methods are not
obvious, and rarely mentioned in the installation instructions
provided with each module.
Now, you've sold a potential client on the wonders of your Perl-
based application. Potential client wants to buy a copy of the
application from you. How are you going to deploy the application
to their system? For one, they'll need Perl, of course. To be
safe, it's probably best that their version of Perl is not older
than the one you developed on. And they need those three extra
modules ... the client isn't technically literate, and you
haven't the means to distribute the modules into their Perl
installation. So, the client has to find someone, possibly you,
to spend time on their machine prepping the Perl installation and
modules, so that your application can work.
So, working with all of these wonderful user-contributed modules
is a double edged sword. Use them and make your programming job
easier, leading to increased productivity and possibly a better
application. But then figure out how to deploy your application
to far flung clients who now need these modules, too.
Perl sorely lacks a sophisticated deployment system, which
seriously hampers one's desire to use Perl for distributable,
medium to large scale applications. There is, and has long been,
discussion of a Perl "compiler", which could crunch source code
into platform-specific machine or C, for example. This would be a
boon to deployment, but present day discussions of such a
compiler in Perl books and Web sites speaks of it with little
sense of urgency, and emphasize the experimental and unstable
nature of these projects. At the least, a Perl "bundler" would be
an interim solution, wherein the client site may still need a
Perl interpreter, but you could bundle all of the source,
including modules, into one neat distribution. Of course, this is
complicated by the fact that some modules are indeed written in
C, and therefore would have to be compiled on the client's
platform if different from your own.
There is a clever commercial solution to the Perl deployment
problem known as perl2exe, by
IndigoStar Software.
This product does indeed let you bundle Perl source code along
with its needed modules into an executable, easily distributable
to other systems. There are versions of the software for Windows
and major Unix-variations such as Linux and SunOS. While a smart
deployment solution, the fact remains that perl2exe is
commercial software with a price tag, and is needed to overcome a
limitation that should be resolved in the architecture of Perl
itself.
Common Criticisms - Page 161
The Perl You Need to Know Part 22: Warts and All - Page 160
A Toolbox Heritage - Page 163
|