печать первого абзаца в python

у меня есть книга в текстовом файле, и мне нужно распечатать первый абзац каждого раздела. Я думал, что если я найду текст между nn и n, я смогу найти свой ответ. Вот мои коды, и это не сработало. Ты можешь сказать мне, в чем я ошибаюсь ?

lines = [line.rstrip('n') for line in open('G:aa.txt')]

check = -1
first = 0
last = 0

for i in range(len(lines)):
    if lines[i] == "": 
            if lines[i+1]=="":
                check = 1
                first = i +2
    if i+2< len(lines):
        if lines[i+2] == "" and check == 1:
            last = i+2
while (first < last):
    print(lines[first])
    first = first + 1

также я нашел код в stackoverflow, я тоже попробовал, но он просто напечатал пустой массив.

f = open("G:aa.txt").readlines()
flag=False
for line in f:
        if line.startswith('nn'):
            flag=False
        if flag:
            print(line)
        elif line.strip().endswith('n'):
            flag=True

я поделился образцом раздела этой книги в belown.

Я

РЕЛЬЕФ Земельный участок

II

ТЕМПЕРАМЕНТ ДИКИХ ЖИВОТНЫХ & Индивидуальность

то, что я пытаюсь сделать здесь, это найти строки верхнего регистра и поместить их все в массив. Затем, используя метод index, я найду первый и последний абзацы каждого раздела, сравнивая индексы этих элементов созданного мной массива.

вывод должен быть такой :

то, что я пытаюсь сделать здесь, это найти строки верхнего регистра и поместить их все в массив. Затем, используя метод index, я найду первый и последний абзацы каждого раздела, сравнивая индексы этих элементов созданного мной массива.

5 ответов


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

from itertools import groupby
with open("in.txt") as f:
    for k, sec in groupby(f,key=lambda x: bool(x.strip())):
        if k:
            print(list(sec))

С еще несколькими itertools foo мы можем получить разделы, используя заголовок верхнего регистра в качестве разделителя:

from itertools import groupby, takewhile

with open("in.txt") as f:
    grps = groupby(f,key=lambda x: x.isupper())
    for k, sec in grps:
        # if we hit a title line
        if k: 
            # pull all paragraphs
            v = next(grps)[1]
            # skip two empty lines after title
            next(v,""), next(v,"")

            # take all lines up to next empty line/second paragraph
            print(list(takewhile(lambda x: bool(x.strip()), v)))

который дал бы вам:

['There is a vast field of fascinating human interest, lying only just outside our doors, which as yet has been but little explored. It is the Field of Animal Intelligence.\n']
['What I am trying to do here is, find the uppercase lines, and put them all in an array. Then, using the index method, I will find the first and last paragraphs of each section by comparing the indexes of these elements of this array I created.']

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

разбить через петли:

from itertools import groupby  
from itertools import groupby
def parse_sec(bk):
    with open(bk) as f:
        grps = groupby(f, key=lambda x: bool(x.isupper()))
        for k, sec in grps:
            if k:
                print("First paragraph from section titled :{}".format(next(sec).rstrip()))
                v = next(grps)[1]
                next(v, ""),next(v,"")
                for line in v:
                    if not line.strip():
                        break
                    print(line)

текст:

In [11]: cat -E in.txt

THE LAY OF THE LAND$
$
$
There is a vast field of fascinating human interest, lying only just outside our doors, which as yet has been but little explored. It is the Field of Animal Intelligence.$
$
Of all the kinds of interest attaching to the study of the world's wild animals, there are none that surpass the study of their minds, their morals, and the acts that they perform as the results of their mental processes.$
$
$
WILD ANIMAL TEMPERAMENT & INDIVIDUALITY$
$
$
What I am trying to do here is, find the uppercase lines, and put them all in an array. Then, using the index method, I will find the first and last paragraphs of each section by comparing the indexes of these elements of this array I created.

знаки доллара-это новые строки, выход:

In [12]: parse_sec("in.txt")
First paragraph from section titled :THE LAY OF THE LAND
There is a vast field of fascinating human interest, lying only just outside our doors, which as yet has been but little explored. It is the Field of Animal Intelligence.

First paragraph from section titled :WILD ANIMAL TEMPERAMENT & INDIVIDUALITY
What I am trying to do here is, find the uppercase lines, and put them all in an array. Then, using the index method, I will find the first and last paragraphs of each section by comparing the indexes of these elements of this array I created.

всегда есть регулярное выражение....

import re
with open("in.txt", "r") as fi:
    data = fi.read()
paras = re.findall(r"""
                   [IVXLCDM]+\n\n   # Line of Roman numeral characters
                   [^a-z]+\n\n      # Line without lower case characters
                   (.*?)\n          # First paragraph line
                   """, data, re.VERBOSE)
print "\n\n".join(paras)

перейдите по коду, который вы нашли, строка за строкой.

f = open("G:\aa.txt").readlines()
flag=False
for line in f:
        if line.startswith('\n\n'):
            flag=True
        if flag:
            print(line)
        elif line.strip().endswith('\n'):
            flag=True

Кажется, что он никогда не устанавливает переменную флага как true.

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


Это должно работать, пока нет абзацев со всеми заглавными буквами:

    f = open('file.txt')

    for line in f:
    line = line.strip()
    if line:  
        for c in line:
            if c < 'A' or c > 'Z': # check for non-uppercase chars
                break
        else:        # means the line is made of all caps i.e. I, II, etc, meaning new section
            f.readline()  # discard chapter headers and empty lines
            f.readline()
            f.readline()
            print(f.readline().rstrip()) # print first paragraph

    f.close()

Если вы также хотите получить последний абзац, Вы можете отслеживать строку, которую видели в последний раз, которая содержала символы нижнего регистра, а затем, как только вы найдете строку в верхнем регистре (I, II и т. д.), указывающую на новый раздел, вы печатаете самую последнюю строку, так как это будет последний абзац в предыдущем разделе.


TXR решение

$ txr firstpar.txr data
There is a vast field of fascinating human interest, lying only just outside our doors, which as yet has been but little explored. It is the Field of Animal Intelligence.
What I am trying to do here is, find the uppercase lines, and put them all in an array. Then, using the index method, I will find the first and last paragraphs of each section by comparing the indexes of these elements of this array I created.

код firstpar.txr:

@(repeat)
@num

@title

@firstpar
@  (require (and (< (length num) 5)
                 [some title chr-isupper]
                 (not [some title chr-islower])))
@  (do (put-line firstpar))
@(end)

в основном мы ищем вход для соответствия шаблону для трехэлементного многострочного шаблона, который связывает num, title и firstpar переменные. Теперь этот шаблон, как таковой, может совпадать в неправильных местах, поэтому добавьте некоторые ограничивающие эвристики с require утверждение. Номер раздела должен быть короткой строкой, а строка заголовка должна содержать несколько прописных букв, и никаких строчных. Это выражение написано на языке TXR Lisp.

если мы получим совпадение с этим ограничением, то мы выведем строку, захваченную в firstpar переменной.