0

のような否定的な後読みしか見つかりません(?<!\\)
しかし、これは c++ と flex ではコンパイルできません。regex.h と flex の両方がこれをサポートしているようですか?

バックスラッシュが前にある場合、通常の引数文字列として><のような特別な文字を扱わなければならないシェルを実装しようとしています。|つまり、先頭に 0 または偶数の '\' が付いていない場合にのみ、特殊文字を特殊文字として扱います。

そうecho \\>aまたはecho abc>a直接出力する必要a
がありますが、echo \>a印刷する必要があります>a

どの正規表現を使用すればよいですか?
flex と yacc を使用して入力を解析しています。

4

2 に答える 2

1

Flex ルール ファイルでは\\、単一のバックスラッシュ「\」文字に一致させるために使用します。これは\、Flex でエスケープ文字として使用されるためです。

    BACKSLASH           \\
    LITERAL_BACKSLASH   \\\\
    LITERAL_LESSTHAN    \\\\<
    LITERAL_GREATERTHAN \\\\>
    LITERAL_VERTICALBAR \\\\|

私があなたを正しくフォローしている場合、あなたの場合、「\>」はリテラル「>」として扱われますが、「\\>」はリテラル「\」として扱われ、その後に特別なリダイレクトが続きます。通常の引数文字と特殊文字のリテラル バージョンの両方を受け入れる 1 つのルールを作成できるため、これを達成するために否定的な後読みや特に特別なことは必要ありません。

説明のために、引数/パラメーターには、' '、'\t'、および特殊な形式の '>'、'<'、'|' 以外の任意の文字を含めることができると仮定しましょう。引数のルールは次のようになります。

    ARGUMENT ([^ \t\\><|]|\\\\|\\>|\\<|\\\|)+

どこ:

[^ \t\\><|]' '、'\t' 以外の任意の 1 文字に
\\\\一致し、特殊文字は "\" の任意のインスタンス (つまり、リテラルのバックスラッシュ)
\\>に一致します ">" の任意のインスタンス (つまり、リテラルより大きい)
\\<に一致します<" (リテラルより小さい)
\\\|は、"\|" の任意のインスタンスに一致します。(つまり、文字通りの垂直バー/パイプ)

実際には...おそらくそのルールを次のように短縮できます。

    ARGUMENT ([^ \t\\><|]|\\[^ \t\r\n])+

どこ:

[^ \t\\><|]は、' '、'\t' 以外の任意の 1 文字と
\\[^ \t\r\n]一致し、特殊文字は、空白を除いて、入力内の '\' が前にあるすべての文字と一致します (これにより、すべての特殊文字が処理され、他のすべての文字のリテラル形式が可能になります)。 )

引数/パラメータにリテラルの空白を許可したい場合は、ルールをさらに短くすることができますが、\\.「\n」と一致する場合と一致しない場合があるため、ルールの後半を使用する場合は注意してください (つまり、末尾を食べます)。コマンド ターミネータ文字!)。

それが役立つことを願っています!

于 2013-03-28T15:06:12.637 に答える
0

文字のコンテキストがわからないため、コマンドラインから単一のエスケープ文字を簡単に抽出することはできません。最も単純なケースでは、次のことを考慮してください。

 LessThan:\<
 BackslashFrom:\\<

最初のもので<は、エスケープされた文字です。2番目のものではそうではありません。言語に引用符が含まれている場合 (ほとんどのシェルがそうであるように)、事態はさらに複雑になります。一度に 1 つのエンティティで、文字列を左から右に解析する方がはるかに優れています。(flexレクサーの作成とテストに時間を浪費するのをやめたので、私は自分自身を使用しますが、そうする教育的理由があるかもしれません。)

特別であってはならない特殊文字を本当に見つける必要がある場合は、それを検索してください (生のリテラルがない C++98 では、すべてのバックスラッシュをエスケープする必要があります)。

 regex: (\\\\)*\\[<>|]
     (An even number -- possibly 0 -- of \, then a \ and a <, > or |) 
 as a C string => "(\\\\\\\\)*\\\\[<>|]"
于 2013-03-06T18:53:26.470 に答える