Tuna has asked for the wisdom of the Perl Monks concerning the following question:

How can I successfully strip the newline character from the end of:
my $date = `date +%Y%m%d`;
or
my $date = system "date +%Y%m%d";
or
my $date = qx (date +%Y%m%d);
Each of the above returns yyyymmdd\n. Am I going about this the wrong way. Right now, the only way I am correctly populating $date is by passing yyyymmdd as a command line argument.

Replies are listed 'Best First'.
Re: System call problem
by lhoward (Vicar) on Mar 08, 2001 at 20:28 UTC
    Its generally considered good perl style to avoid doing system calls unnecessarily. In your case: instead of doung a system call to date, use localtime (or some other perl time function/module). Its generally less prone to unexpected errors and in many cases significantly faster to do it all in perl:
    my ($day,$mon,$year)=(localtime(time))[3,4,5]; my $date=sprintf("%0d%02d%02d",$year+1900,$mon+1,$day);
    a quick benchmark on my system shows the localtime method is 39 times faster than the system call to date method:
     localtime:  4 wallclock secs ( 3.10 usr +  0.06 sys =  3.16 CPU) @ 30622.78/s (n=96768)
       sysdate: 31 wallclock secs ( 0.38 usr  3.65 sys + 11.15 cusr  2.36 csys = 17.54 CPU) @ 767.25/s (n=3092)
    
    using
    #!/usr/bin/perl -w use strict; use Benchmark; timethese(0, { sysdate => "chomp( my \$date = `date +\%Y\%m\%d` );", localtime => 'my ($day,$mon,$year)=(localtime(time) +)[3,4,5]; my $date=sprintf("%0d%02d%02d",$year+1900,$mon+1,$day);', });
      exact ! I totaly agree with you, I avoid extra process creation when it's possible ( in complience with perlstyle I think :)
      _______________________
      Hope this helps
Re: System call problem
by arturo (Vicar) on Mar 08, 2001 at 20:34 UTC

    Better yet from a performance standpoint, spare yourself a system call and use the builtin localtime, à la:

    sub get_date { my @time=(localtime)[3..5]; $time[2]+=1900; $time[1]++; foreach ($time[1], $time[0]) { $_ = '0'.$_ if $_ < 10; } "$time[2]$time[1]$time[0]"; }

    Yes, it's wordier, but adding this to your toolkit will allow you to cut n' paste it wherever you need it; you can also stick it in a module.

    Philosophy can be made out of anything. Or less -- Jerry A. Fodor

Re: System call problem
by arhuman (Vicar) on Mar 08, 2001 at 20:20 UTC

    Err... the correct answer is RTFM but I'd rather tell you chomp (in case I would have missed something...)
    my $date = `date +%Y%m%d`; chomp $date; print "($date)";

    "Trying to be a SMART lamer" (thanx to Merlyn ;-)
Re: System call problem
by Gloom (Monk) on Mar 08, 2001 at 20:23 UTC
    Try chomp
    this remove the last character of a string, if it's a newline.
    this work also for an array ( processing each entry ).
    Becarefull, this function return true or false ( newline or not ) ! not the modified line.
    so
    my $date = chomp( `date ...` );
    will not return what you want, but
    chomp( my $date = `date ...` );
    does.
    ______________________
    Hope this helps
Re: System call problem
by andye (Curate) on Mar 08, 2001 at 20:20 UTC
Re: System call problem
by Jouke (Curate) on Mar 08, 2001 at 20:21 UTC
    Use chop() to cut off the last character, or chomp() to remove the trailing 'record seperator' (which normally is the "\n", but could be something else on other platforms.

    hth,

    Jouke Visser, Perl 'Adept'
Re: System call problem
by Tuna (Friar) on Mar 08, 2001 at 20:29 UTC
    Ok. I got it. Actually, although I forgot to post it originally, I did try:
    my $date = chomp( `date +%Y%m%d` );
    and thanks Gloom for correcting my syntax! And thx to all who replied!