The problem I have is that is trying to match both sets of delimiter (above and below)

I'm trying to match only the second part of the delimiter below (bolded).

enter image description here

This is so I can add a new version made on the same day to multiple files. Using perl, so I can get a result like this when I make the replacement enter image description here

How ever according to https://regex101.com/ (and my experience when I ran the command) it selects both sets of delimiters, enter image description here

making a replacement above and below. enter image description here

This is the RegEx I'm using


And the comand in UNIX:

perl -pe 's#(?!V[0-9]{2}.[0-9]{2}.[0-9]{4}.1)(.*=.$)#-* V02.11.2020.1 11/Feb/2020 Author2 Minor Changed Include lms \n -* ================ ============= ==================== =========== ========================================================/#g' path/to/file

Is there a way to select the one below? Or the problem originates from the Negative Lookahead? -**********************************************************************
I used the command selected by bey0nd

3,$s/ -\*  =[=[:space:]]*\// -*  V02.11.2020.1\t  11\/Feb\/2020\t  Author2\t\t   Minor\tChange include 1ms\n\0/1

It helped a lot with readability

But I'm still getting both delimeters (= signs) repalced. I thought that the lookaround function of regex would've helped

enter image description here

I'm using perl 5 and sed 4.2

At least I got it to work in regex101.com, but in my version didn't work

Hope someone finds it useful

(-\*  =[=[:space:]]*\/)(?!\n.-\*[[:space:]].V[0-9]{2}.[0-9]{2}.[0-9]{4}.1*)
  • I am guessing that what you are doing is use the capture group (.*=.$) and replacing it with the Version/Date/Author/Change/Description string followed by the back reference \1? What exactly does this file look like? Are those the only 2 instances of the delimiter? Is anything else there? Commented Feb 12, 2020 at 6:34
  • Is the PHP flag really relevant to the question?
    – Kusalananda
    Commented Feb 12, 2020 at 12:47
  • @Kusalananda♦ Is the "flavor" that I'm using in regex101.com. And the one that matched my problem with perl. Commented Feb 12, 2020 at 15:34
  • @Poisson Aerohead The command that I'm using looks like this -UNIX perl -pe 's#(.*=.$)(?<! V[0-9]{2}.[0-9]{2}.[0-9]{4}.1)#-* V02.11.2020.1 11/Feb/2020 Author2 Minor Changed Include lms \n -* ================ ============= ==================== =========== ========================================================/#g' path/to/file Commented Feb 12, 2020 at 15:36

3 Answers 3


This is the sed command I would use:

sed -e '3,$s/ -\*  =[=[:space:]]*\// -*  V02.11.2020.1\t11\/Feb\/2020\tAuthor2\tMinor\tChange include 1ms\n\0/' file

You might have to fiddle around with the tabs to make it fit your layout.

  • Thanks, the escaped characters helped for readability and you simplified my regex. The thing is that it selects both "=" signs at the top and at the bottom making the replacement twice. Like in the last image Commented Feb 12, 2020 at 22:56
  • In your first example the fist line with '=' signs was line number two. Now it's line number three. 8-/ The first number in the sed-command should be the line number (of the first '=' line) plus one.
    – bey0nd
    Commented Feb 13, 2020 at 9:31

I think I have what you want to add to your script. I made a file called testfile.txt with the following text in it:

-* some lines
-* some more lines
-* ======= ====== ======= ======= =======/
-* data data data
-* more data more data more data
-* ====== ====== ======= ======= ======/

I did this just so it would look roughly like your file, you can tailor to your specific needs. The following commands (which can go into a shell script) will insert "inserting new data inserting new data inserting new data" before the second delimiter, which is at the end of the data section. I understand that to be what you are trying to do.

lines=`grep -nEe "=+" testfile.txt | sed -e s/":.*"//`
lines=`echo $lines`
read line1 line2 <<< $lines
sed -i ${line2}i"-* inserting new data inserting new data inserting new data" testfile.txt

The final file for me is now

-* some lines
-* some more lines
-* ======= ====== ======= ======= =======/
-* data data data
-* more data more data more data
-* inserting new data inserting new data inserting new data
-* ====== ====== ======= ======= ======/

This effectively completes what I understand your issue to be. Please clarify if there are any other corners that need addressing for this to be complete.

Note that my regex is very simple just to force the match to the line with all the equal signs and assumes that the file is "well behaved." You may want your more specific regex if the file contents can vary (i.e. if a non delimiter line can contain equal signs). I take your question to imply you can write the regex on your own and needed help with getting the second match. Also note I assumed that you only want the second match and there are always going to be exactly 2.

The first command stores all line numbers that match the pattern in the variable lines. The second command cleans some kind of bad character out of the variable lines (I am not sure what) so that it is space delimited. The third command stores each matching line number in its own variable (here I assume exactly 2 matches). The fourth inserts the desired new data before the second match.


I think Poisson Aerohead's approach might be the better one.
I would just take some complexity out.

line=`grep -n '^ -\*  =*' testfile.txt | tail -1 |sed -e s/:.*//`
sed -i ${line}i'\ -* inserting new data ' testfile.txt

Be aware that this will insert the data before the last line which starts with ' -* ==', even though if there is only one line ( then this is also the last) like this.
If there is no line it will be inserted before each line!!

  • That is a nice clean way to get the last match. I used the method I did because the question was specifically for the second match, so I left open the case where there are more than 2 matches. Commented Feb 13, 2020 at 23:59

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .