I'm probably doing this all wrong. I have a text file full of data and I want to match and replace patterns of "item" and "catalog number" that are in the file. But the order of each element in the file is very important, so I want to match/replace starting from the top of the file and then work my way down.
The code snippet below actually works, but when I execute it, it replaces the third instance of the "SeaMonkey" & "SMKY-1978" pattern and then it replaces the second instance of that pattern. What I'd like it to do is replace the first instance of the pattern and then the second.
So I'd like the output to say "Found Kurt's SMKY-1978 SeaMonkeys" and then "Found Shane's SMKY-1978 SeaMonkeys" and then leave Mick's SMKY-1978 SeaMonkeys alone since I only want to find and replace the first 2 instances of the pattern. Right now it says "Found Shane's SMKY-1978 SeaMonkeys" and "Found Mick's SMKY-1978 SeaMonkeys" because it is matching the last pattern each time the for loop is executed.
So am I missing a subtle little known regexp character or am I just doing what I want to do completely and utterly wrong?
Here is the working code:
# my regexp matches from the bottom to the top but I'd like it to repl +ace from the top down local $/=undef; my $DataToParse = <DATA>; my $item = "SeaMonkeys"; my $catNum = "SMKY-1978"; my $maxInstancesToReplace = 2; parseData(); exit(); sub parseData { for (my $counter = 0; $counter < $maxInstancesToReplace; $counter+ ++) { # Stick in a temporary text placeholder that I will replace la +ter after more processing $DataToParse =~ s/(.+)\sELEMENT\s(.+?)\s\(Item := \"$item\".+? +CatalogNumber := \"$catNum.+?END_ELEMENT(.+)/$1 ***** Found $2\'s $ca +tNum $item. (counter: $counter) *****$3/s; } print("Here's the result:\n$DataToParse\n"); } __DATA__ ELEMENT Kurt (Item := "BrightLite", ItemID := 29, CatalogNumber := "BTLT-9274", Vendor := 100, END_ELEMENT ELEMENT Mick (Item := "PetRock", ItemID := 36, CatalogNumber := "PTRK-3475/A", Vendor := 82, END_ELEMENT ELEMENT Kurt (Item := "SeaMonkeys", ItemID := 12, CatalogNumber := "SMKY-1978/E", Vendor := 77, END_ELEMENT ELEMENT Joe (Item := "Pong", ItemID := 24, CatalogNumber := "PONG-1482", Vendor := 5, END_ELEMENT ELEMENT Shane (Item := "SeaMonkeys", ItemID := 1032, CatalogNumber := "SMKY-1978/E", Vendor := 77, END_ELEMENT ELEMENT Kurt (Item := "Battleship", ItemID := 99, CatalogNumber := "BTLS-5234", Vendor := 529, END_ELEMENT ELEMENT Mick (Item := "SeaMonkeys", ItemID := 8, CatalogNumber := "SMKY-1978/F", Vendor := 77, END_ELEMENT ELEMENT Frank (Item := "PetRock", ItemID := 42, CatalogNumber := "PTRK-3475/B", Vendor := 82, END_ELEMENT ELEMENT Joe (Item := "SeaMonkeys", ItemID := 8, CatalogNumber := "SMKY-1979/A", Vendor := 77, END_ELEMENT
And here is what it currently outputs:
Here's the result: ELEMENT Kurt (Item := "BrightLite", ItemID := 29, CatalogNumber := "BTLT-9274", Vendor := 100, END_ELEMENT ELEMENT Mick (Item := "PetRock", ItemID := 36, CatalogNumber := "PTRK-3475/A", Vendor := 82, END_ELEMENT ELEMENT Kurt (Item := "SeaMonkeys", ItemID := 12, CatalogNumber := "SMKY-1978/E", Vendor := 77, END_ELEMENT ELEMENT Joe (Item := "Pong", ItemID := 24, CatalogNumber := "PONG-1482", Vendor := 5, END_ELEMENT ***** Found Shane's SMKY-1978 SeaMonkeys. (counter: 1) ***** ELEMENT Kurt (Item := "Battleship", ItemID := 99, CatalogNumber := "BTLS-5234", Vendor := 529, END_ELEMENT ***** Found Mick's SMKY-1978 SeaMonkeys. (counter: 0) ***** ELEMENT Frank (Item := "PetRock", ItemID := 42, CatalogNumber := "PTRK-3475/B", Vendor := 82, END_ELEMENT ELEMENT Joe (Item := "SeaMonkeys", ItemID := 8, CatalogNumber := "SMKY-1979/A", Vendor := 77, END_ELEMENT
In reply to can I make my regex match first pattern instead of last? by kleucht
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |