LinuxQuestions.org

LinuxQuestions.org (/questions/)
-   Programming (https://www.linuxquestions.org/questions/programming-9/)
-   -   Perl: why $scalar += 0; (https://www.linuxquestions.org/questions/programming-9/perl-why-%24scalar-%3D-0%3B-853739/)

catkin 01-02-2011 12:51 PM

Perl: why $scalar += 0;
 
Hello :)

I am dabbling in Perl like a tiny cygnet adrift on a windy river.

Here's the code:
Code:

my $pop = Net::POP3->new("poczta",Timeout=>30)# conect to mail
              or die "Can't connect to host: $!\n";
  my $messages = $pop->login("demerzeli"=>"mail")
              or die "Can't log in: ",$pop->message,"\n";
my $last  =$pop->last();
$messages += 0;
print "inbox has $messages messages";

What is the $messages += 0; for? As I understand it, $messages is set by the login function of the Net::POP3 object (is object the right term?) thus it is a scalar variable which has had a value assigned to it -- so what is achieved by adding 0 to it?

BTW I've netsearched for Perl intros/tutorials and found a gazillion. Are there any which are particularly recommended? A Perl cribsheet/reference would be handy too.

Best

Charles

makyo 01-02-2011 01:25 PM

Hi.

I don't know what login returns, but it might be something like an empty (visually) string. An example:
Code:

#!/usr/bin/env perl

# @(#) p1        Demonstrate why "$v += 0" is useful.

$b += 0;

print " a is :$a:, b is :$b:\n";

producing:
Code:

% ./p1
 a is ::, b is :0:

So, in a human-readable message the latter is preferable.

Try printing $messages before the arithmetic operation.

I use books, but if I run across a cheat-sheet, I'll post the link ... cheers, makyo

catkin 01-02-2011 01:36 PM

Thanks makyo :) Hole in one! Nice illustration. From http://search.cpan.org/~gbarr/libnet-1.19/Net/POP3.pm:
Code:

login ( [ USER [, PASS ]] )

    Send both the USER and PASS commands. If PASS is not given the Net::POP3 uses Net::Netrc to lookup the password using the host and username. If the username is not specified then the current user name will be used.

    Returns the number of messages in the mailbox. However if there are no messages on the server the string "0E0" will be returned. This is will give a true value in a boolean context, but zero in a numeric context.

    If there was an error authenticating the user then undef will be returned.

Presumably undef is equivalent to an empty string so as you reasoned but would that error not trigger the or die clause -- in which case the $messages += 0; would not be reached?

makyo 01-02-2011 01:53 PM

Hi, catkin.

I tried a lot of return values; it depends on how they do it:
Code:

#!/usr/bin/env perl

# @(#) p6        Demonstrate why "$v += 0" is useful.

use strict;
use warnings;

my ( $a, $b, $c );

$a = some_function() or die " Can't set scalar to empty string.\n";

$b += 0;

$c = 0E0;

print " a is :$a:, b is :$b:, c is :$c:\n";

exit(0);

sub some_function {

  # return "";
  # return " ";
  # return undef;
  # return "\000";
  # return 0E0;
  return "0E0";
}

producing:
Code:

% ./p6
 a is :0E0:, b is :0:, c is :0:

Best wishes ... cheers, makyo

wje_lq 01-02-2011 02:37 PM

Quote:

Originally Posted by catkin (Post 4210593)
Presumably undef is equivalent to an empty string so as you reasoned but would that error not trigger the or die clause -- in which case the $messages += 0; would not be reached?

There's a good chance they're not using undef. Here's what might be happening:
Code:

#!/usr/bin/perl
sub eye { return "0E0" };
my $pop=eye() or die "no spinach for you!\n";
print "$pop\n";
$pop+=0;
print "$pop\n";

The output from this toy script:
Code:

0E0
0


wje_lq 01-02-2011 03:00 PM

To clarify, as I should have said in the previous post:
  1. If they can't log in, they pass back either undef or 0 (we don't know which, and it doesn't matter), and we die.
  2. If there are no messages, they return 0E0, so we won't die.
Once we're past the possiblity of dying, we prettify it by adding zero to it.

markush 01-02-2011 05:42 PM

Hello together,
Quote:

Originally Posted by catkin (Post 4210557)
...BTW I've netsearched for Perl intros/tutorials and found a gazillion. Are there any which are particularly recommended? A Perl cribsheet/reference would be handy too...

I'd recommend to read the camel-book http://oreilly.com/catalog/9780596000271
It is not only an excellent tutorial for Perl but also covers a wide variety of Unix/Linux in a whole. It is very well written, and readable. You know Larry Wall, the creator of Perl is a linguist as well as an excellent adept of Unix. Since Perl has it's origin in the Unix-world and bases on many of the standard Unix-tools like e.g. sed, grep and the various shells, this book covers far more than only the Perl-language.

In my opinion it belongs to a handful of "must have read" books about Unix/Linux (where the other very important book is "Regular Expression" of Jeffrey Friedl).

Markus

Sergei Steshenko 01-02-2011 06:15 PM

Quote:

Originally Posted by catkin (Post 4210557)
Hello :)

