非常复杂的正则表达式

Mal*_*ala 6 regex encryption

我一直在努力写这个我需要的正则表达式.基本上,我有一个由两种不同类型的数据组成的长字符串:

  1. [A-f0-9] {32}
  2. [A-ZA-Z0-9 =] {X}

问题是,x在特定实例中只是常量:如果在一种情况下,它碰巧是12,那么对于那个特定的数据集它将是12,但是下次我运行正则表达式时它可能需要是15或45例如.我在每个类型(2)之间有一个不可预测的类型(1).我的目标是"收获"所有类型(2)的数据.

例如,我可以使用以下形式的字符串:

[a-f0-9]{192}
[a-zA-Z0-9=]{11}
[a-f0-9]{96}
[a-zA-Z0-9=]{11}
[af-0-9]{160}
[a-zA-Z0-9=]{11}
Run Code Online (Sandbox Code Playgroud)

(所有放在一起没有划界).我需要它返回一个由[a-zA-Z0-9 =]字符集的33个字符组成的字符串.事实上每个子串中的字符数在实例中是恒定的(在上面的情况下它是11,但它可能很容易已经是13)是至关重要的,因为它包含较小的字符集,否则它将是不可能知道一个字符串的开头和另一个字符串的结束.

我一直试图让它工作近一个月,我接近撕裂了我的头发.我不是特别擅长正则表达式......

示例数据:

3c21e03a10b9415fb3e1067ea75f8205
c8dc9900a5089d31e01241c7a947ed7e
d5f8cd6bb86ebef6d7d104c84ae6e8a7
e23c99af9c9d6d0294d8b51094c39021
4bb4af7e61760735ba17c29e8f542a66
875da91e90863f1ddb7e149297fc59af
cf5de951fb65d06d2927aab7b9b54830
e2d935616a54c381c2f38db3731d5a37
SGVsbG8gbXk
6dd11d15c419ac219901f14bdd999f38
0ad94e978ad624d15189f5230e5435a9
2dc19fe95e583e7d593dd52ae7e68a6e
465ffa6074a371a8958dad3ad271181a
23310939b981b4e56f2ecee26f82ec60
fe04bef49be47603d1278cc80673b226
gbmFtZSBpcy
3c21e03a10b9415fb3e1067ea75f8205
c8dc9900a5089d31e01241c7a947ed7e
d5f8cd6bb86ebef6d7d104c84ae6e8a7
e23c99af9c9d6d0294d8b51094c39021
BvbGl2ZXIga
4bb4af7e61760735ba17c29e8f542a66
875da91e90863f1ddb7e149297fc59af
cf5de951fb65d06d2927aab7b9b54830
e2d935616a54c381c2f38db3731d5a37
G9vcmF5IQ==
Run Code Online (Sandbox Code Playgroud)

我想提取"SGVsbG8gbXkgbmFtZSBpcyBvbGl2ZXIgaG9vcmF5IQ ==".

Mar*_*ers 8

这是你的幸运日!这个问题一般无法解决,但我相信以下内容几乎总能为现实生活中的典型数据提供正确答案:

<?php

$s = '
3c21e03a10b9415fb3e1067ea75f8205
c8dc9900a5089d31e01241c7a947ed7e
d5f8cd6bb86ebef6d7d104c84ae6e8a7
e23c99af9c9d6d0294d8b51094c39021
4bb4af7e61760735ba17c29e8f542a66
875da91e90863f1ddb7e149297fc59af
cf5de951fb65d06d2927aab7b9b54830
e2d935616a54c381c2f38db3731d5a37
SGVsbG8gbXk
6dd11d15c419ac219901f14bdd999f38
0ad94e978ad624d15189f5230e5435a9
2dc19fe95e583e7d593dd52ae7e68a6e
465ffa6074a371a8958dad3ad271181a
23310939b981b4e56f2ecee26f82ec60
fe04bef49be47603d1278cc80673b226
gbmFtZSBpcy
3c21e03a10b9415fb3e1067ea75f8205
c8dc9900a5089d31e01241c7a947ed7e
d5f8cd6bb86ebef6d7d104c84ae6e8a7
e23c99af9c9d6d0294d8b51094c39021
BvbGl2ZXIga
4bb4af7e61760735ba17c29e8f542a66
875da91e90863f1ddb7e149297fc59af
cf5de951fb65d06d2927aab7b9b54830
e2d935616a54c381c2f38db3731d5a37
G9vcmF5IQ==
';
$s = preg_replace('/\r?\n/', '', $s);

for ($i = 1; $i < 20; ++$i) {
    $pattern = "/^(([a-f0-9]{32})+([a-zA-Z0-9=]{{$i}})?)+$/";
    if (preg_match($pattern, $s)) {
        $pattern = "/(?:[a-f0-9]{32})+([a-zA-Z0-9=]{{$i}})/";
        $matches = array();
        preg_match_all($pattern, $s, $matches);
        print_r(join('', $matches[1]));
        break;
    }
}
Run Code Online (Sandbox Code Playgroud)

这种情况下的输出:

SGVsbG8gbXkgbmFtZSBpcyBvbGl2ZXIgaG9vcmF5IQ==
Run Code Online (Sandbox Code Playgroud)

我相信代码可以改进,但我相信你很高兴得到一些有用的东西.我认为这与你上面描述的"火箭筒"方法类似,但我老实说不认为有更好的方法.另请注意,首先要从小猜测开始,以尽量减少错误匹配的可能性.正则表达式中的术语顺序对于增加在可能有多个选择时正确选择的可能性也是很重要的(尝试最先匹配,贪婪,然后最简单的匹配,只有当失败时).


Eri*_*ier 5

我不相信正则表达式是解决此问题的正确工具.

困扰我的一件事是范围[a-f0-9]包含在[a-zA-Z0-9 =]范围内,并且因为没有分隔符并且记录的长度是可变的,所以两者之间的边界记录看起来很模糊.

您可能有一个启发式方法,通过在数据中查找模式来确定记录的开始和结束位置,然后您可以使用此模式应用正则表达式,但正则表达式不太可能帮助您在第一名.