0

SMS からの非構造化文字列からデータを抽出する必要があります

抽出する必要があるデータは次のとおりです

コード: これは 5 文字の英数字の文字列で、少なくとも 1 桁の数字が含まれている必要があります

身分証明書: これは 5 ~ 8 文字の数値文字列です。有効な形式は次のとおりです。

V55555555
E55555555
55555
55 555
E55 555 555
55 555 555
5 555 555
555 555

抽出する必要があるデータは、文字列内の任意の位置にある可能性があります。文字列を正規化し、重複するスペースを 1 つだけ置き換え、スペース、数字、文字以外のものをすべて削除しました

サンプル

1. resuelvete 15C20 Pdero Perez c.i. V55.555.555,
2. Pedro Perez resuelvete 15c20 55 555 555,
3. 15c20 Resuelvete 555555 Pedro Perez,
4. Resuelvete 555555 Pedro Perez 15c20

コード部分については、この正規表現を試しました:

$regex = '/([a-zA-Z0-9]{5})/i';

私もこれを試しました: $regex = '(?=.{5})(?=.*[A-Z])(?=.*[a-z])(?=.*\d)[a-zA-Z\d]';ここに表示されますが、機能していません (この正規表現を完全には理解していないと言わざるを得ません)

しかし、それは機能していません。文字列の最初の 5 文字を返します。この例で返す必要があります。15c20

身分証明書の部分については、次のことを試しました。

// This not work with spaces
$regex = "/(V|E)?(\d{5,8})/i";

// This not work without spaces
//This fail in first case returning only 7 digits instead of 8
// Also fails in cases  3 and 4,  does not match anything
$regex = "/(V|E)?(\d{1,2}? ?\d{3} ?\d{3})/i";
4

2 に答える 2

1

これはコード部分で機能するはずです(ここに少なくとも1つのアルファ文字が必要であると想定していることに注意してください。そうしないと、 ##### ケースのコードとIDの違いがわからないでしょう)

$code_pattern = '/\b(?=.*[\d].*\b)(?=.*[a-zA-Z].*\b)[a-zA-Z\d]{5}\b/';

この(?=....)構文は、正の先読みと呼ばれるものであることに注意してください。パターンのその部分の次の値がそのパターンに一致することをアサートするために使用されます (実際には一致内の文字としてカウントされません。

ID の部分については、シンプルに保ち (つまり、すべてのソリューションに適合する 1 つの正規表現を探しません)、preg_*関数でパターンの配列を使用します。

$identity_patterns = array(
    '/\b(V|E)[0-9]{8}\b/', // V########, E########
    '/\b[\d]{5}\b/', // #####
    '/\bE[\d]{2}\w[\d]{3}\w[\d]{3}\b/', // E## ### ###
    '/\b[\d]{1,3}\w[\d]{3}(\w[\d]{3})?\b/' // #{1,3} ### (###)?
);

そのすべてを単一の正規表現に統合することは確かに可能ですが、将来必要になった場合に読み取りと変更が非常に困難になります。

于 2013-01-10T00:23:00.527 に答える
0

[編集]\w次の正規表現パターンのすべてをに変更しました。これは、この回答を書いたときに忘れていたアンダースコア(_)文字も含まれている[a-zA-Z0-9]ためです。\w

コードには、次のようなものを使用できます

~\b(?=[a-zA-Z0-9]{5}\b)[a-zA-Z0-9]*\d[a-zA-Z0-9]*~

に割り込むことができます

\b                  # a word boundary (beginning of word in this case)
(?=                 # from here on...
    [a-zA-Z0-9]{5}  # 5 alphanumeric characters (a-z,A-Z,0-9)
    \b              # followed by a word boundary (end of word)
)
[a-zA-Z0-9]*        # 0 or more alphanumeric characters (a-z,A-Z,0-9)
\d                  # a decimal
[a-zA-Z0-9]*        # 0 or more alphanumeric characters (a-z,A-Z,0-9)

IDドキュメントの場合…提供した例以外に可能なグループ化がない場合は、次のようなものを使用できます。

'~(?<=\b|\bE|\bV)(?=[\d\ .]{5,10}\b)(
    \d{8}|
    \d{5}|
    \d{3}[\ .]\d{3}|
    \d{2}([\ .])\d{3}(\2\d{3})?|
    \d([\ .])\d{3}\4\d{3}
)~x'

そしてこれは言う

(?<=                        # preceded by
    \b|                     # a word boundary (beginning of word) or
    \bE|                    # a word boundary (beginning of word) and E or
    \bV                     # a word boundary (beginning of word) and V
)
(?=                         # from here on...
    [\d\ .]{5,10}           # a group consisting of only decimals, spaces and dots 
    \b                      # followed by a word boundary (end of word)
)
(                           # either:
    \d{8}|                  # an 8 digit number
    \d{5}|                  # a 5 digit number
    \d{3}[\ .]\d{3}|        # a 3 digit number, space or dot, a 3 digit number
    \d{2}([\ .])\d{3}       # a 2 digit number, space or dot, a 3 digit number
    (                       # optionally...
        \2                  # previous sign (space or dot)
        \d{3}               # a 3 digit number
    )?| 
    \d([\ .])\d{3}\4\d{3}   # a 1 digit number, space or dot, a 3 digit number, previous sign, a 3 digit number
)
于 2013-01-10T03:18:08.880 に答える