4

分離する必要がある情報を含むファイルを処理するのに最適な方法について、少し懸念があります。

例として、ブロックに分割されたデータを含むログ ファイルを想像してください。各ブロックにはサブ ブロックのリストがあります。

ログファイルの例:

data
data
data
data 
   block 1 start
    -sub block 1 start
    --data x
    --data y
    -sub block 1 end
    -sub block 2 start
    --data x
    --data marked as good
    --data z
    -sub block 2 end
    block 1 end
    block 1 summary

    block 2 start
    -sub block 1 start
    .....
    -sub block 1 end
    ....
data
data
data

大きなファイル (さまざまな mb のテキスト) を解析し、ブロックを分離してから、各ブロックでサブブロック内の特定の行をチェックする効率的な方法を探しています。行がサブ ブロック内にある場合、サブ ブロックが属するブロックの開始行と終了行、および行が存在するサブ ブロックを保存します (ただし、データを持たない他のサブ ブロックは破棄します)。ファイルの最後に到達するまで。

結果がどのように見えるかの例:

block 1 start
-sub block 2 start
--data marked as good
-sub block 2 end
block 1 summary
.....

現在、私はこのアプローチを使用しています。ファイルを開き、ファイルを小さなサブセットに分割して操作します。情報を収集する 3 つのリストがあります。

List_general と呼ばれる最初のリストには、ログ ファイル全体の解析結果から、分離する必要があるブロックに関連しないものを除いたものが含まれます。基本的に、このステップの後、上記の例のように、「データ」行を除いたブロックのみが表示されます。これを行う間、「適切なデータ」文字列をチェックします。その文字列が少なくとも 1 回表示された場合は、処理して保存する必要があるデータがあることを意味します。それ以外の場合は、単に関数を終了します。

処理するデータがある場合は、list_general で 1 行ずつ進み、各ブロックとサブブロックの分離を開始します。最初のブロックから始めます (例を見ると、ブロック 1 からブロック 1 の要約が始まります)。

ブロックの終わりに到達したら (ブロック 1 の概要) ; 良好とマークされたデータがある場合は、解析を開始し、各サブブロックを調べて、どのサブブロックが良好なデータを持っているかを見つけます。

ブロックの場合と同様に、各サブブロックを1行ずつコピーし(基本的に、「サブブロック1の開始」から「サブブロック1の終了」まで1行ずつコピーを開始します)、そのサブに適切なデータがあるかどうかを確認しますブロック。そうであれば、リストの内容を最終リストにコピーします。そうでない場合は、リストを削除して次のサブブロックから始めます。

各セクションを解析するこのメカニズムは、リソースに関して非常に面倒で高価であることを私は知っています。これを行うための「より良い」方法があるかどうか疑問に思っていました。私はPythonにかなり慣れていないので、同様の問題へのアプローチがどのように直面するかわかりません。うまくいけば、ここの誰かが同様の問題を抱えていたので、この問題に直面する最善の方法を提案できます.

4

2 に答える 2

1

ログファイルの場合、ファイルを解析するときに気にしない行を捨てて、sqlite で役立つものを詰め込みます (モジュール sqlite3 を確認してください)。次に、ファイルの解析が完了したら、レポート/処理を行います。

Sqlite は、ディスクまたはメモリをストレージとして使用するように構成できるため、必要に応じて選択できます。

このアプローチが気に入っているのは、柔軟性があり、何かを 2 回解析する必要がないことです。

追加: これに似たものはありますか?

class Parser:
    def __init__(self, logfile):
        self.log = open(logfile)
        self.logentry = []
    def next(self):
        found = False
        for line in self.log:
            self.logentry.append(line)            
            if <block ends>:
                e = '\n'.join(self.logentry)
                self.logentry = []
                yield e
于 2013-02-04T01:02:00.793 に答える
0

block ... startと だけでブロックまたはサブブロックの境界を識別できる場合はblock ... end、読み取り時に各ブロックを処理し、必要な場所に結果を保存できます。

于 2013-02-04T01:09:50.373 に答える