1

.ics ファイルから複数の順序付けられたプロパティ値 (DTSTART、DTEND、SUMMARY) を選択できるものを構築しようとして、しばらくこの正規表現をいじっていました。他のオプション (一度に 1 行ずつ読み取ってスキャンするなど) はありますが、すべてを処理できる単一の正規表現を作成したいと考えていました。

サンプルパール

# There has got to be a better way...
my $x1 = '(?:^DTSTART[^\:]*:(?<dts>.*?)$)';
my $x2 = '(?:^DTEND[^\:]*:(?<dte>.*?)$)';
my $x3 = '(?:^SUMMARY[^\:]*:(?<dtn>.*?)$)';
my $fmt = "$x1.*$x2.*$x3|$x1.*$x3.*$x2|$x2.*$x1.*$x3|$x2.*$x3.*$x1|$x3.*$x1.*$x2|$x3.*$x2.*$x1";

if ($evts[1] =~ /$fmt/smo) {
printf "lines:\n==>\n%s\n==>\n%s\n==>\n%s\n", $+{dts}, $+{dte}, $+{dtn};
} else {
print "Failed.\n";
}

サンプルデータ

BEGIN:VEVENT
UID:0A5ECBC3-CAFB-4CCE-91E3-247DF6C6652A TRANSP
:OPAQUE
SUMMARY:Gandalf_flinger1
DTEND:20071127T170005
DTSTART,lang=en_us:20071127T103000
DTSTAMP:20100325T003424Z
X-APPLE-BUSYEVENTS:20100325BUSYEVENTS :
0

サンプル出力

行:
==>
20071127T103000
==>
20071127T170005
==>
Gandalf_flinger1

4

4 に答える 4

2

CPAN はあなたの友達です:

vファイル

iCal パーサー

vFile 形式 (些細なファイル以外) のパーサーを使用しないと、髪の毛がハゲるまで引き抜くことになります。これに対する正規表現は非常に困難です。

于 2010-04-12T00:36:48.260 に答える
1

3 つの正規表現を OR を使用して 1 つの大きなパターンに並べ替える代わりに、3 つのパターンを個別にテストしてみませ$んか?

my $x1 = qr/(?:^DTSTART[^:]*:(?<dts>.*?)$)/smo;
my $x2 = qr/(?:^DTEND[^:]*:(?<dte>.*?)$)/smo;
my $x3 = qr/(?:^SUMMARY[^:]*:(?<dtn>.*?)$)/smo;

if ($evts[1] =~ $x1 and $evts[1] =~ $x2 and $evts[1] =~ $x3)
{
    # ...
}

(x 変数自体をパターンに変換し、文字クラスの不要なエスケープを削除しました。)

于 2010-04-12T00:07:14.387 に答える
0

3 つの正規表現と追加のロジックを使用することをお勧めします。この問題は、正規表現には適していません。

于 2010-04-11T22:56:40.340 に答える
0

それは醜いです...「より良い方法」は、一度に各プロパティを一致させることだと思います。

于 2010-04-11T22:59:22.503 に答える