0

I need to find ONLY the lines that start with the string G1 Z, and then replace any occurrence on that same line of F1800 with a new value of F500. For example:

G1 Z9.800 F1800.000 ; move to next layer (48)
G1 X103.711 Y99.145 F1800.000 ; move to first perimeter point
G1 X96.289 Y96.289 E320.13685 ; perimeter
G1 Z0.000 F1800.000 ; move to next layer (49)
G1 X103.711 Y96.289 E320.44978 ; perimeter
G1 X103.711 Y99.070 E320.56702 ; perimeter
G1 X95.782 Y104.218 E321.13977 F1800.000 ; perimeter

Should become:

G1 Z9.800 F500.000 ; move to next layer (48)
G1 X103.711 Y99.145 F1800.000 ; move to first perimeter point
G1 X96.289 Y96.289 E320.13685 ; perimeter
G1 Z10.000 F500.000 ; move to next layer (49)
G1 X103.711 Y96.289 E320.44978 ; perimeter
G1 X103.711 Y99.070 E320.56702 ; perimeter
G1 X95.782 Y104.218 E321.13977 F1800.000 ; perimeter

I know /^G1 Z will find these lines, and %s/F1800/F500/g will replace ALL F1800s, but I can't see how to restrict the replace to the lines starting with that string.

I'm on GVIM 8.0.586.

6

Try:

:g/^G1 Z/s/F1800/F500/g

The :g is the "global" command. It selects lines with a regular expression and then executes a command on it.

Here it selects lines that start with G1 Z and then substitutes all "F1800" with "F500" in this line.

BTW:

  • The default command for :g is print. So by just executing :g/^G1 Z/ Vim will print all lines that start with G1 Z.
  • There is also the :v/.../ command. It selects all lines that does not match the given regular expression.

See :help multi-repeat.

2

The following command uses look behind regex pattern:

:%s/\v(^G1 Z.*)@<=F1800/F500/g
  • %s starts the substitution in the whole file.
  • / starts the find part of the find and replace.
  • \v enables very-magic (see :h /magic)
  • (^G1 Z.*)@<= looks behind for lines starting with G1 Z. But it doesn't start the matching. (see :h /\@<=)
  • F1800 starts matching for, well, F1800.
  • / starts the replace part of find and replace.
  • F500 replaces the matched pattern
  • / finishes the replace pattern
  • g is for global substitution, so that all the instances of F1800 will be replaced by F500. (see :h :s_flags)
  • Can also use \zs. e.g. :%s/^G1 Z.*\zsF1800/F500/ – Peter Rincker Mar 20 at 19:06
  • Thanks for the answer and detailed explanation. I found the other answer easier to follow. – Davo Mar 20 at 19:25
  • 1
    @PeterRincker but that wouldn't work if there are more than one F1800 in a line – klaus Mar 20 at 19:29
  • @Davo yes. I just wanted to see if I could get the solution. I learnt about @<= today. Although I know using :g/pattern/cmd is more intuitive in cases like this. By the way, does it work? – klaus Mar 20 at 19:32
  • 1
    Yes, both answers and @PeterRincker's example all worked. :) – Davo Mar 20 at 19:39

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.