11

データが次のような .txt ファイル (Web サイトから事前に書式設定されたテキストとしてスクレイピング) があります。

B, NICKOLAS                       CT144531X       D1026    JUDGE ANNIE WHITE JOHNSON  
ANDREWS VS BALL                   JA-15-0050      D0015    JUDGE EDWARD A ROBERTS        

列の間の余分なスペースをすべて削除したいと思います (実際には、タブではなくスペースの数が異なります)。また、次のように、区切り文字(データ内にコンマがあるため、タブまたはパイプ)に置き換えたいと思います。

ANDREWS VS BALL|JA-15-0050|D0015|JUDGE EDWARD A ROBERTS

周りを見回して、最適なオプションは正規表現またはシュレックスを使用して分割することであることがわかりました。2 つの類似したシナリオ:

4

6 に答える 6

7

What about this?

your_string ='ANDREWS VS BALL                   JA-15-0050      D0015    JUDGE EDWARD A ROBERTS'
print re.sub(r'\s{2,}','|',your_string.strip())

Output:

ANDREWS VS BALL|JA-15-0050|D0015|JUDGE EDWARD A ROBERTS

Expanation:

I've used re.sub() which takes 3 parameter, a pattern, a string you want to replace with and the string you want to work on.

What I've done is taking at least two space together , I 've replaced them with a | and applied it on your string.

于 2016-04-30T17:32:52.413 に答える
7

You can apply the regex '\s{2,}' (two or more whitespace characters) to each line and substitute the matches with a single '|' character.

>>> import re
>>> line = 'ANDREWS VS BALL                   JA-15-0050      D0015    JUDGE EDWARD A ROBERTS        '
>>> re.sub('\s{2,}', '|', line.strip())
'ANDREWS VS BALL|JA-15-0050|D0015|JUDGE EDWARD A ROBERTS'

Stripping any leading and trailing whitespace from the line before applying re.sub ensures that you won't get '|' characters at the start and end of the line.

Your actual code should look similar to this:

import re
with open(filename) as f:
    for line in f:
        subbed = re.sub('\s{2,}', '|', line.strip())
        # do something here
于 2016-04-30T17:33:16.273 に答える
5
s = """B, NICKOLAS                       CT144531X       D1026    JUDGE ANNIE WHITE JOHNSON  
ANDREWS VS BALL                   JA-15-0050      D0015    JUDGE EDWARD A ROBERTS
"""

# Update
re.sub(r"(\S)\ {2,}(\S)(\n?)", r"\1|\2\3", s)
In [71]: print re.sub(r"(\S)\ {2,}(\S)(\n?)", r"\1|\2\3", s)
B, NICKOLAS|CT144531X|D1026|JUDGE ANNIE WHITE JOHNSON  
ANDREWS VS BALL|JA-15-0050|D0015|JUDGE EDWARD A ROBERTS
于 2016-04-30T17:48:08.600 に答える
3

あなたのデータは「テキストテーブル」形式のようです。

最初の行を使用して各列の開始点と長さを把握し (手動で、または可能性のある列を決定する正規表現を使用してスクリプトを記述します)、次にファイルの行を反復処理するスクリプトを記述し、行を次のようにスライスすることをお勧めします。列セグメントを作成し、各セグメントにストリップを適用します。

正規表現を使用する場合は、列の数追跡し、特定の行に予想される列数を超える (または残りの数とは異なる) 場合にエラーを発生させる必要があります。列の値に 2 つ以上のスペースがある場合、2 つ以上のスペースでの分割は中断されます。これは完全に可能であるだけでなく、可能性もあります。 このようなテキスト テーブルは、正規表現で分割されるようには設計されていません。列のインデックス位置で分割されるように設計されています。

データの保存に関しては、csv モジュールを使用して csv ファイルに書き込み/読み取りを行うことができます。これにより、区切り文字を指定するよりも、文字の引用とエスケープをより適切に処理できます。列の 1 つに|値として文字が含まれている場合、エスケープまたは引用符で囲まれたリテラルを処理する方法でデータをエンコードしていない限り、読み取り時に出力が壊れます。

上記のテキストを解析すると、次のようになります (理解しやすいように、従来の形式の代わりにブラケットを使用してリスト内包表記を入れ子にしました)。

cols = ((0,34),
        (34, 50),
        (50, 59),
        (59, None),
        )
for line in lines:
    cleaned = [i.strip() for i in [line[s:e] for (s, e) in cols]]
    print cleaned

次に、次のように記述できます。

import csv
with open('output.csv', 'wb') as csvfile:
    spamwriter = csv.writer(csvfile, delimiter='|',
                            quotechar='"', quoting=csv.QUOTE_MINIMAL)
    for line in lines:
        spamwriter.writerow([line[col_start:col_end].strip()
                             for (col_start, col_end) in cols
                             ])
于 2016-04-30T18:00:02.317 に答える
3

列を区切るスペースが少なくとも 2 つあることを考慮して、これを使用できます。

lines = [
'B, NICKOLAS                       CT144531X       D1026    JUDGE ANNIE WHITE JOHNSON  ',
'ANDREWS VS BALL                   JA-15-0050      D0015    JUDGE EDWARD A ROBERTS        '
]

for line in lines:
    parts = []
    for part in line.split('  '):
        part = part.strip()
        if part:  # checking if stripped part is a non-empty string
            parts.append(part)
    print('|'.join(parts))

入力の出力:

B, NICKOLAS|CT144531X|D1026|JUDGE ANNIE WHITE JOHNSON
ANDREWS VS BALL|JA-15-0050|D0015|JUDGE EDWARD A ROBERTS
于 2016-04-30T17:27:47.857 に答える
0

このライブラリはこれをうまく解決できるようです: http://docs.astropy.org/en/stable/io/ascii/fixed_width_gallery.html#fixed-width-gallery

印象的...

于 2016-05-12T21:13:59.663 に答える