【问题标题】:Split single line with multiple words into many lines with x words on each将带有多个单词的单行拆分为多行,每行带有 x 个单词
【发布时间】:2017-01-13 17:52:32
【问题描述】:

我有一个大文本文件,其中仅包含 1 行。它看起来像这样:

blaalibababla.ru text text text text what's the weather like tooday? blaazzabla.zu some_text blabewdwefla.au it is important not to be afraid of sed blabkrlqbla.ru wjenfkn lkwnef lkwnefl blarthrthbla.net 1234 e12edq 42wsdfg blablabla.com this should finally end

我需要一种方法让它看起来像这样:

blaalibababla.ru text text text text what's the weather like tooday?
blaazzabla.zu some_text
blabewdwefla.au it is important not to be afraid of sed
blabkrlqbla.ru wjenfkn lkwnef lkwnefl
blarthrthbla.net 1234 e12edq 42wsdfg 
blablabla.com this should finally end

我知道如何使用单个域名和sed

sed -i 's/blablabla.ru/\n&/g' file.txt

“但不是在之后的附加文本中。” - 我不是这个意思。

如果sed 不是最好的方法,请告诉我。

更新: 这是我的文本文件:

wsd.qwd.qwd.kjqnwk.ru PUPPETD CRITICAL 2017-01-13 00:09:52   lor notify-by-sms FILE_AGE CRITICAL:   /var/lib/puppet/state/state.yaml is 2438046 seconds old and 19459 bytes   zm-goas-04.asdg.net LOAD CRITICAL 2017-01-13 00:10:32   tech-lor notify-by-telegram CRITICAL - load average: 42.91,   49.91, 53.88   glas07.kvm.ext.asdg.ru PUPPETD CRITICAL 2017-01-13 00:28:02   lor notify-by-sms FILE_AGE CRITICAL:   /var/lib/puppet/state/state.yaml is 19821 seconds old and 26337 bytes    

我需要它看起来像:

wsd.qwd.qwd.kjqnwk.ru PUPPETD CRITICAL 2017-01-13 00:09:52   lor notify-by-sms FILE_AGE CRITICAL:   /var/lib/puppet/state/state.yaml is 2438046 seconds old and 19459 bytes   
zm-goas-04.asdg.net LOAD CRITICAL 2017-01-13 00:10:32   tech-lor notify-by-telegram CRITICAL - load average: 42.91,   49.91, 53.88   
glas07.kvm.ext.asdg.ru PUPPETD CRITICAL 2017-01-13 00:28:02   lor notify-by-sms FILE_AGE CRITICAL:   /var/lib/puppet/state/state.yaml is 19821 seconds old and 26337 bytes    

【问题讨论】:

  • 你能举一些实际数据作为例子吗?我很好奇some_text 到底长什么样。
  • 请用你的代码编辑

标签: bash sed split xargs


【解决方案1】:

使用xargs 一次处理n 记录的更简单方法,在您的情况下就是2

xargs -n2 <file
blablabla.ru some_text
blablabla.zu some_text
blablabla.au some_text
blablabla.ru some_text
blablabla.net some_text
blablabla.com some_text

根据man xargs 页面的-n 标志在哪里,

-n max-args, --max-args=max-args
      Use at most max-args arguments per command line.  Fewer than max-args arguments 
      will be used if the size (see the -s option) is exceeded, unless the
      -x option is given, in which case xargs will exit.

要替换回原始文件,请执行

xargs -n2 <file >tmpfile; mv tmpfile file

【讨论】:

  • @JamesBrown: 是的 :),最后 4k 很快就过去了
  • 很好的答案@Inian!我正在做某事,我只需要这个xargs -n
  • 是的,我给你投票了,看起来这让你超越了顶峰!恭喜。
  • 现在,下一个是 100k。 :D
  • @JamesBrown:这正是我所拥有的bash,黄金。击中它,然后真正获得生命:D
【解决方案2】:

Awk:

$ awk 'gsub(/([^ ]+ ){2}/,"&\n")' file
blablabla.ru some_text 
blablabla.zu some_text 
blablabla.au some_text 
blablabla.ru some_text 
blablabla.net some_text 
blablabla.com some_text

解释:

将每两次重复的[^ ]+(非空格字符串和一个空格)替换为自身(&amp;)和换行符\n。如果最后有剩余(即不匹配),则不会打印(除非您将gsub(...) 包装为{}1)。

【讨论】:

    【解决方案3】:

    尝试按此模式拆分:([-a-z0-9]+\.[a-z]+){1,} 用于域名。

    使用 GNU sed:

    sed -r 's/ +(([-a-z0-9]+\.[a-z]){1,}) */\n\1/g' file
    

    请注意,任何匹配一个空格后跟[-a-z0-9]、后跟.[a-z] 字符的字符串都将作为域名处理。

    【讨论】:

    • sed -r 's/ +(([-a-z0-9]+\.[a-z]){1,} ) */\n\1/g' 文件 - 不' t 工作 sed -r 's/ +(([-a-z0-9]+\.[a-z]){1,}) */\n\1/g' 文件 - 很好用 非常感谢你的帮助!
    • 很高兴为您提供帮助。请看What should I do when someone answers my question?
    • 能否请您更改此行的答案: sed -r 's/ +(([-a-z0-9]+\.[a-z]){1,} ) */ \n\1/g' 文件到这个: sed -r 's/ +(([-a-z0-9]+\.[a-z]){1,}) */\n\1/g' 文件?
    猜你喜欢
    • 2019-11-24
    • 2017-06-17
    • 1970-01-01
    • 2021-09-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多