By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
457,602 Members | 1,553 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 457,602 IT Pros & Developers. It's quick & easy.

Pattern matching and inserting a line in a file

P: 23
Hi All

I am trying to match a pattern in a file and insert a line. If the pattern matches then insert a line before the matching pattern line.

for example,
I have the following content in a file:

//This is my source file
//this is where i want to insert a line
Expand|Select|Wrap|Line Numbers
  1. class Class1
  2. {
  3.     data members
  4.     member functions
  5. }
  7. //this is where i want to insert a line
  8. class Class2
  9. {
  10.     data members
  11.     member functions
  12. }
I have to match for a pattern "Class" and insert a line before that pattern match.

This is what i have tried so far:

Expand|Select|Wrap|Line Numbers
  1. $presentFlag = 0;
  2. $notPresentFlag = 0;
  4. ##$ Open source file for reading the contents
  5. open(SOURCE,"<",$sourceFile) or die( "File not found...$!");
  6. ### open new file for inserting new line ->  [TestFixture], after matching a pattern
  7. open(DEST,">",$destFilename) or die("File not found...$!");
  9. while($fileLine = <SOURCE>){    
  10.     if( $fileLine =~ m/public class/ ){ # pattern to be matched in source file
  11.         if( $previousLine =~/[TestFixture]/ ){ # check for previous line if it already has new text
  12.             print "\n Pattern already present in FN $destFilename...$previousLine";
  13.             $presentFlag = 1;
  14.         }
  15.         else {
  16.             print "\n Pattern NOT present in FN $destFilename...$previousLine";
  17.             $notPresentFlag = 1;
  18.         }
  19.     }
  20.     ##### If pattern already present then print the file contents as it is in dest file    
  21.     if($presentFlag){
  23.         print DEST $fileLine;
  24.     }
  25.     ## Get the previous line here
  26.     $previousLine=$fileLine;
  27. }# end of while
  29. ### If pattern matches and doesnt have the previous line as required        
  30. if($notPresentFlag){
  31.     ### I am stuck do i move my insertion pointer to previous line in my source and dest file???
  32.     ### do i need to have a counter or is there any other alternate way?
  33. }
  34. close(SOURCE);
  35. close(DEST);

Thanks in advance.

Feb 19 '08 #1
Share this Question
Share on Google+
5 Replies

Expert 100+
P: 410
From your description, I feel this is what you need:
Expand|Select|Wrap|Line Numbers
  2. $i=0;
  3. $test_fixture="xxxxxxxxxxxxx"; ###put your [Test Fixture]
  4. open(SOURCE,"<",$sourceFile) or die( "File not found...$!");
  5. open(DEST,">",$destFilename) or die("File not found...$!");
  6. @source=<SOURCE>;
  7. while(@source)
  8. {
  9.    if( /public class/ ) {  ##search for the pattern in each line
  10.       ### insert test fixture if previous line doesn't have it already
  11.       print DEST "$test_fixture\n" unless($source[$i-1]=~/$test_fixture/);
  12.       print DEST $_;
  13.   }
  14.   else {
  15.     print DEST $_;
  16.  }
  17.  $i++;
  18. }
  20. close(SOURCE);
  21. close(DEST);
Feb 19 '08 #2

P: 14

read the file contents into an array like this
Expand|Select|Wrap|Line Numbers
  1. @array = <SOURCE>;
once the file is in the array you can loop through the array and take two lines [none od them should ne null - betwwn two lines there might be blank lines, they have to be supressed]
Expand|Select|Wrap|Line Numbers
  1. if( $arr[i]=~ m/public class/ ) and $arr[i-1] !~ $lineToBeInserted
  2. #tthen 
  3. print DEST $arr[i-1]
  4. print DEST $lineToBeInserted
try this in this manner
Feb 19 '08 #3

Expert 2.5K+
P: 4,059
It would help greatly if you showed the real text file you are trying to insert a line into. This part of your code makes little sense out of context and looks like it will just be wrong since you are using square brackets improperly /[TestFixture]/:

Expand|Select|Wrap|Line Numbers
  1.    if( $fileLine =~ m/public class/ ){ # pattern to be matched in source file
  2.        if( $previousLine =~/[TestFixture]/ ){ # check for previous line if it already has new text
Inserting lines into files is easily done using perls inplace editor once you learn how to get it running, which is extremely simple but few perl books or tutorials cover the use of the inplace editor. It is also extrememly fast so editing even big files should be quick.
Feb 19 '08 #4

P: 23
Thanks a lot Nithin. and thanks Npidaparthy for optimized code.
I am able to achieve to some extent of what was required.
But the complexity is incresing now. I will get back in case i need any further help on this.
Kevin, please send me more information on PERL inplace editor for Windows platform. i have seen that some of the statements work only in Unix( for ex: perl -p -i.bak -e.....). Thanks in advance.

Thanks everyone.

Feb 20 '08 #5

Expert 2.5K+
P: 4,059
the inplace editor for Windows works the same as Unix. The only differences I am aware of is you have to define a backup extension with Windows (-i.bak) and you use double-quotes instead of single-quotes around the code part:

-e "some code here"
Feb 20 '08 #6

Post your reply

Sign in to post your reply or Sign up for a free account.