【问题标题】:awk -cut how to delete second column with field separatorawk -cut 如何删除带有字段分隔符的第二列
【发布时间】:2018-02-16 13:45:42
【问题描述】:

我有一个 csv 文件,其数据显示如下

'&(||o||022344527||o||lonyfoe||o||Joe||o||Joe||o||Otieno

我正在尝试删除第二列。

输出:

'&(||o||lonyfoe||o||Joe||o||Joe||o||Otieno

有什么想法吗?

这是我迄今为止尝试过的

cut -d'||o||' -f2 --complement 

awk -F'||o||' '{
   for(n=1; n<=NF; n++){
      if(n!=NF)fmt="%s|"; else fmt="%s\n"
      if(n!=2)printf(fmt,$n)
   }
}' 

但它不起作用

【问题讨论】:

  • 我知道语言会进化,但我觉得将其称为“逗号分隔值”文件确实有点牵强:-/
  • 根据该术语的任何定义,这都不是 CSV,即使您将“CS”延伸为表示字符分隔而不是逗号分隔,值也由多字符串分隔,而不是由单个字符分隔.

标签: bash awk sed


【解决方案1】:

如果您的 Input_file 与所示示例相同,那么以下内容可能对您有所帮助:

awk '{sub(/\|\|o\|\|[0-9]+\|\|o\|\|/,"||o||")} 1'  Input_file

输出如下:

'&(||o||lonyfoe||o||Joe||o||Joe||o||Otieno

【讨论】:

    【解决方案2】:

    cut 分隔符只能是单个字符。在您的情况下,您可以使用|,以便由||o|| 分隔的每个值都被视为4 个字段(空、o、空、值)。第二列现在是 5-8 范围:

     cut -d'|' -f5-8 --complement
    

    【讨论】:

      【解决方案3】:

      添加了第二个非数字字段的示例行

      $ cat ip.txt
      '&(||o||022344527||o||lonyfoe||o||Joe||o||Joe||o||Otieno
      ijk||o||foobar||o||123||o||xyz
      

      使用perl的解决方案

      $ perl -lne '$,="||o||"; @f=split /\Q$,/; print @f[0,2..$#f]' ip.txt
      '&(||o||lonyfoe||o||Joe||o||Joe||o||Otieno
      ijk||o||123||o||xyz
      
      • $,="||o||" 设置print 的参数之间使用的分隔符
      • @f=split /\Q$,/ 获取由$, 指定的分隔符的数组,其中\Q 可用于转义正则表达式元字符。默认情况下,split 将作用于 $_ - 在这种情况下输入记录
      • print @f[0,2..$#f]打印必填字段,$,的值决定了数组元素之间使用的字符串

      【讨论】:

        【解决方案4】:

        这可能对你有用(GNU sed):

        sed 's/||o||/\n/g;s/[^\n]*\n//2;s/\n/||o||/g' file
        

        用换行符替换所有分隔符。删除第二个字段及其分隔符。用分隔符替换换行符。

        另一种选择:

        sed 's/||o||/\n/2;s/\(.*||o||\).*\n/\1/' file
        

        【讨论】:

          【解决方案5】:

          您可以尝试以下...

          sed -e 's/||o||/|/g' your-input-file | cut -d'|' -f1,3- | sed -e 's/|/||o||/g'
          
          • 第一个 sed 命令将原始分隔符转换为单个“|”使用 cut 命令会更好。 cut 命令似乎只需要单个字符分隔符。
          • cut 命令删除第二个字段,留下其余字段。使用“-f1,3-”是因为它可能与更多版本的“cut”更兼容。 “--complement”选项可能不适用于所有版本的 cut 命令。例如。在 Mac OSX 上。
          • 最后的 sed 命令只是将分隔符反转回原来的值

          希望有帮助。

          【讨论】:

          • 不错,但这假设没有其他字段包含字符 |... 用于格式化代码,选择该行并按 ctrl+k 或单击 {} 图标
          • 感谢有关代码格式的提示。完毕。是的,假设字段不包含“|”,您是正确的字符,这是个问题。
          【解决方案6】:

          你可以试试这个 sed

          sed 's/\(||o||[^|]*\)//1' infile
          

          【讨论】:

            猜你喜欢
            • 2013-05-03
            • 1970-01-01
            • 1970-01-01
            • 2012-11-01
            • 2014-04-27
            • 2018-05-21
            • 1970-01-01
            • 1970-01-01
            • 2020-05-24
            相关资源
            最近更新 更多