正規表現が正規表現ではないのはいつですか?


9

私は正式な言語の大学のコースで勉強しているので、正規表現を使用して素数を見つける方法を説明するこれらの魅力的な投稿(One Two)に出会いました。言ったように、正規表現ではなく、正規表現。正規表現は有限状態オートマトンによって計算された文字列に一致でき、素数を見つけることはFSAでは実行できないため、ブログの投稿に示されている正規表現は、文字列に一致するようにバックトラックするため、完全に正規表現ではありません。

私は正規表現を実際に使用したことがないので、今、私の質問:

「真の」正規表現から見ただけで、すぐに正規表現を認識するにはどうすればよいですか?

定義:正規表現では、正式な言語で定義されている概念を指します。正規表現とは、現代のプログラミング言語でサポートされている概念を意味します。regexp構文には、多くの場合、後方参照などの追加機能が含まれています。プログラミング言語で見られる正規表現は、正式な言語スタイルの正規表現よりも厳密に強力です。


5
Regexpは、正規表現の単なる省略形です。素数の計算は、正規表現ではなくPerlハックに基づいています。

1
かなりシンプルです。通常の言語では、連結、繰り返し、および代替が使用されます。エンジンがこれらと同等ではない何かをサポートするときはいつでも、それは非正規です。
Kilian Foth、2015

1
関連質問:123
ラファエル

@Yannisフェンスを超えてCSにジャンプすると、それは真実ではなくなります。プログラミング言語で見られるような正規表現は、(形式言語スタイルの)正規表現よりも厳密に強力であり、短い形式の「正規表現」は、慣例により(1つがどれだけ普及しているかはわかりません)後者ではなく前者に使用されます。種類。
ラファエル

@KilianFothしかし、それは本当に役立つ説明ではありません。たとえば、正規表現にパワーを増やさずに否定(または、ブール結合子の有限のセット)を追加できます。
David Richerby

回答:


13

tl; dr backrefs。

\1正規表現に(またはUnicodeをエスケープするために使用されない任意の数)があるとすぐに、それは正規表現ではありません。

Backrefsを使用すると、n> 1の場合、n回、b、(a+)b\1n回のa順に一致するものを照合できますa。これは通常の言語ではありません(非通常言語のポスターの子です)。

これは、後方参照が参照する任意の長さの文字列またはそれが含まれていることにマッチする正規表現が含まれるグループことが必要とほぼ十分である*かを+(A)B\1Aが有限言語である形式の正規表現の(私が見つけた)唯一の例外(それらを受け入れるすべての単語の列挙で置き換えることができます)。word1+Bword1|word2+Bword2Aは有限なので、等に変換できます。

ルックアラウンドグループは、正規表現の規則性を削除しません。A(?=B)Cは正規表現の断面AB.*ACあり、2つの正規言語の断面は正規です。負の先読みは、B.*(通常の言語の補数が正規である)の補数を使用することを除いて、似ています。後読みは全く同じであり、同様A(?<=B)Cの断面図であるAC.*BC


これは必要で十分ですか?(a)\1backrefを使用している間は、のように見えますが、aaそれは簡単です。また、先読みアサーションが非正規言語の認識に使用できるかどうかも疑問に思っています。
MSalters 2015

1
@MSalters:本当に技術的になりたい場合(a)\1は、正規表現ではなく、正規言語を認識します。
イェルクWミッターク
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.