чтение ввода из текстового файла в словари с регулярным выражением в некоторых случаях - PullRequest
0 голосов
/ 26 апреля 2020

, поэтому я хотел бы из файла input.txt создать словарь

, например, вот пример файла input.txt

%. VAR %first=Billy
%. VAR %last=Bob
%. PRINT VARS
%. VAR %petName=Gato
%. VAR %street="1234 Home Street"
%. VAR %city="New York" 
%. VAR %state=NY 
%. VAR %zip=21236 
%. VAR %title=Dr.
%. PRINT VARS
%. FORMAT LM=5  JUST=LEFT
%. PRINT FORMAT

, поэтому VAR %varName=value

то есть в случае %first=Billy вы получите что-то вроде varDict = {"first": "Billy"} верно? Теперь я хочу знать, как это сделать через весь файл

Есть два словаря, которые мне нужно заполнить, один для переменных и один для FORMAT, который просто содержит значения, на самом деле ничего не делает на данный момент.

Что касается желаемого вывода, я думаю о чем-то подобном, я бы использовал функцию pprint как pprint.pprint(varDict , width=30) и вывел бы что-то вроде

{'first': 'Billy',
'last': 'Bob'}
{'city': 'New York',
'first': 'Billy',
 'last': 'Bob',
'petName': 'Gato',
'state': 'NY',
'street': '1234 Home Street',
'title': 'Dr.',
'zip': '21236'}
{'BULLET': 'o',
'FLOW': 'YES',
'JUST': 'LEFT',
'LM': '5',
'RM': '80'}

РЕДАКТИРОВАТЬ

Я собираюсь ввести код, который у меня сейчас есть для моего setFormatWIP.py

import re
import sys
import pprint

input=(sys.argv[1])

regexFormat = re.compile(r'^%\.\s*?FORMAT\s*?((?:(?:\w+)=(?:\w+)\s*)*)$', re.MULTILINE)
regexPrintFORMAT = re.compile(r'^%\.\s*PRINT\s(FORMAT)',re.MULTILINE)

file = open(input)
line = file.readline()
formatDict = dict()

while line:
    formatList = regexFormat.findall(line)
    printFormatObj = regexPrintFORMAT.search(line)
    if printFormatObj != None:
            pprint.pprint(formatDict, width=30)
    for param in formatList[0].split():
        splitParam = param.split('=')
        formatDict[splitParam[0]] = splitParam[1]

    line = file.readline()
file.close()

, который работает, я получаю эту ошибку

Traceback (most recent call last):
File "formatTest.py", line 19, in <module>
for param in formatList[0].split():
IndexError: list index out of range

Ответы [ 2 ]

1 голос
/ 26 апреля 2020

Если вы можете прочитать весь файл в строку, то следующее выражение должно извлечь все ваши переменные:

import re

var_pat = re.compile(r'^%\.\s*?VAR\s*?%(\w+)=(\w+|".*")\s*$', re.MULTILINE)
with open('input.txt') as f:
    text = f.read()

var_list = var_pat.findall(text)
print(var_list)
[('first', 'Billy'), ('last', 'Bob'), ('petName', 'Gato'), ('street', '"1234 Home Street"'), ('city', '"New York"'), ('state', 'NY'), ('zip', '21236')]

После этого вы можете сделать что-то подобное, чтобы получить свой словарь:

var_dict = dict()
for k, v in var_list:
    var_dict[k] = v

Для шаблона формата этот

format_pat = re.compile(r'^%\.\s*?FORMAT\s*?((?:(?:\w+)=(?:\w+)\s*)*)$', re.MULTILINE)
format = format_pat.findall(text)
print(format)

даст

['LM=5  JUST=LEFT']

Таким образом, вы можете получить свой дикт, выполнив:

format_dict = dict()
for param in format[0].split():
    split_param = param.split('=')
    format_dict[split_param[0]] = split_param[1]
print(format_dict)
{'LM': '5', 'JUST': 'LEFT'}

Вы можете узнать об этих регулярных выражениях по ссылке, опубликованной Мейс.


Редактировать

Чтобы получить желаемый результат - вместо ищите все VAR одновременно, просто переберите строки файла и попробуйте сопоставить каждый шаблон с этой строкой, затем обработайте эту строку в соответствии с ее соответствием:

var_dict = {}
with open('input.txt', 'r') as f:
    for line in f:
        m_var = var_pat.match(line)
        if m_var:
            var_dict[m_var.group(1)] = m_var.group(2)
            continue
        m_print = print_pat.match(line)
        if m_print:
            pprint.pprint(var_dict, width=30)
        .
        .
        .

Где print_pat - регулярное выражение шаблон, который соответствует линии PRINT VARS.
Подробнее о python функциях регулярного выражения, таких как re.match() , можно прочитать здесь .

1 голос
/ 26 апреля 2020

Ваш главный вопрос, кажется, об использовании регулярных выражений. Может быть, это поможет вам начать. re.findall довольно прост. Он возвращает список найденных значений для вашего выражения.

import re

lines = [
    "%. VAR     %first=Billy",
    "%. VAR     %last=Bob",
    "%. PRINT VARS",
    "%. VAR     %petName=Gato",
    "%. VAR     %street=\"1234 Home Street\"",
    "%. VAR     %city=\"New York\" ",
    "%. VAR     %state=NY ",
    "%. VAR     %zip=21236 ",
    "%. VAR     %title=Dr.",
    "%. PRINT VARS",
    "%. FORMAT LM=5  JUST=LEFT",
    "%. PRINT FORMAT",
    ]

# find VAR
re_VAR = r'^\%\.\s+VAR\s+%'
VAR_list = []
for line in lines:
    re_result = re.findall(re_VAR, line)
    if re_result:
        text = line.replace(re_result[0], '')
        text_parts = text.split('=')
        VAR_list.append({text_parts[0]: text_parts[1]})

print(VAR_list)

Результат

[{'first': 'Billy'}, {'last': 'Bob'}, {'petName': 'Gato'}, {'street': '"1234 Home Street"'}, {'city': '"New York" '}, {'state': 'NY '}, {'zip': '21236 '}, {'title': 'Dr.'}]

Вы можете проверить свои регулярные выражения здесь regex101.com

...