#1
  1. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0

    Select data between strings


    Hi,
    i have the following line in a file (file.dat)

    DECAY 6100006 7.08092110e-05 # t1 decays

    and I need to extract only the 7.08092110e-05 and both print it at video and save it into file.
    I have tried

    open(file "file.dat");
    while(<file>){
    print $1 if /DECAY 6100006 (.*\n)/;
    }
    close(file);

    but this just give me

    7.02489719e-05 # t2 decays

    while I just need the number.. is there a way to do this?

    Cheers
  2. #2
  3. No Profile Picture
    Contributing User
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Apr 2009
    Posts
    1,938
    Rep Power
    1225
    Have you tried the 2 solutions you were already given on your cross post at perlguru.com?
  4. #3
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by FishMonger
    Have you tried the 2 solutions you were already given on your cross post at perlguru.com?
    yes both none of the two works :-(
  6. #4
  7. No Profile Picture
    Contributing User
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Apr 2009
    Posts
    1,938
    Rep Power
    1225
    They both work for me. You must have not copied the code correctly.

    What was the exact code you tested? What errors/warnings did you receive?
  8. #5
  9. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by FishMonger
    They both work for me. You must have not copied the code correctly.

    What was the exact code you tested? What errors/warnings did you receive?
    Hi thanks,
    with the first I just do

    while ( <FILE> )
    {
    chomp;
    if (/DECAY 6100006 ((([1-9][0-9]*\.?[0-9]*)|(\.[0-9]+))([Ee][+-]?[0-9]+)?)/)
    {
    print $1 , "\n";
    }
    }

    after that I have opened the file.dat, but this doesn't print me anything in output.

    With the second the thing is a bit more strange, if I try to put
    use strict;
    I obtain a lot of errors starting from the first lines, but i guess this is due to some package that I am missing... :\
  10. #6
  11. No Profile Picture
    Contributing User
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Apr 2009
    Posts
    1,938
    Rep Power
    1225
    after that I have opened the file.dat, but this doesn't print me anything in output.
    What do you mean by that?

    Are you expecting the file to be altered after running that code? It won't be.

    You should post your entire script and any errors/warnings that it generates. And explain how the results differ from what you expected.
  12. #7
  13. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by FishMonger
    What do you mean by that?

    Are you expecting the file to be altered after running that code? It won't be.

    You should post your entire script and any errors/warnings that it generates. And explain how the results differ from what you expected.

    No, i wasn't expecting the file to be altered after running the code... I was expecting to be printed at video with the instruction print $1 (is this correct).
    the entire script is quite long, more or less 3000 lines, so I was just putting the part of the script that I need to change to obtain what I expect.
    Namely I have a file.dat file in which I have a lot of data,
    from these data i need to extract a particular number which is situated between the strings, namely from the line

    DECAY 6100006 7.08092110e-05 # t1 decays

    I need to extract 7.08092110e-05 without anything else.
    I manage to print at video and save into file

    7.08092110e-05 # t1 decays

    but since I have to plot this data i need to get rid of the # t1 decays...

    Hope this is a bit more clear than before.. and thanks in advance..
  14. #8
  15. No Profile Picture
    Contributing User
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Apr 2009
    Posts
    1,938
    Rep Power
    1225
    Both of the solutions given on perlguru will produce your desired results provided your actual data is as you posted.

    If you wish, you could make a slight adjustment to your original regex to get your desired result, assuming your data is consistent in its format.

    Code:
    print $1 if /DECAY 6100006 (\S+)/;
  16. #9
  17. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by FishMonger
    Both of the solutions given on perlguru will produce your desired results provided your actual data is as you posted.

    If you wish, you could make a slight adjustment to your original regex to get your desired result, assuming your data is consistent in its format.

    Code:
    print $1 if /DECAY 6100006 (\S+)/;
    Ok... so is just a problem of my computer i guess.
    the line is esactely the one I post it

    DECAY 6100006 7.08092110e-05 # t1 decays

    is the 161th line in file.dat and I'm just writing this part of code

    open(FILE, "file.dat");
    while(<FILE>){
    print $1 if /DECAY 6100006 (\S+)/;
    }
    close(FILE);

    and seems correct... but at video I don't get any printing...
    So don't know... I'll try an alternative way..
  18. #10
  19. No Profile Picture
    Contributing User
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Apr 2009
    Posts
    1,938
    Rep Power
    1225
    Are you sure that the open call was successful?

    You should ALWAYS check the return code of an open call to verify it was successful and take action if it wasn't.

    You should also use a lexical var for the filehandle instead of the bareword and you shoud use the 3 arg form of open.

    Code:
    open my $fh, '<', "file.dat" or die "failed to open 'file.dat' $!";
    
    while( my $line = <$fh>){
        chomp $line;
        print "$1\n" if $line =~ /DECAY 6100006 (\S+)/;
    }
    
    close($fh);
    If you're using perl 5.10.0 or above, you could change that print statement to:
    Code:
    say $1 if $line =~ /DECAY 6100006 (\S+)/;
    Last edited by FishMonger; June 18th, 2013 at 11:06 AM.
  20. #11
  21. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by FishMonger
    Are you sure that the open call was successful?

    You should ALWAYS check the return code of an open call to verify it was successful and take action if it wasn't.

    You should also use a lexical var for the filehandle instead of the bareword and you shoud use the 3 arg form of open.

    Code:
    open my $fh, '<', "file.dat" or die "failed to open 'file.dat' $!";
    
    while( my $line = <$fh>){
        chomp $line;
        print "$1\n" if $line =~ /DECAY 6100006 (\S+)/;
    }
    
    close($fh);
    If you're using perl 5.10.0 or above, you could change that print statement to:
    Code:
    say $1 if $line =~ /DECAY 6100006 (\S+)/;
    Thanks for the tips!
    Now my code is

    open my $fh, '<', "file.dat" or die "failed";
    while(my $line = <$fh>){
    print $1 if $line =~ /DECAY 6100006 (\S+)/;
    }
    close($fh);

    but still no ouput at video...
  22. #12
  23. No Profile Picture
    Contributing User
    Devshed Intermediate (1500 - 1999 posts)

    Join Date
    Apr 2009
    Posts
    1,938
    Rep Power
    1225
    Originally Posted by dani8586
    Thanks for the tips!
    Now my code is

    open my $fh, '<', "file.dat" or die "failed";
    while(my $line = <$fh>){
    print $1 if $line =~ /DECAY 6100006 (\S+)/;
    }
    close($fh);

    but still no ouput at video...
    Then your data is not formatted the same as the sample line you posted.

    Please post at least 10 lines of your sample data. Copy/paste the lines, do not retype the lines.
  24. #13
  25. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by FishMonger
    Then your data is not formatted the same as the sample line you posted.

    Please post at least 10 lines of your sample data. Copy/paste the lines, do not retype the lines.
    here there are, thanks!

    6300008 6.00000000e+02 # X3MASS
    6400008 6.00000000e+02 # X4MASS
    6100007 6.00000000e+02 # Y1MASS
    6200007 6.00000000e+02 # Y2MASS
    6300007 6.00000000e+02 # Y3MASS
    6400007 6.00000000e+02 # Y4MASS
    # PDG Width
    DECAY 6100006 7.08092110e-05 # t1 decays
    # BR NDA ID1 ID2
    0.00000000e+00 2 2 23 # BR(t1 -> u z )
    0.00000000e+00 2 4 23 # BR(t1 -> c z )
    0.00000000e+00 2 6 23 # BR(t1 -> t z )
    0.00000000e+00 2 2 25 # BR(t1 -> u h )
    0.00000000e+00 2 4 25 # BR(t1 -> c h )
    0.00000000e+00 2 6 25 # BR(t1 -> t h )
    0.00000000e+00 2 1 24 # BR(t1 -> d w+ )
  26. #14
  27. No Profile Picture
    Contributing User
    Devshed Novice (500 - 999 posts)

    Join Date
    Jun 2012
    Posts
    832
    Rep Power
    496
    Try changing you code to:

    Perl Code:
    open my $fh, '<', "file.dat" or die "failed";
            while (my $line = <$fh>) {
    		   print $1 if $line =~ /DECAY\s+6100006\s+(\S+)/;
    	}   
    close($fh);
  28. #15
  29. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2013
    Posts
    8
    Rep Power
    0
    Originally Posted by Laurent_R
    Try changing you code to:

    Perl Code:
    open my $fh, '<', "file.dat" or die "failed";
            while (my $line = <$fh>) {
    		   print $1 if $line =~ /DECAY\s+6100006\s+(\S+)/;
    	}   
    close($fh);
    Thanks :-)

IMN logo majestic logo threadwatch logo seochat tools logo