2016-11-29 8 views
1

私は与えられた正規表現に基づいてファイルをフィルタリングする汎用シェルスクリプトを書いています。名前がタイムスタンプであるフィルタフォルダ - findユーティリティによるパターンマッチングと正規表現のマッチング

私のシェルスクリプト:例1で

files=$(find $path -name $regex) 

(フィルタには)、私はディレクトリ内のフォルダをフィルタリングする、フォルダの名前は以下の形式である:

20161128-20:34:33:432813246 
YYYYMMDD-HH:MM:SS:NS 

正しい正規表現に到着できません。

正規表現'*data.txt'を使用して、フォルダ内のファイルのパスを取得できました。そのファイル内のファイルの名前はわかっています。

しかし、それは私にファイルのフルパスを与え、私がしたいことは、単純である

/path/20161128-20:34:33:432813246/data.txt 

のようなもの:

/path/20161128-20:34:33:432813246 

私の要件

の正しい正規表現を識別するのに私を助けてください

注:

私は

files=$(find $path -name $regex) 

後にデータを処理する方法を知っている。しかしスクリプトは多くのユースケースのための汎用的である必要があるため、私は渡す必要がある正しい正規表現を必要としています。

+3

これはワイルドカードの正規表現ではありません。 –

+0

あなたは、私が必要とするのはワイルドカードで正規表現ではないということですか? – ADPK

+0

いいえ、私はあなたが 'find'で正規表現を使うことができないことを意味しました。ワイルドカードパターンのみ(ワイルドカードを使用) –

答えて

