Использование генератора с any()
для определения наличия в файле определенной строки:
if any(tgt_str in line for line in my_file):
print("string found")
else:
print("not found")
any()
содержит генератор и остановится на первой строке с целевой строкой и вернет результат. True
. Если строка отсутствует в файле, она будет отсканирована до конца и any()
вернет False
. См. Ниже очень краткое введение в генераторы и список понимания.
any(line for line in my_file if tgt_str in line)
Также работает. next()
также может быть использован, но он вызовет StopIteration
, если строка не найдена в файле.
Ниже приведено сохранение большей части вашего кода с некоторыми дополнениями.
runtime_l = '," Run Time'
start_tm = '," Start Time'
end_tm = '," End Time'
test_ID = ' Host Name: '
program_n = 'Test Program Name:'
prod_n = 'Product:'
class OneTime:
def __init__(self):
self.test_ID = 0
self.program_n = 0
self.prod_n = 0
def all_done(self):
return self.test_ID & self.program_n & self.prod_n
given_path = './test_logs'
for filename in os.listdir(given_path):
filepath = os.path.join(given_path, filename)
if not os.path.isfile(filepath):
continue
with open(filepath, 'r') as mfile:
if not any(runtime_l in ln for ln in mfile):
continue # Onto the next file...
# If we get this far, we know the runtime_l string is in
# the file. Proceed...
mfile.seek(0) # Back to start of file.
one_time = OneTime()
one_time_done = 0
print("File Name: ", filename)
print("File Name\\Path:", filepath)
for line in mfile:
line = line.rstrip()
if runtime_l in line:
# do something with the line
print(line)
elif start_tm in line:
# do something with the line
print(line)
elif end_tm in line:
# do something with the line
print(line)
elif not one_time_done:
if not one_time.test_ID and test_ID in line:
# do something with the line
one_time.test_ID = 1
print(line)
elif not one_time.program_n and program_n in line:
# do something with the line
one_time.program_n = 1
print(line)
elif not one_time.prod_n and prod_n in line:
# do something with the line
one_time.prod_n = 1
print(line)
one_time_done = one_time.all_done()
Роль класса OneTime
заключается только в размещении переменных, указывающих, была ли напечатана одна из напечатанных разовых строк. Вы можете использовать dict или просто переменные для отслеживания этого.
Оператор внутри функции any(...)
создает генератор , который создает элементы при повторении. Это как список, в котором вы получаете значения по одному, за исключением того, что он ленив. Элементы не хранятся внутри него, но читаются по мере необходимости, когда any()
запрашивает каждую строку, пока не достигнет строки, которая оценивается как True
.
Я знаю, что это кажется продвинутым, когда вы новичок в Python и пытаетесь учиться. Я дам краткое объяснение и предоставлю ссылку ниже, если вы хотите узнать больше.
В двух словах, я не уверен, что вы уже знакомы с "списком пониманий", но я Я уверен, что вы их видели. Они выглядят как циклы внутри квадратных скобок и создают элементы списка:
>>> li = [char for char in "abcdefghijklmnop"]
>>> li
['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p']
Это ^ создаст список символов, поскольку, когда вы перебираете строку, он генерирует один символ за раз.
Генератор выглядит как представление списка в круглых скобках (вместо квадратных скобок) и имеет тот же эффект, но символы не создаются до тех пор, пока их не попросят:
>>> gen = (char for char in "abcdefghijklmnop")
>>> gen
<generator object <genexpr> at 0x7f9a447aec10>
>>> next(gen)
'a'
Итак, назад до any()
. Он будет тянуть предметы из генератора, пока не увидит что-то, что оценивается как True
, а затем остановится. Он ищет только любое значение True в последовательности элементов.
>>> any([False, False, False, True])
True
>>>
>>> any("foo" in line for line in ["bar", "baz", "foo", "qux"])
True
Когда итерация достигает "foo"
, выражение "foo" in line
равно True
. Итерация на этом останавливается. Весь оператор в списке параметров any()
является генератором - иногда они не нуждаются в собственных скобках при использовании в качестве параметра.
Во многом так же, как и в предыдущем примере, генератор файлов будет читать по одной строке за раз до тех пор, пока any()
не будет удовлетворен - и это go не будет дальше. Таким образом, это несколько эффективно.
Вот базовый учебник c, если вы заинтересованы: https://www.csestack.org/python-fibonacci-generator/.