2017-06-23 7 views
1

0または0の直後に3.1415926535897932384626433832795028841971のような数字の文字列を分割しようとしています。しかし、私は各グループの後に0を保持したいと思います。空白の文字列でlookahead/lookbehindの文字列を分割する

Iが正の後読み文字列を離れて分割しようとした、空例えば、ストリング10203040506070809011

['10', '20', '30', '40', '50', '60', '70', '80', '90', '11'] 

に分割されるべきであり、文字列3.1415926535897932384626433832795028841971

['3.14159265358979323846264338327950', '28841971'] 

に分割されなければなりません文字列:

import re 
p = '(?<=0+)' 

re.search(p, '102030405') 
><_sre.SRE_Match object; span=(2, 2), match=''> 

'102030405'.split(p) 
>['102030405'] 

たとえパターンが一致していても、文字列をまったく分けることはありません。

0に基づいて文字列を分割し、最初のカップルの文字列の後に0を追加してみましたが、複雑で非効率なようです。

空の文字列の先読みまたはルックバックに基づいて文字列を分割する方法はありますか?私は数字だけではなく、一般的なケースについて尋ねています。たとえば、amまたはpmを失うことなく3:18am5:19pm10:28amを別々の時間に分割し、配列['3:18am', '5:19pm', '10:28am']を取得する場合は、どうすればこのようになるでしょうか?

+0

使用しているPythonのバージョンは何ですか? 're.search(p、 '102030405')' –

+0

Python 3.6.1を使用するとエラーが発生します – victor

+0

'' 10020''をどのように分割したいですか? '' ['100'、 '20'] ''、 '' ['10'、 '020'] ''? – randomir

答えて

1

re.findallでこの単純な正規表現で十分です:

l = re.findall(r'[.1-9]+(?:0+|$)', s) 

注:

  • findall戻りすべての非を重複文字列のパターンに一致します。リストはです。我々は最終的に

  • ゼロ別の一致として捕捉されるべきではない数字の最も長い文字列(又はドット)は、少なくとも1つのゼロで終わる、または文字列の末尾をしたい各マッチのため

  • (したがって(?:...)もし第例えば同様

>>> re.findall(r'[\d:]+(?:am|pm|$)', '3:18am5:19pm10:28am') 
['3:18am', '5:19pm', '10:28am'] 

先読み/後読み魔法の必要はありません、または非GREエディマッチング。

1

使用re.findall

l = re.findall(r'(?<![^0])[1-9.]+0*', s) 

キーは二重否定を使用することである:ゼロ(先行ゼロまたは文字列の先頭と一致する)

ないと に先行しません
1

Python splitには、幅がゼロでない一致が必要です。

あなたのマッチを取得するには、この正規表現でfindallを使用することができます。

>>> print re.findall(r'([\d.]+?(?:0+|$))', '10203040506070809011') 
['10', '20', '30', '40', '50', '60', '70', '80', '90', '11'] 

>>> print re.findall(r'([\d.]+?(?:0+|$))', '3.1415926535897932384626433832795028841971') 
['3.14159265358979323846264338327950', '28841971'] 

([\d.]+?(?:0|$))0または行の終わりで終わる数字またはドットと一致します。


更新:

私はあなたの編集した質問から注意してください、あなたは、分割操作のためにゼロ幅の正規表現パターンを使用する汎用ソリューションを探しているというコメントが。

非常に便利なregex moduleをPythonにインストールすることをお勧めします。このモジュールのバージョン1はPCREの機能のほとんどを提供し、デフォルトのreモジュールをはるかに上回ります。

インストールは簡単です。ただ、上記のリンクからのtar gzipファイルをダウンロードして実行します。

sudo python setup.py install 

あなたはtarファイルを抽出した後に取得するディレクトリの内側から。 (インストールプロセスではほとんど無視されます)。 regexはちょうどこのコードを使用してインストールされると

>>> import regex 

>>> regex.DEFAULT_VERSION = regex.VERSION1 

>>> regex.split(r'(?<=[ap]m)(?=.)', '3:18am5:19pm10:28am') 
['3:18am', '5:19pm', '10:28am'] 

>>> print regex.split(r'(?<=0)(?=[1-9])', '10203040506070809011') 
['10', '20', '30', '40', '50', '60', '70', '80', '90', '11'] 

>>> print regex.split(r'(?<=0)(?=[1-9])', '3.1415926535897932384626433832795028841971') 
['3.14159265358979323846264338327950', '28841971'] 

>>> print regex.split(r'(?<=0)(?=[1-9])', '10020') 
['100', '20'] 
+1

先読みや見た目がなければ私が解決できない状況はないのは本当ですか?私の元の質問は、空の文字列を特定の先読み/見た目と一致させることでしたが、今私はそれについて考えて、それが唯一の選択肢である場合を想像することはできません。 – victor

+1

はい、そうです。この例のようにregexを修正することで、常に問題を解決することができます。マッチ/スプリットのための空白またはゼロ幅のマッチを許可することは、Pythonにとって確かにいいことでした。 – anubhava

関連する問題