Hi Evgeny!
On Saturday 14 March 2009 16:01:02 Evgeny wrote:
> Thank you, now it looks much better.
>
You're welcome.
> > I would write it like that: (untested)
> >
> > <<<<<<<<<
> > while (my ($key, $cb) = each(%matchers))
> > {
> > if (my @subgroups = ($line =~ $key))
> > {
> > $cb->(@subgroups);
> > }
> > }
>
> Will try not to post the whole messages this time. Just 1-2K :)
>
Thanks! I see it's much better now. There's still an HTML part, but I can live
with that because KMail (and I assume most other MUA's) display the text part
just fine.
>
> Now there is also another issue I remember having.
> How can I pass an unspecified amount of arguments to a function, since a
> function does not really care how many parameters it gets - I just read
> them one by one with "shift". I want to have a generic
> $callback->(.........) where instead of the dots I dont use an array, but
> "explode" this array into multiple arguments.
>
> In ruby it is done exactly like that callback( * array ) where the * is
> exploding it.
>
Well, in Perl 5, every subroutine accepts an array (and returns one). It's up
to you to decide how to extract the arguments from it. If you do
<< $callback->(@array) >>, then @array will be clobbered into the @_ of
$callback. So you can do for example (tested):
<<<<<<<<
#!/usr/bin/perl
use strict;
use warnings;
sub sing
{
my ($first_name, $last_name, $song) = @_;
print "$first_name $last_name sings $song\n";
return;
}
{
my @input1 = ("David", "Ben-Yishay", "Mizmor-Le-David");
sing(@input1);
}
{
my @input2 = ("Aretha", "Franklin", "Respect");
sing(@input2);
}
{
my @input2 = ("Jonh", "Lennon", qq{"Imagine"});
sing(@input2);
}
>>>>>>>>
Passing an array to a function may not be as straightforward in case the
function defines a prototype (which it usually shouldn't - see:
http://www.perlfoundation.org/perl5/index.cgi?prototype ).
If you're interested in passing an array to a function without clobbering the
rest of the argument list, then you should pass it as a reference using
\...@myarray, or [...@myarray] (depending on what you want to do - see
http://perldoc.perl.org/perlreftut.html ). Then you can just do inside the
function:
<<<<<<<<
sub my_func
{
my $my_array_ref = shift;
# Do stuff with $my_array_ref like:
print $my_array_ref->[$idx], "\n";
print join (",",@{$my_array_ref}), "\n";
}
>>>>>>>>
Also note that, with methods, the first argument must be the object reference,
and the rest of the arguments should follow it. That's because it is used to
determine the package that the object is associated with and which method to
call.
> Because, as you have seen, I would love to write the callbacks like this:
>
> Given('a (.*)', sub {
> my $object = shift;
> })
>
> But since I can only pass an array, I end up with this:
> Given('a (.*)', sub {
> my @params = shift;
This is wrong. You need either:
<<<
my @params = @_;
>>>
Or:
<<<
my $params = shift;
>>>
> my $project = $params[0];
> })
>
You can pass the object as the first argument to the callback and then the
rest of the params either flattened or as a reference:
* $callback->($object, @params);
* $callback->($object, \...@params);
>
>
>
> Regarding you comments on DSL, it looks like you assume that I would want
> to parse the DSL ... well, in a way I guess I am parsing it. But not
> really. I rather thing that the actual DSL would be the language to write
> specification code - not the story specification itself.
>
Not sure I understand you.
> So where I use
>
> sm(qr/Given a (.*)/, sub {
> some code here;
> })
>
> I would want a DSL to allow programmers to write it easier, with less
> syntax. Like in ruby's cucumber:
>
> Given /a (.*)/ {
> some code here;
> }
>
Hmmmm.... not sure if the Perl 5 syntax is that flexible.
> And if there is anything that I can do to remove the extra syntax sugar
> from the perlish way, I would gladly do it.
Just a note: the term "syntactic sugar" is used when the extra syntax is a
good thing. The term you are looking for in this case is "syntactic salt".
> Since the engine (the final
> loop) is not being actively edited. But these matchers will be multiple and
> need to be written quite a lot, the simpler they are the better. (and
> naturally i dont want to parse it as a DSL ... but maybe if its easy then
> it is also a solution).
Well, writing a parser using Parse::RecDescent or a different parser generator
is not too hard, but can be time consuming. I think every programmer worth his
weight in salt (or sugar... ;-)) should know how to write parsers using yacc
and similar tools. But note that embedding arbitrary Perl code inside may
become nasty unless you have a good mechanism to delimit it (like here-
documents).
>
>
> Also thank you for the greedy/non-greedy examples and generally
> manipulating regexps. I will probably need it sometime later.
>
You're welcome.
Regards,
Shlomi Fish
>
>
> Regards,
> Evgeny
>
--
-----------------------------------------------------------------
Shlomi Fish http://www.shlomifish.org/
Stop Using MSIE - http://www.shlomifish.org/no-ie/
God gave us two eyes and ten fingers so we will type five times as much as we
read.
_______________________________________________
Perl mailing list
[email protected]
http://perl.org.il/mailman/listinfo/perl