Re: negative match pattern, again
It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Edward Wong wrote: Learn a lot more about regexp from this post. Thanks! Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Just a question, why it is necessary to have the ^ anchor? Isn't .* already includes the characters start from the beginning of the line? Sorry if I'm asking a stupid one Not a stupid question at all. [EMAIL PROTECTED] and variants are tricky (IMHO). Considering: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] First, big.*bar.*tummy can not match quite often! Just as [EMAIL PROTECTED] ordered. So look at the following two lines: big junk bar junk tummy junk foo junk bar junk tummy junk foo Its best to :set hls first, so as to see what matches. Try matching with and without that leading ^. With the ^, big junk bar junk tummy junk foo-- doesn't match junk bar junk tummy junk foo-- matches which is what one would expect. However, without that ^, the pattern is free to start matching _after_ the start-of-line, and so ig junk bar junk tummy junk foo -- matches junk bar junk tummy junk foo-- matches (I left off the non-matching b in the first line). Thus, both lines match, which isn't what's wanted, especially considering the regexp was expected to be used with :g/regex-here/somecmd Regards, Chip Campbell
Re: negative match pattern, again
Very great explanation! Many thanks to Gerald and Chip Campbell. Now I _really_ got it. :) On 6/13/06, Charles E Campbell Jr [EMAIL PROTECTED] wrote: It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Edward Wong wrote: Learn a lot more about regexp from this post. Thanks! Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Just a question, why it is necessary to have the ^ anchor? Isn't .* already includes the characters start from the beginning of the line? Sorry if I'm asking a stupid one Not a stupid question at all. [EMAIL PROTECTED] and variants are tricky (IMHO). Considering: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] First, big.*bar.*tummy can not match quite often! Just as [EMAIL PROTECTED] ordered. So look at the following two lines: big junk bar junk tummy junk foo junk bar junk tummy junk foo Its best to :set hls first, so as to see what matches. Try matching with and without that leading ^. With the ^, big junk bar junk tummy junk foo-- doesn't match junk bar junk tummy junk foo-- matches which is what one would expect. However, without that ^, the pattern is free to start matching _after_ the start-of-line, and so ig junk bar junk tummy junk foo -- matches junk bar junk tummy junk foo-- matches (I left off the non-matching b in the first line). Thus, both lines match, which isn't what's wanted, especially considering the regexp was expected to be used with :g/regex-here/somecmd Regards, Chip Campbell -- Ed
Re: negative match pattern, again
I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. Well, there are several ways to go about it. One would be to use Dr. Chip's logipat script: http://vim.sourceforge.net/scripts/script.php?script_id=1290 Another would be to use something like :g/foo/if getline(.)!~'blah' | print getline(.) | endif which would search for lines that do contain foo, but don't contain blah. I don't know about using the \ atom. There might be a solution with that as well, but for negating matters, it becomes trickier. -tim
Re: negative match pattern, again
On Mon, Jun 12, 2006 at 02:42:18PM +, Yakov Lerner wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. I think I need to use \ ^.*foo\^XXX$ and then put, in place of XXX, the pattern that matches anything not containing /)\s*;/. How do I express it in vim. Yakov I'd write \([^)]\|)\S\|)\s*[^;]\) failing other things. How about preceding 'foo' with '\(...\)\@!' and following it with '\(...\)[EMAIL PROTECTED] as in /\()\s*;.*\)\@!foo\(.*)\s*;\)[EMAIL PROTECTED]/ HTH --Benji Fisher
Re: negative match pattern, again
On 6/12/06, Tim Chase [EMAIL PROTECTED] wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. Well, there are several ways to go about it. One would be to use Dr. Chip's logipat script: http://vim.sourceforge.net/scripts/script.php?script_id=1290 LogiPat does wonders. Thanks. For the record, :echo LogiPat('foo!bar') produces: \%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) Yakov
Re: negative match pattern, again
Yakov Lerner wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. I think I need to use \ ^.*foo\^XXX$ and then put, in place of XXX, the pattern that matches anything not containing /)\s*;/. How do I express it in vim. Yakov I'd write \([^)]\|)\S\|)\s*[^;]\) failing other things. May I suggest that you try LogiPat out: http://vim.sourceforge.net/scripts/script.php?script_id=1290 or at http://mysite.verizon.net/astronaut/vim/index.html#VimFuncs (see LogiPat) (as always, my website has the most up-to-date version) In this case, :echo LogiPat('foo !)\s*;') yields \%(.*foo.*\^\%(\%()\s*;\)[EMAIL PROTECTED])*$\) Regards, Chip Campbell
Re: negative match pattern, again
On 6/12/06, Benji Fisher [EMAIL PROTECTED] wrote: On Mon, Jun 12, 2006 at 02:42:18PM +, Yakov Lerner wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. I think I need to use \ ^.*foo\^XXX$ and then put, in place of XXX, the pattern that matches anything not containing /)\s*;/. How do I express it in vim. Yakov I'd write \([^)]\|)\S\|)\s*[^;]\) failing other things. How about preceding 'foo' with '\(...\)\@!' and following it with '\(...\)[EMAIL PROTECTED] as in /\()\s*;.*\)\@!foo\(.*)\s*;\)[EMAIL PROTECTED]/ Benji, Im not sure the post-foo part works. I think it will give the false match whenever it something after foo that does not match )\s*;. This is not what I wanted. Yakov
Re: negative match pattern, again
On 6/12/06, Gerald Lai [EMAIL PROTECTED] wrote: On Mon, 12 Jun 2006, Gerald Lai wrote: On Mon, 12 Jun 2006, Yakov Lerner wrote: On 6/12/06, Tim Chase [EMAIL PROTECTED] wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. Well, there are several ways to go about it. One would be to use Dr. Chip's logipat script: http://vim.sourceforge.net/scripts/script.php?script_id=1290 LogiPat does wonders. Thanks. For the record, :echo LogiPat('foo!bar') produces: \%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) Yakov In addition to the regex above, you can also do: /^\%(.*)\s*;\)[EMAIL PROTECTED] It's a little shorter, and probably a little faster since the LogiPat regex does a \%(..\)* for every character position of the line. The speed is evident for a long line. It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Is the trailing .* necessary there ? Why ? Yakov
Re: negative match pattern, again
On Mon, 12 Jun 2006, Yakov Lerner wrote: On 6/12/06, Gerald Lai [EMAIL PROTECTED] wrote: On Mon, 12 Jun 2006, Gerald Lai wrote: On Mon, 12 Jun 2006, Yakov Lerner wrote: On 6/12/06, Tim Chase [EMAIL PROTECTED] wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. Well, there are several ways to go about it. One would be to use Dr. Chip's logipat script: http://vim.sourceforge.net/scripts/script.php?script_id=1290 LogiPat does wonders. Thanks. For the record, :echo LogiPat('foo!bar') produces: \%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) Yakov In addition to the regex above, you can also do: /^\%(.*)\s*;\)[EMAIL PROTECTED] It's a little shorter, and probably a little faster since the LogiPat regex does a \%(..\)* for every character position of the line. The speed is evident for a long line. It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Is the trailing .* necessary there ? Why ? Nope, not necessary for :g//. I left it there for hlsearch appeal ;) HTH. -- Gerald
Re: negative match pattern, again
Gerald Lai wrote: On Mon, 12 Jun 2006, Gerald Lai wrote: On Mon, 12 Jun 2006, Yakov Lerner wrote: On 6/12/06, Tim Chase [EMAIL PROTECTED] wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. Well, there are several ways to go about it. One would be to use Dr. Chip's logipat script: http://vim.sourceforge.net/scripts/script.php?script_id=1290 LogiPat does wonders. Thanks. For the record, :echo LogiPat('foo!bar') produces: \%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) Yakov In addition to the regex above, you can also do: /^\%(.*)\s*;\)[EMAIL PROTECTED] It's a little shorter, and probably a little faster since the LogiPat regex does a \%(..\)* for every character position of the line. The speed is evident for a long line. It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Hello! These two regex's produce different results; I'm using foo and bar instead of foo and )\s*;, because its more human readable... To see the results, use: vim tst :set hls :so pat1 :so pat2 (also, use a fixed font to see this properly in the email) -- tst --P1--P2- foo * * bar foo junk* * bar junk junk foo* * junk bar foo junk bar* bar junk foo -- pat1 /^\%(bar\)[EMAIL PROTECTED] -- pat2 /\%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) -- To summarize: Gerald's pattern (P1, pat1) matches the same three that LogiPat's (P2, pat2) does, plus it allows one line that P2 rejects. Regards, Chip Campbell
Re: negative match pattern, again
On Mon, 12 Jun 2006, Charles E Campbell Jr wrote: Gerald Lai wrote: On Mon, 12 Jun 2006, Gerald Lai wrote: On Mon, 12 Jun 2006, Yakov Lerner wrote: On 6/12/06, Tim Chase [EMAIL PROTECTED] wrote: I need to match lines using g// (not v//); those lines having 'foo' and NOT having /)\s*;/ anywhere in the line. How do I write such regex. Well, there are several ways to go about it. One would be to use Dr. Chip's logipat script: http://vim.sourceforge.net/scripts/script.php?script_id=1290 LogiPat does wonders. Thanks. For the record, :echo LogiPat('foo!bar') produces: \%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) Yakov In addition to the regex above, you can also do: /^\%(.*)\s*;\)[EMAIL PROTECTED] It's a little shorter, and probably a little faster since the LogiPat regex does a \%(..\)* for every character position of the line. The speed is evident for a long line. It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Hello! These two regex's produce different results; I'm using foo and bar instead of foo and )\s*;, because its more human readable... To see the results, use: vim tst :set hls :so pat1 :so pat2 (also, use a fixed font to see this properly in the email) -- tst --P1--P2- foo * * bar foo junk* * bar junk junk foo* * junk bar foo junk bar* bar junk foo -- pat1 /^\%(bar\)[EMAIL PROTECTED] -- pat2 /\%(.*foo.*\^\%(\%(bar\)[EMAIL PROTECTED])*$\) -- To summarize: Gerald's pattern (P1, pat1) matches the same three that LogiPat's (P2, pat2) does, plus it allows one line that P2 rejects. In the same context, pat1 should instead be: /^\%(.*bar\)[EMAIL PROTECTED] and both patterns match the same. -- Gerald
Re: negative match pattern, again
Gerald Lai wrote: In the same context, pat1 should instead be: /^\%(.*bar\)[EMAIL PROTECTED] and both patterns match the same. And so they do! (with your pattern having .* again, which is unnecessary for :g... as you mentioned). Regards, Chip Campbell
Re: negative match pattern, again
It follows the general form of a negative line search for embedded search: /^\%(.*[limit0.*]search[.*limit1]\)[EMAIL PROTECTED] For example, to match a line that contains foo but does not contain bar between big and tummy: /\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Learn a lot more about regexp from this post. Thanks! Sorry, I missed the ^ anchor: /^\%(.*big.*bar.*tummy\)[EMAIL PROTECTED] Just a question, why it is necessary to have the ^ anchor? Isn't .* already includes the characters start from the beginning of the line? Sorry if I'm asking a stupid one -- Ed