Linux

bash 腳本:如何在 bash 腳本中執行 rm -v !(*.yaml)?

  • September 11, 2022

在它讀取的腳本中: rm -v !\(*.yaml\) ; 這會產生 rm: cannot remove ‘!(*.yaml)’: No such file or directory,但在命令行中可以正常工作。嘗試過以各種方式逃跑:

`\!\(\*.yaml\)`
`!\(*.yaml\"\)`
"\!\(\*.yaml\)"

似乎無法弄清楚適當的轉義序列,我根本不明白。擺脫括號是我的第一步。然後試圖逃跑!,然後*。也嘗試不轉義,使用反引號,但我收到錯誤“rm缺少操作數”。我有點難過。已經使用了大約一個小時 - 只是“rm all not yaml”……有人可能會發現錯誤/建議修復嗎?

非常感謝,

PS:也試過#!/bin/sh 和#!/bin/bash。想著說不定會有一些效果。

!(x)是 Korn shell glob 運算符。bash支持ksh’s glob 運算符的子集,包括該運算符,但僅在shopt -s extglob¹之後

所以:

shopt -s extglob
rm -f -- !(*.yaml)

將刪除目前目錄中的所有非隱藏文件,但名稱以 . 結尾的文件除外.yaml

在任何情況下,glob 運算符在引用時都不會被辨識,因此使用\(Bourne-like shell 中的引用運算符之一)將無濟於事。

zsh外殼中的等價物是:

rm -f -- ^*.yaml

你需要set -o extendedglob的。

(它也支持!(x)emulate kshor之後set -o kshglob)。

sh儘管您可能會發現某些sh實現,例如基於ksh支持!(x)作為擴展的實現,但該語言中沒有等價物。


¹ 因為這會影響 shell 語法解析,所以必須在讀取和解析包含這些 ksh 擴展運算符之一的行之前shopt執行該命令。例如在 中,您會收到一個語法錯誤,因為首先解析整行(extglob 尚未打開),然後執行(好吧,如果不是因為語法錯誤,本來會執行)。很好。bash -c 'shopt -s extglob; echo !(x)'``shopt``bash -O extglob -c 'echo !(x)'

引用自:https://unix.stackexchange.com/questions/716848