Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I conditionally replace a line with a single word using Perl?

Tags:

perl

I want to replace a lines that ends with 'YES' with 'YES' and replace lines that ends with 'NO'with 'NO'. I have to apply for a large file.

Input:

 max. C    13       0.457   0.32   YES
 max. Y    13       0.232   0.33   NO
 max. S     1       0.315   0.87   NO  

Output:

YES
NO
NO
like image 871
bharathy Avatar asked Feb 28 '23 15:02

bharathy


1 Answers

While Paul's answer is correct, I wanted to point out there was another way to look at your problem. Your question states that the line ends with "YES" or "NO". Therefore another thing you could do is split the line and print the last element, if it matches "YES" or "NO":

perl -lape'$_=$F[-1] if $F[-1]=~m/^(?:YES|NO)$/'

In your example, all the lines ended in YES or NO. If this is really the case for all lines in your input, this can be simplified to:

perl -lape'$_=$F[-1]'

A short explanation of the Perl command-line flags used (you can also read this at "perldoc perlrun"):

  • -l is used to automatically chomp the input strings and append "\n" when printing.
  • -a auto-splits the input line on whitespace into the @F array, when used together with "-n" or "-p".
  • -p creates a loop that runs over the lines of the given input file/s and does a "print" at the end after your code is run.
  • -e is of course the flag for giving code on the command line

So basically the command-line flags do most of the work. The only thing I have to do is assign $F[-1] (the last element of the line) into $_ which is the thing which will be printed thanks to "-p".

My goal wasn't to play Perl Golf and show you a shorter way of answering your question, instead I'm trying to point out that simply thinking about a problem from a slightly different angle can show you different ways to solve it, which might be better/more elegant. So please don't focus on which solution is shorter, instead think about how different people attacked even this simple problem from different directions and how you can do the same.

One more point, you wrote "I want to replace a lines". If you meant replace in the input file itself, the "-i" (in-place replace) command-line flag is your friend:

perl -lapi.bak -e'$_=$F[-1]'
like image 51
Offer Kaye Avatar answered May 08 '23 23:05

Offer Kaye