I am dabbling in Perl like a tiny cygnet adrift on a windy river.

Here's the code:
Code:

my $pop = Net::POP3->new("poczta",Timeout=>30)# conect to mail
              or die "Can't connect to host: $!\n";
  my $messages = $pop->login("demerzeli"=>"mail")
              or die "Can't log in: ",$pop->message,"\n";
my $last  =$pop->last();
$messages += 0;
print "inbox has $messages messages";

What is the $messages += 0; for? As I understand it, $messages is set by the login function of the Net::POP3 object (is object the right term?) thus it is a scalar variable which has had a value assigned to it -- so what is achieved by adding 0 to it?

BTW I've netsearched for Perl intros/tutorials and found a gazillion. Are there any which are particularly recommended? A Perl cribsheet/reference would be handy too.


Best

Charles

Why not use the example from the official documentation: http://search.cpan.org/~gbarr/libnet-1.22/Net/POP3.pm ?


Anyway, from the documentation:

Code:

login ( [ USER [, PASS ]] )

    Send both the USER and PASS commands. If PASS is not given the Net::POP3 uses Net::Netrc to lookup the password using the host and username. If the username is not specified then the current user name will be used.

    Returns the number of messages in the mailbox. However if there are no messages on the server the string "0E0" will be returned. This is will give a true value in a boolean context, but zero in a numeric context.

    If there was an error authenticating the user then undef will be returned.

, so the


Code:

$messages += 0;
is a dirty way to make $messages numeric 0 rather then '0E0' string. A clean way is to check whether $messages is a number:

Code:

perldoc -otk -t -q scalar number
and my favorite is:

Code:

    There are also some commonly used modules for the task. Scalar::Util
    (distributed with 5.8) provides access to perl's internal function
    "looks_like_number" for determining whether a variable looks like a
    number.

.

makyo 01-02-2011 09:40 PM

Hi.
Quote:

Originally Posted by catkin (Post 4210557)
... A Perl cribsheet/reference would be handy too ...

Not short, but at least look at the pdf: http://www.digilife.be/quickreferenc...20Perl%205.pdf

Best wishes ... cheers, makyo

Sergei Steshenko 01-02-2011 10:16 PM

Regarding books - probably http://perldoc.perl.org/ -> Reference, http://perldoc.perl.org/index-tutorials.html .

Tinkster 01-03-2011 03:17 AM

Quote:

Originally Posted by makyo (Post 4210976)
Hi.

Not short, but at least look at the pdf: http://www.digilife.be/quickreferenc...20Perl%205.pdf

Best wishes ... cheers, makyo

I assume the link is legit as there's no reference to the old-timer
on O'Reilly's website... :}


Just one note on that: Perl 5.004 is 14 years old, things have
evolved a fair bit since.

makyo 01-03-2011 05:31 AM

Hi, Tinkster.
Quote:

Originally Posted by Tinkster (Post 4211182)
I assume the link is legit as there's no reference to the old-timer
on O'Reilly's website... :}

Just one note on that: Perl 5.004 is 14 years old, things have
evolved a fair bit since.

Ramblings:

I had not thought about that. The Guide author's page is at http://www.vromans.org/johan/perlref.html pointing to http://www.squirrel.nl/pub/perlref-5.004.1.pdf so I think the 31-page pdf is OK. There are also links to text and HTML versions.

I agree that Perl has moved ahead, and I have not looked at the Guide in detail. The edition of Programming perl book that I use is from 2000 (3rd edition). There is a long history of editions for the Guide. The 4th Edition available from O'Reilly has 96 printed pages. My take is that the basic stuff is pretty much the same. Some of the perl 6 functionality has been made available in modules, e.g. http://search.cpan.org/~jesse/perl-5...lib/feature.pm

I have attended local conferences, for example one coming up is http://www.frozen-perl.org/mpw2011/ , and implementations of perl 6 still seems likely to be in development for a while.

cheers, makyo

catkin 01-03-2011 10:00 AM

Quote:

Originally Posted by makyo (Post 4210603)
I tried a lot of return values; it depends on how they do it

Thanks for taking the time to try that makyo :) Most likely the technique is used to make the 0E0 number format more palatable as Sergei and wje_lq described.

catkin 01-03-2011 10:08 AM

Quote:

Originally Posted by Sergei Steshenko (Post 4210820)
Why not use the example from the official documentation: http://search.cpan.org/~gbarr/libnet-1.22/Net/POP3.pm ?

Thanks Segei :) Once I understand the code well enough I probably will but I'm starting with somebody else's script and wanting to understand it completely before having the temerity to re-write it!

catkin 01-03-2011 10:14 AM

Quote:

Originally Posted by makyo (Post 4210976)
Not short, but at least look at the pdf: http://www.digilife.be/quickreferenc...20Perl%205.pdf

Thank you makyo, thank you O'Reilly :) That's exactly what I was hoping for and the ToC entries are hot links; nice.

EDIT: concerns about it being back-level noted; will see how it works out in practice, cross-referencing other sources as necessary (and will try to remember to update this thread if findings are significant).


All times are GMT -5. The time now is 03:44 AM.