【问题标题】:Extract 2 fields from string with search通过搜索从字符串中提取 2 个字段
【发布时间】:2020-06-16 08:03:00
【问题描述】:

我有一个包含多行数据的文件。这些字段并不总是在相同的位置/列中。我想搜索 2 个字符串,然后只显示字段和后面的数据。例如:

{"id":"1111","name":"2222","versionCurrent":"3333","hwVersion":"4444"}

{"id":"5555","name":"6666","hwVersion":"7777"}

我想返回以下内容:

"id":"1111","hwVersion":"4444"

"id":"5555","hwVersion":"7777"

我很挣扎,因为数据并不总是在同一个位置,所以我无法选择列号。我觉得我需要搜索 "id""hwVersion" 任何帮助都非常感谢。

【问题讨论】:

  • 解析 json 使用 json 感知工具。使用jq

标签: bash ubuntu unix awk sed


【解决方案1】:

完全同意@KamilCuk。更具体的

jq -c '{id: .id, hwVersion: .hwVersion}' <<< '{"id":"1111","name":"2222","versionCurrent":"3333","hwVersion":"4444"}'

输出:

{"id":"1111","hwVersion":"4444"}

不是指定的输出,而是有效的 JSON

更重要的是,您的输入可能应该逐条记录处理,我猜测带有“id”和“hwVersion”的两列输出会更容易解析:

cat << EOF | jq -j '"\(.id)\t\(.hwVersion)\n"'
{"id":"1111","name":"2222","versionCurrent":"3333","hwVersion":"4444"}
{"id":"5555","name":"6666","hwVersion":"7777"}
EOF

输出:

1111    4444
5555    7777

【讨论】:

    【解决方案2】:

    由于数据看起来像映射对象,甚至对应于 JSON 格式,如果您不介意使用 Python(JSON 附带)支持,应该这样做:

    import json
    
    def get_id_hw(s):
        d = json.loads(s)
        return '"id":"{}","hwVersion":"{}"'.format(d["id"], d["hwVersion"])
    

    我们将一行输入字符串放入s,并将其作为JSON解析到字典d中。然后我们返回一个格式化字符串,其中包含双引号 idhwVersion 字符串,后跟先前获得的 dict 中对应键的列和双引号值。

    我们可以用这些测试输入字符串和打印来试试这个:

    # These will be our test inputs.
    s1 = '{"id":"1111","name":"2222","versionCurrent":"3333","hwVersion":"4444"}'
    s2 = '{"id":"5555","name":"6666","hwVersion":"7777"}'
    
    # we pass and print them here
    print(get_id_hw(s1))
    print(get_id_hw(s2))
    

    但我们也可以遍历任何输入的行。

    如果你真的想使用awk,你可以,但它不是最强大和最合适的工具:

    awk '{ i = gensub(/.*"id":"([0-9]+)".*/, "\\1", "g")
           h = gensub(/.*"id":"([0-9]+)".*/, "\\1", "g")
           printf("\"id\":\"%s\",\"hwVersion\":\"%s\"\n"), i, h}' /your/file
    

    由于您提到位置未知并且假设它可以按任何顺序排列,我们使用一个正则表达式提取id,另一个提取hwVersion,然后我们以给定格式打印出来。如果这些值可能不是您的示例中的十进制数字,则 [0-9]+ 但需要反映这一点。

    如果文件中的条目位于sed

    sed -e 's#.*\("\(id\|hwVersion\)":"[0-9]\+"\).*\("\(id\|hwVersion\)":"[0-9]\+"\).*#\1,\3#' file
    

    它会查找两组"id""hwVersion",后跟:"&lt;DECIMAL_DIGITS&gt;"

    【讨论】:

      猜你喜欢
      • 2018-08-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-07-27
      • 2011-08-02
      • 2010-12-23
      • 1970-01-01
      相关资源
      最近更新 更多