How can I use inverse or negative wildcards when pattern matching in a unix/linux shell?

前端 未结 11 1731
梦如初夏
梦如初夏 2020-11-22 13:50

Say I want to copy the contents of a directory excluding files and folders whose names contain the word \'Music\'.

cp [exclude-matches] *Music* /target_direc         


        
11条回答
  •  被撕碎了的回忆
    2020-11-22 14:13

    The extglob shell option gives you more powerful pattern matching in the command line.

    You turn it on with shopt -s extglob, and turn it off with shopt -u extglob.

    In your example, you would initially do:

    $ shopt -s extglob
    $ cp !(*Music*) /target_directory
    

    The full available extended globbing operators are (excerpt from man bash):

    If the extglob shell option is enabled using the shopt builtin, several extended pattern matching operators are recognized.A pattern-list is a list of one or more patterns separated by a |. Composite patterns may be formed using one or more of the following sub-patterns:

    • ?(pattern-list)
      Matches zero or one occurrence of the given patterns
    • *(pattern-list)
      Matches zero or more occurrences of the given patterns
    • +(pattern-list)
      Matches one or more occurrences of the given patterns
    • @(pattern-list)
      Matches one of the given patterns
    • !(pattern-list)
      Matches anything except one of the given patterns

    So, for example, if you wanted to list all the files in the current directory that are not .c or .h files, you would do:

    $ ls -d !(*@(.c|.h))
    

    Of course, normal shell globing works, so the last example could also be written as:

    $ ls -d !(*.[ch])
    

提交回复
热议问题