I've been receiving logged data in a text file that is just one long line with each value separated by a space. Is there a command or set of commands that will split one line into multiple lines?
4 Answers
You could simply replace any consecutive space on the line with a newline using the command :s/\s\+/\r/g
. \s\+
mean one or more whitespace characters, and \r
is a newline, see :help :substitute
and :help regexp
for details. If you run the command on a line like:
foo bar baz
You get:
foo
bar
baz
If you have hlsearch
enabled and you don't want to clutter your screen with highlighted spaces everywhere, you can write a little function like the following to avoid it:
function! SplitLineNicely()
" Save previous value of last search register
let saved_last_search_pattern = @/
" :substitute replaces the content of the search register with the `\s\+`
" pattern highlighting all whitespaces in the file
substitute /\s\+/\r/g
" Restore previous search register
let @/ = saved_last_search_pattern
endfunction
-
"If you don't want to clutter your screen with highlighted spaces everywhere" this assumes too much about the OP's setup.– romainlFeb 13, 2015 at 15:26
-
-
1
-
2It is
\r
, see:help s/\r
. It could be replaced by a literal newline typing<c-v><cr>
. In this context\n
is a null character, see:help s/\n
.– toro2kFeb 13, 2015 at 16:09 -
1
The easiest way I've found to split lines in Vim is the normal mode command gq
(type both letters in quick succession in normal or visual mode).
In visual mode, it will split whatever is selected, in normal mode, you follow gq
with a motion.
For example, gql
will split one line to the currently set width. To set the width of the split lines to be different from your current setting, you can use :set textwidth=n
, where n
is the number of characters you want in a line, e.g., 10
and change back to your normal width when you're done.
Got this information from a Youtube video by Kholidfu that shows how to join and split lines in normal mode using a motion.
Using vim
's substitution is probably one of the better ways to accomplish your task, but you can use a macro as well. Suppose we have the following data, with the cursor somewhere on line 1:
1 a b c d e f
~
Starting in normal mode, hitting qq will start recording a macro callable via @q. Anything typed after qq will be repeatable via aforementioned call. Our goal is to record normal commands that will be general enough to allow for seamless repetition.
Thus, we may type 0 to bring the cursor to the start of the line, then fspace to move the cursor to the first space. This allows us to then type renter, resulting in:
1 a
2 b c d e f
~
Hitting q now is a good idea as our reusable macro is ready for repetition. Somewhat arbitrarily, we note that there are 4 spaces left to replace with newlines. Thus by hitting, 4@q, we repeat the q
macro 4 times resulting in:
1 a
2 b
3 c
4 d
5 e
6 f
~
Note that because of the way we set up the macro, it would have been safe to repeat the command over 9000 times, as it would only affect the current line, and since there were no spaces to the right of the last data entry, fspace will 'nicely' fail, preventing data from being replaced with newlines.
So to repeat from the beginning:
qq0fspacerenterq9001@q
provides our result.
-
2I love that you have a
9001
key on your keyboard for typing your username fast.– RichMay 2, 2019 at 12:24
I recommend you this regex:
:%s/\(\zs\w.\{-}\)\{8} \zs/\r/g
You can specify the number of characters to divide your long sentence where is the 8.
:%s/\(\zs\W.\{-}\)\{8}/\r/g
This another do almost the same but counting by words.