You can always choose to walk the kings road: <snip> use Filesys::DiskSpace;
($fs_type, $fs_desc, $used, $avail, $fused, $favail) = df $dir; $total = $used + $avail; print "Total:$total\nUsed:$used\ n"; </snip> Yaron Kahanovitch ----- Original Message ----- From: "kapil.V" <[EMAIL PROTECTED]> To: beginners@perl.org, "Paul Lalli" <[EMAIL PROTECTED]> Cc: beginners@perl.org Sent: 10:55:01 (GMT+0200) Africa/Harare יום שישי 20 יולי 2007 Subject: Re: Query Paul Lalli wrote: > On Jul 18, 6:43 am, [EMAIL PROTECTED] (kapil.V) wrote: >> su-2.05b# df -h . >> Filesystem Size Used Avail Capacity Mounted on >> /dev/ad0s1e 136G 102G 23G 82% /home >> >> From my script I do: >> my $du = qx#df -h \.#; >> ($total,$used) = $du =~ /([0-9]+(\.[ 0-9]+)?)[ M|G]/sg; >> print "Total:$total\nUsed:$used\ n"; >> >> Output: >> Total:136G >> Used: >> >> Why is "$used" not set? > > Because you're not understanding the return value of m//. Which is > understandable, because there's so many things that can affect what > this operator returns. In this case, you have three factors: > * It's being called in list context > * It's using the /g modifier > * It contains capturing parentheses. > > In that case, Perl will repeatedly search the string for the pattern, > finding all instances of the entire pattern. The return value will be > a list of ALL instances of ALL captured submatches, in order. (ie, > the first $1, the first $2, the first $3, the second $1, the second > $2, the second $3, etc) > > Take a look at this: > $ perl -lwe' > my $du = "/dev/ad0s1e 136G 102G 23G 82% /home"; > print for $du =~ /([0-9]+(\.[ 0-9]+)?)[ M|G]/sg; > ' > 136 > Use of uninitialized value in print at -e line 3. > > 102 > Use of uninitialized value in print at -e line 3. > > 23 > Use of uninitialized value in print at -e line 3. > > > Do you see the issue now? Your pattern is successfully matched > (because of the /g modifier) a total of three times. The first time > through, the first set of capturing parentheses matches 136. The > second set is undefined, because you allowed it to be optional, so > that part wasn't matched at all (ie, there was no "period-and-more- > digits" following the set of digits). So the first two return values > of the m// are 136 and undef. > > Then the second time through, the first set of capturing parentheses > matched 102, and the second set again didn't match anything, so the > third and fourth return values of the m// are 102 and undef. > > The real problem here is that you don't want the second set of > parentheses to be capturing. You only want that period-and-digits to > be associated with each other so you can make them optional as a > group. This is known as "clustering" rather than capturing. To make > parentheses cluster without capturing, you start them with a ?: > sequence. Observe: > > $ perl -lwe' > my $du = "/dev/ad0s1e 136G 102G 23G 82% /home"; > print for $du =~ /([0-9]+(?:\.[ 0-9]+)?)[ M|G]/sg; > ' > 136 > 102 > 23 > > Now, there is only one set of capturing parentheses in this pattern. > The first time through, that set of parentheses matches 136. The > second time through, it maches 102. The third time through, it > matches 23. So the return value of this m// will be (136, 102, 23). > > For more information, please read: > perldoc perlre > perldoc perlreref > perldoc perlretut > > Hope this helps, > Paul Lalli > Thanks a lot. The issue is clear now. Previously, I was under the impression that a nested paranthesis would not qualify as a return value for a matched pattern. Thx. -- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] http://learn.perl.org/ -- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] http://learn.perl.org/