Wednesday, October 22, 2014

replace submatches in matchlist

Is there a good way to replace submatches in matchlist() and modify the
original line with it? I like to write a script which modifies all of the
submatches in a pattern in one step.

For example the original line is 'some AfooBar' and i like to change it to
'some CfooDar':

let pattern = '\(A\)foo\(B\)'
let line = 'some AfooBar'
let found = matchlist( line, pattern )

The 'found' contains "['AfooB', 'A', 'B', '', '', '', '', '', '', '']". Now i
like to modify the 'line' to 'some CfooDar' so the best should be:

let found[1] = 'C'
let found[3] = 'D'
let line = MATCHLIST_TO_STRING( found )

As i know it's not possible with the builtin functions, so i need to write
one. The beginning of the line is not modified till the match, thus i can copy
that part to the 'new_line':

let new_line = strpart( line, 0, match( line, pattern ) )

But at this point i don't know how to continue. I can append the modified 'A'
immediately, because the pattern starts with it (in this example, but the user
can use any kind of pattern). But how can i find out the (offset) index of the
'foo' and the 'B'? In this example it's trivial, because there is no other
'foo' and 'B' in the line, but let see another example:

let line = 'A A A A A'
let pattern = 'A \(A\) A \(A\)'

If i like to modify this to 'A B A C A' then it's hard to detect the position
of the submatches in the 'line'.

One solution is to use submatches for the 'inner words' (like 'foo' in the
previous example'), but it decreasing the number of useful submatches. For
example:

let pattern = '\(A\)\(foo\)\(B\)'
let line = 'some AfooBar'
let found = matchlist( line, pattern )
" Remove the full match, we need only the submatches.
call remove( found, 0 )
let found[0] = 'C'
let found[2] = 'D'
let new_line = strpart( line, 0, match( line, pattern ) ) . join( found, '')

In this case we used one additional submatch, but the 'A \(A\) A \(A\) A' may
become '\(A \)\(A\)\( A \)\(A\)\( A\)' and it's too lot.

So is there a good way to replace all of the submatches with a new value in
one step?

--
--
You received this message from the "vim_use" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php

---
You received this message because you are subscribed to the Google Groups "vim_use" group.
To unsubscribe from this group and stop receiving emails from it, send an email to vim_use+unsubscribe@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

No comments: