[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)

我需要解析这些数据和IN。/ OUT: /INOUT: 取决于所给的三个词组。

regex1 = r"\[2\]\s*IN:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
regex2 = r"\[2\]\s*OUT:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
regex3 = r"\[2\]\s*IN:\s*(\S+?)\s*INOUT:\s*(\S+?)\s.*?.\s*OUT:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"

My output should be:

IN_r1 2.12 INOUT_r1 3.52
IN_r3 2.12 INOUT1_r3 3.52 OUT_r3 2.42 INOUT2_r3 2.62
OUT_r2 2.42 INOUT_r2 2.62
IN_r3 2.12 INOUT1_r3 3.52 OUT_r3 2.42 INOUT2_r3 2.62
IN_r1 2.12 INOUT_r1 3.52 
OUT_r2 2.42 INOUT_r2 2.62
IN_r3 2.12 INOUT1_r3 3.52 OUT_r3 2.42 INOUT2_r3 2.62

The code I tried:

import re
regex1 = r"\[2\]\s*IN:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
regex2 = r"\[2\]\s*OUT:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
regex3 = r"\[2\]\s*IN:\s*(\S+?)\s*INOUT:\s*(\S+?)\s.*?.\s*OUT:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
data = "
[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
lines = re.split("\[2]",data)
for line in lines:
    if re.search(regex1,data):
        tracks = re.findall(regex1,data,re.DOTALL)
        for track in tracks:
            input,inout = (float(z) for z in track)
            with open("checked_ant.txt",'a') as a:
                print("IN_r1",input,"INOUT_r1",inout,file=a)
    elif re.search(regex2,data):
        tracks = re.findall(regex2,data,re.DOTALL)
        for track in tracks:
            output,inout = (float(z) for z in track)
            with open("checked_ant.txt",'a') as a:
                print("OUT_r2",output,"INOUT_r2",inout,file=a)
    elif re.search(regex3,data):
        tracks = re.findall(regex3,data,re.DOTALL)
        for track in tracks:
            input,inout1,output,inout2 = (float(z) for z in track)
            with open("checked_ant.txt",'a') as a:
                print("IN_r3",input,"INOUT1_r3",inout1,"OUT_r3",output,"INOUT2_r3",inout2,file=a)

我面临的问题是,它不能正确地进行解析,而且对于每个以[2]开头的子数据,它不能得到匹配。

5 个评论
你是否真的想see你在上面标记的输出,还是你想提取某些数据? 如果是后者,请告诉我们这些数据应该是什么样子,例如在一个列表或字典中。
你关心它是来自IN还是OUT,还是INOUT?
abcd
yes it should be from the specific IN or OUT or INOUT
abcd
@TimBiegeleisen 提取的数据需要以这种形式打印出来
但你的预期输出不包含这样的信息。它只是说你需要提取所有的数字。
python
regex
parsing
abcd
abcd
发布于 2021-07-14
2 个回答
Lei Yang
Lei Yang
发布于 2021-07-14
已采纳
0 人赞同

虽然我觉得这个要求很奇怪(提供了regex,不能改变),但我得到了预期的结果。你可以试试。

import re
s = '''[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)'''
r1 = r"\[2\]\s*IN:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
r2 = r"\[2\]\s*OUT:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
r3 = r"\[2\]\s*IN:\s*(\S+?)\s*INOUT:\s*(\S+?)\s.*?.\s*OUT:\s*(\S+?)\s*INOUT:\s*(\S+?)\s"
def g(reg, s, n):
    return float(re.search(reg, s).group(n))
paras = s.split('\n\n')
for p in paras:
    if re.search(r1, p):
        print(f'IN_r1 {g(r1, p, 1)} INOUT_r1 {g(r1, p, 2)}')
    if re.search(r2, p):
        print(f'OUT_r2 {g(r2, p, 1)} INOUT_r2  {g(r2, p, 2)}')
    if re.search(r3, p):
        print(
            f'IN_r3 {g(r3, p, 1)} INOUT1_r3 {g(r3, p, 2)} OUT_r3 {g(r3, p, 3)} INOUT2_r3 {g(r3, p, 4)}')

为了获得更好的性能,你可以只匹配一次,并获得分组。以r1为例。

gs = re.search(r1, p)
if gs:
    print(f'IN_r1 {gs.group(1)} INOUT_r1 {gs.group(2)}')
    
abcd
谢谢你的回答。我的导师告诉我,要严格遵守我的代码中提到的重码。从IN,OUT,INOUT中提取的浮点数需要存储在if-else条件中的input,output,inout。我所面临的问题是,对于每一个以[2]开始的部分我想用上述3个词组进行解析和检查,但不知为何,它只是跳过了一些以[2]开头的部分。
如果他为你写的是搜索结果(最困难的部分),为什么他不写其余的代码呢? 我在你的搜索结果中没有看到匹配float的地方。
abcd
这方面没有任何头绪。我希望他能在这方面更加灵活。但他说,这种regex格式是进一步加强的必要条件。
abcd
是的,这给出了我所需要的输出!我只是想问一下,{g(reg,s,n)}中的匹配数据是以浮动值还是字符串的形式存储的?如果我必须以浮动值存储它们,我需要做什么?
return float(re.search(reg, s).group(n)) updated.
Tim Biegeleisen
Tim Biegeleisen
发布于 2021-07-14
0 人赞同

这里有一个regex查找所有的方法。 我们可以先搜索每一个以[2]开头的多行部分,然后找到所有的数据编号,并在一行中打印出来。

import re
inp = """[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
[2]   OUT: 2.42   INOUT: 2.62  (Output)
[2]   IN: 2.12    INOUT: 3.52  (Input)
      OUT: 2.42   INOUT: 2.62  (Output)"""
first  = 1
for m in re.finditer(r'\[\d+\](.*?)(?=\[\d+\]|$)', inp, flags=re.DOTALL):
    nums = re.findall(r'\d+(?:\.\d+)?', m.group(1))
    if first != 1:
        print('')
    print(' '.join(nums), end='')
    first = 0

This prints:

2.12 3.52
2.12 3.52 2.42 2.62
2.42 2.62