3
  • Per POSIXfind-name-path予備選挙(テスト)patternsを使用(別名ワイルドカード式、グロブ)t oファイル名とパス名を一致させます(パターンと正規表現は遠く離れていますが、その構文と機能は大きく異なります。要するに、パターンは構文的に単純ですが、はるかに強力です)。入力パスの

    • -nameベース名(単なるファイル名)に対してパターンに一致する部分のみ
    • -path
    • 全体パス名(フルパス)
  • に対してパターンと一致します

    GNUとBSD/macOSの両方find非標準の拡張子

    それらは大文字と小文字を区別せずにと一致していることを除いて、(パターンに基づいて)その標準に準拠対応ように動作
    • -iname-ipath、。 正規表現(正規表現)によってパス名を一致させるため
    • -regex-iregex試験。
      • 警告:どちらの実装は、から選択するには、少なくとも2つの正規表現の方言をご利用いただけます(-EのサポートはBSD find拡張正規表現を活性化し、GNU find-regextypeにはいくつかの方言から選択することができますが、どの2つの方言が正確ではありません2つの実装間で同じ - 血みどろの詳細については下を参照してください

。フォルダ名に

固定幅の命名スキーム以下、パターンが働くだろう:もちろん

pattern='[0-9][0-9][0-9][0-9][0-9][0-9][0-9]-[0-9][0-9]:[0-9][0-9]:[0-9][0-9]:[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]' 

をあなたは偽陽性を期待していない場合は、ショートカットを取ることができます:

pattern='[0-9]*-[0-9]?:[0-9]?:[0-9]?:[0-9]*' 

*?は、正規表現とは異なり、前述の式を参照複製シンボル(数量)ではありませんどのように注意が、それ自体では、任意の文字列(*)または任意の1文字(?)を表します。

我々はすべて一緒にそれを置く場合:

files=$(find "$path" -type d -name "$pattern") 
  • これは、特に、パス内の任意の空白を保持するために、不要なシェル拡張から値を保護するために二重引用符変数の参照に重要だとシェルによる早すぎるグロビングを防ぐために$pattern

  • -type dを追加して、ディレクトリ(フォルダ)に一致することを制限しました。これにより、パフォーマンスが向上します。


オプションの背景情報

以下

のMacOS 10.12.1に見られるようなGNU find v4.6.0/BSD findのよう正規表現機能行列です:

  • GNU findの機能は、 sは-regextypeオプションでサポートされ、emacsがデフォルトです。

    • いくつかのposix-* -named正規表現の種類は、彼らが機能何POSIX義務を超えたをサポートするという点でmisnomersであることに注意してください。
  • BSD find特徴は、(プラットフォーム風味EREsを意味オプション-Eを使用して)basic(プラットフォーム風味BREsを意味NO正規表現オプションを、使用していない)とextendedによって記載されています。 -regextype posix-extendedを使用している間と​​にこだわっ

    クロスプラットフォーム用の

、GNUfindBSDfind-Eを使用しては安全ですが、あなたが期待するかもしれない、すべての機能がサポートされることに注意し、特に\b\</\>などの文字クラスショートカット、\dなどの文字クラスショートカット。

=================== GNU find =================== 
== REGEX FEATURE: \{\} 
TYPE: awk:          - 
TYPE: egrep:          - 
TYPE: ed:           ✓ 
TYPE: emacs:          - 
TYPE: gnu-awk:         - 
TYPE: grep:          ✓ 
TYPE: posix-awk:         - 
TYPE: posix-basic:        ✓ 
TYPE: posix-egrep:        - 
TYPE: posix-extended:        - 
TYPE: posix-minimal-basic:      ✓ 
TYPE: sed:          ✓ 
== REGEX FEATURE: {} 
TYPE: awk:          - 
TYPE: egrep:          ✓ 
TYPE: ed:           - 
TYPE: emacs:          - 
TYPE: gnu-awk:         ✓ 
TYPE: grep:          - 
TYPE: posix-awk:         ✓ 
TYPE: posix-basic:        - 
TYPE: posix-egrep:        ✓ 
TYPE: posix-extended:        ✓ 
TYPE: posix-minimal-basic:      - 
TYPE: sed:          - 
== REGEX FEATURE: \+ 
TYPE: awk:          - 
TYPE: egrep:          - 
TYPE: ed:           ✓ 
TYPE: emacs:          - 
TYPE: gnu-awk:         - 
TYPE: grep:          ✓ 
TYPE: posix-awk:         - 
TYPE: posix-basic:        ✓ 
TYPE: posix-egrep:        - 
TYPE: posix-extended:        - 
TYPE: posix-minimal-basic:      - 
TYPE: sed:          ✓ 
== REGEX FEATURE: + 
TYPE: awk:          ✓ 
TYPE: egrep:          ✓ 
TYPE: ed:           - 
TYPE: emacs:          ✓ 
TYPE: gnu-awk:         ✓ 
TYPE: grep:          - 
TYPE: posix-awk:         ✓ 
TYPE: posix-basic:        - 
TYPE: posix-egrep:        ✓ 
TYPE: posix-extended:        ✓ 
TYPE: posix-minimal-basic:      - 
TYPE: sed:          - 
== REGEX FEATURE: \b 
TYPE: awk:          - 
TYPE: egrep:          ✓ 
TYPE: ed:           ✓ 
TYPE: emacs:          ✓ 
TYPE: gnu-awk:         ✓ 
TYPE: grep:          ✓ 
TYPE: posix-awk:         - 
TYPE: posix-basic:        ✓ 
TYPE: posix-egrep:        ✓ 
TYPE: posix-extended:        ✓ 
TYPE: posix-minimal-basic:      ✓ 
TYPE: sed:          ✓ 
== REGEX FEATURE: \< \> 
TYPE: awk:          - 
TYPE: egrep:          ✓ 
TYPE: ed:           ✓ 
TYPE: emacs:          ✓ 
TYPE: gnu-awk:         ✓ 
TYPE: grep:          ✓ 
TYPE: posix-awk:         - 
TYPE: posix-basic:        ✓ 
TYPE: posix-egrep:        ✓ 
TYPE: posix-extended:        ✓ 
TYPE: posix-minimal-basic:      ✓ 
TYPE: sed:          ✓ 
== REGEX FEATURE: [:digit:] 
TYPE: awk:          ✓ 
TYPE: egrep:          ✓ 
TYPE: ed:           ✓ 
TYPE: emacs:          - 
TYPE: gnu-awk:         ✓ 
TYPE: grep:          ✓ 
TYPE: posix-awk:         ✓ 
TYPE: posix-basic:        ✓ 
TYPE: posix-egrep:        ✓ 
TYPE: posix-extended:        ✓ 
TYPE: posix-minimal-basic:      ✓ 
TYPE: sed:          ✓ 
== REGEX FEATURE: \d 
TYPE: awk:          - 
TYPE: egrep:          - 
TYPE: ed:           - 
TYPE: emacs:          - 
TYPE: gnu-awk:         - 
TYPE: grep:          - 
TYPE: posix-awk:         - 
TYPE: posix-basic:        - 
TYPE: posix-egrep:        - 
TYPE: posix-extended:        - 
TYPE: posix-minimal-basic:      - 
TYPE: sed:          - 
== REGEX FEATURE: \s 
TYPE: awk:          ✓ 
TYPE: egrep:          ✓ 
TYPE: ed:           - 
TYPE: emacs:          ✓ 
TYPE: gnu-awk:         ✓ 
TYPE: grep:          - 
TYPE: posix-awk:         ✓ 
TYPE: posix-basic:        - 
TYPE: posix-egrep:        ✓ 
TYPE: posix-extended:        ✓ 
TYPE: posix-minimal-basic:      - 
TYPE: sed:          - 
=================== BSD find =================== 
== REGEX FEATURE: \{\} 
TYPE: basic:          ✓ 
TYPE: extended:         - 
== REGEX FEATURE: {} 
TYPE: basic:          - 
TYPE: extended:         ✓ 
== REGEX FEATURE: \+ 
TYPE: basic:          - 
TYPE: extended:         - 
== REGEX FEATURE: + 
TYPE: basic:          - 
TYPE: extended:         ✓ 
== REGEX FEATURE: \b 
TYPE: basic:          - 
TYPE: extended:         - 
== REGEX FEATURE: \< \> 
TYPE: basic:          - 
TYPE: extended:         - 
== REGEX FEATURE: [:digit:] 
TYPE: basic:          ✓ 
TYPE: extended:         ✓ 
== REGEX FEATURE: \d 
TYPE: basic:          - 
TYPE: extended:         - 
== REGEX FEATURE: \s 
TYPE: basic:          - 
TYPE: extended:         ✓ 
+0

は魅力的に働いていました!!、 '-type d'がなくても動作します – ADPK

+0

@ADPK:それを聞いて嬉しいです。はい、名前パターンが十分に特定のものであれば、厳密には '-type d 'は必要ありませんが、それを追加するとパフォーマンスが向上します。なぜなら' find'はディレクトリだけを見るからです。 – mklement0

-1

ファイルのフルパスがある場合、ディレクトリ名を抽出する正規表現は必要ありません。

dirname "/path/20161128-20:34:33:432813246/data.txt" 

あなたが本当に正規表現をしたい場合は、あなたに

/path/20161128-20:34:33:432813246 

を与える、これを試してみてください。

\d{8}-\d{2}:\d{2}:\d{2}:\d{9} 
+2

ワイルドカードや正しい正規表現に辿り着くのがより具体的なので、これは答えにはならないと思います。 – Deepak

+0

OPが質問の正規表現を定義しようとする試みを全く示さなかったことを考えれば、これがまさに彼らが探していたものであれば私には驚かないだろう。 – chepner

+1

OPは、うまくいくパターンの例として、 ''* data.txt' 'を使用していますが、ディレクトリ名を直接照合し、ディレクトリパスを直接出力するように意図しています事実の後で 'dirname'を適用する必要はありません)。 あなたのregexについて:(a)GNUもBSDも文字クラスのショートカット '\ d'をサポートしていませんし、(b)' -regex'と一緒に使用すると、_entireのパス_ 。 – mklement0

関連する問題