sed（意為流編輯器，源自英語「stream editor」的縮寫）是一個使用簡單緊湊的程式語言來解析和轉換文字 Unix 實用程式。

sed 由貝爾實驗室的李・E・麥克馬洪於 1973 年至 1974 年開發， 
並且現在大多數作業系統都可以使用。 sed 基於互動式編輯器 ed（「editor」，1971）和早期 qed（「quick editor」，1965-66）的指令碼功能。sed 是最早支援正規表示式的工具之一，至今仍然用於文字處理，特別是用於替換命令。用於純文字字串操作和「流編輯」的常用工具還有 AWK 和 Perl 。



歷史

sed 是為命令列處理資料檔案而構建的早期 Unix 命令之一，首次出現在 Version 7 Unix 中 。它很自然地演變成為流行的 grep 命令的後繼。 最初的動機與 grep（g/re/p）的替換類似，因此稱為「g/re/s」。 考慮到這樣的話還會出現針對每個命令的專用程式，例如 g/re/d，李・E・麥克馬洪編寫了一個通用的面向行的流編輯器，該編輯器後來成為了 sed。 sed 的語法，特別是把 `/` 用於模式匹配，把 `s///` 用於替換，起源於 sed 的前身 ed（當時 ed 很常用） 而且正規表示式語法影響了其他一些語言，特別是 ECMAScript 和 Perl。後來，更強大的語言 AWK 問世，這些工具相互補充，讓通過 shell 指令碼完成強大的文字處理成為可能。sed 和 AWK 常被認為 Perl 的祖先和靈感來源，並且影響了 Perl 的語法和語意，尤其影響了匹配和替換運算子。

GNU sed 添加了一些新功能，包括檔案的就地編輯 。_Super-sed_ 是 sed 的擴充版本，包含與 Perl 相容的正規表示式。sed 的另一變體 _minised_ ，最初埃里克・雷蒙把 4.1BSD sed 通過逆向工程寫成，目前由 René Rebe 維護。在 GNU 計劃基於新的 GNU 正規表示式庫編寫了新版本的 sed 之前，GNU 計劃一直使用 minised。當前 minised 包含一些 BSD sed 的擴充，但不像 GNU sed 那樣功能豐富。它的優點是速度快，占用的記憶體少。它用於嵌入式系統，是 Minix 提供的 sed 版本。



工作模式

sed 是一個面向行的文字處理實用程式：它從輸入流或檔案中逐行讀取文字到一個稱為_模式空間_ 的內部緩衝區。每讀一行開始一個_迴圈_ 。對於模式空間，sed 會應用 _sed 指令碼_ 指定的一個或多個操作。sed 實現了一種程式語言，其中包含大約 25 個指定文字操作的_命令_ 。對於每個輸入行，在執行指令碼之後，sed 通常輸出模式空間（由指令碼修改的行），然後從下一行再次開始迴圈。其他指令碼結束行為可通過 sed 選項和指令碼命令獲得，例如 `d` 刪除模式空間，`q` 登出，`N` 立即將下一行添加到模式空間，等等。因此，sed 指令碼對應於迴圈體，迴圈體遍歷流的行，其中迴圈本身和迴圈變數（當前行號）是隱式的並由 sed 維護。

可以在命令列上指定 sed 指令碼（ `-e` 選項），也可以從單獨的檔案中讀取（ `-f` 選項）。sed 指令碼中的命令可以採用行號或正規表示式的作為_位址_ 。該位址確定決定命令何時執行。例如，`2d` 將僅在第二個輸入行上執行 `d`（刪除）命令（列印除第二個輸入行之外的所有行），而 `/^ /d` 將刪除以空格開頭的所有行。一些單獨的特殊緩衝區，即_保持空間_，可以由幾個 sed 命令使用，用於在迴圈之間保持和累積文字。sed 的命令語言只有兩個變數（「保持空間」和「模式空間」）和類似 GOTO 的分支功能；然而，這種語言是圖靈完備的， 用深奧 sed 指令碼甚至寫得出推箱子、打磚塊、西洋棋和俄羅斯方塊等遊戲。

為輸入流的每一行執行一次主迴圈，在輸入的每一行上計算 sed 指令碼。sed 指令碼的每一行都是模式 - 動作對，指示著要匹配的模式和要執行的操作，可以將其重新組合為條件語句。因為主迴圈、工作變數（模式空間和保持空間）、輸入和輸出流以及預設操作（複製行到模式空間、列印模式空間）是隱式的，所以可以編寫簡潔的單行程式。例如，以下 sed 程式：

```
10q
```

將列印輸入的前 10 行，然後停止。



用法

替換命令

下面的範例顯示了 sed 用於替換的典型（也是最常見的）用法。這種用法確實是 sed 的最初動機：

在某些版本的 sed 中，表達式的前面必須加上 `-e`，以表示後面跟著一個表達式。`s` 表示替換，而 `g` 表示全域，這意味著行中的所有匹配項都將被替換。要搜尋的正規表示式（即 pattern）放在第一個分隔符號（此處為斜槓）之後，而要替換成的字串跟在第二個分隔符號後面。斜槓（`/`）是傳統的符號，起源於 ed 中的「搜尋」字元，但其實在 pattern 和替換文字中都未出現的任何其他符號都可以用作分隔符號，使其可讀性更強；這有助於避免「傾斜牙籤症候群」。

替換命令源自 ed 中的搜尋 - 替換，實現了簡單的解析和模板化 。`regexp` 提供模式匹配和通過子表達式儲存文字的功能，而 `replacement` 可以是純文字，也可以是包含「完全匹配」`&`，或第 _n_ 個子表達式（從 `\1` 到 `\9`）這種特殊跳脫序列的格式字串。例如， `sed -r "s/(cat|dog)s?/\1s/g"` 用「cat」或「dog" 替換所有出現的「cats」或「dogs」，而不複製現有的「s」：在正規表示式中，`(cat|dog)` 是第一個（也是唯一）儲存的子表達式，格式字串中的 `\1` 將其替換到輸出里。

其他 sed 命令

除了替換之外，使用大約 25 個 sed 命令可以進行其他形式的簡單處理。例如，下面使用 _d_ 命令刪除空行或只包含空格的行：

本例使用了下列正規表示式元字元（sed 支援所有正規表示式）：


* 脫字元（ `^` ）匹配行首。

* 美元符號（ `$` ）匹配行尾。

* 星號（ `*` ）匹配前一個字元零次或多次出現。

可以有很複雜的 sed 結構，讓 sed 用作一種簡單但高度專業化的程式語言。例如，可以通過使用標籤（冒號後跟字串）和分支指令 `b` 來管理控制流程。指令 `b` 後跟有效的標籤名稱，將把處理流程移動到該標籤後面的塊。

sed 用作過濾器

在 Unix 下，sed 通常用作管道中的過濾器：

也就是說，諸如「generateData」之類的程式生成資料，然後用 sed 把 _x_ 替換成 _y_。例如：

基於檔案的 sed 指令碼

將幾個 sed 命令（每行一個命令）放入指令碼檔案（例如 `subst.sed`）中然後使用 `-f` 選項從檔案中執行命令（例如 `s/x/y/g`）通常很有用：

可以在指令碼檔案中放置任意數量的命令，使用指令碼檔案也可以避免 shell 跳脫或替換的問題。

這樣的指令碼檔案可以直接從命令列執行，方法是在其前面加上一個包含 sed 命令的 "shebang 行"，並為該檔案分配可執行權限。例如，可以使用以下內容建立檔案 `subst.sed`：

然後，當前使用者可以使用 `chmod` 命令使檔案可執行：

然後可以直接從命令列執行該檔案：

就地編輯

GNU sed 中引入的 `-i` 選項允許就地編輯檔案（實際上，在後台建立了一個臨時輸出檔案，然後將原始檔案替換為臨時檔案）。例如：



範例

Hello, world! 例子

這個「Hello, world!」指令碼位於檔案（如 script.txt）中，並使用 `sed -f script.txt inputFileName` 呼叫，其中「inputFileName」是輸入文字檔案。指令碼將「inputFileName」第 1 行更改為「Hello, world!」然後登出，在 sed 登出之前列印結果。第 1 行後的任何輸入行都不會被讀取，也不會被列印。唯一的輸出是「Hello, world!」。

這個例子強調了 sed 的許多關鍵特性：


* sed 是獨一無二的。沒有其他「Hello, world!」例子與之相似。

* 典型的 sed 程式相當簡短。

* sed 指令碼可以有注釋（以 `#` 符號開頭的行）。

* `s`（替換）命令是最重要的 sed 命令。

* sed 允許使用 `q`（登出）等命令進行簡單編程。

* sed 使用正規表示式，例如 `.*` （任何字元的零個或多個）。

其他簡單的例子

下面是各種 sed 指令碼；可以把它們作為參數傳遞給 sed，或者放入一個單獨的檔案並通過 `-f` 執行或通過使指令碼本身可執行來執行。

要把檔案中某個單詞（例如 IRC 密碼）替換為「REDACTED」，並儲存結果：

要刪除包含「yourword」一詞的所有行（ _位址_ 為「/yourword/」）：

要刪除所有「yourword」這個詞：

要同時從檔案中刪除兩個單詞：

為了在一行表示前面的範例，比如在命令列輸入時，可以通過分號連接兩個命令：

多行處理範例

在下一個範例中，sed（通常僅在一行上工作）會在某一行的後一行以一個空格打頭的情況下刪除換行符。
請考慮以下文字：

```
This is my dog,
 whose name is Frank.
This is my fish,
whose name is George.
This is my goat,
 whose name is Adam.
```

下面的 sed 指令碼會將上面的文字轉換為以下文字。請注意，該指令碼僅影響以空格開頭的輸入行：

```
This is my dog, whose name is Frank.
This is my fish,
whose name is George.
This is my goat, whose name is Adam.
```

使用的指令碼是：

```
N
s/\n / /
P
D
```

這段指令碼應按如下理解：


* （`N`）將下一行添加到模式空間；

* （`s/\n / /`）尋找一個換行符後跟一個空格，替換為一個空格；

* （`P`）列印模式空間的頂行；

* （`D`）從模式空間中刪除頂行並再次執行指令碼。

這可以通過分號在一行中表示出來:

```
sed 'N; s/\n / /; P; D' inputFileName
```



限制和替代方案

雖然 sed 具有簡單性和局限性，但對於大量用途而言，它的功能已經足夠強大。對於更複雜的處理，可以使用更強大的語言，如 AWK 或 Perl 或者 PowerShell。雖然使用保持緩衝區理論上可以進行任意複雜的轉換，但如果轉換行的方式比正規表示式提取和模板替換更複雜，則使用一般會使用上面提到的更強大的語言。

相反，對於更簡單的操作，grep （列印匹配模式的行），head（列印檔案的第一部分），tail（列印檔案的最後部分）和 tr（翻譯或刪除字元）等專門的 Unix 實用程式通常更可取。對於設計用於執行的特定任務，此類專用實用程式通常比較一般的解決方案（如 sed）更簡單、清晰和快速。

ed/sed 命令和語法繼續用於衍生程式，例如文字編輯器 vi 和 vim。sam/ssam 與 ed/sed 類似，其中 sam 是 Plan 9 編輯器，ssam 是它的流介面，其功能類似於 sed。

 



注釋



參考文獻



擴充閱讀


* 貝爾實驗室的第八版（約 1985 年）Unix sed（1）手冊頁（頁面存檔備份，存於網際網路檔案館）

* GNU sed（1）手冊頁

* Dale Dougherty & Arnold Robbins. sed & awk 2nd. O'Reilly. March 1997 [2018-11-10]. ISBN1-56592-225-5. （原始內容存檔於 2018-11-02）.

* Arnold Robbins. sed and awk Pocket Reference 2nd. O'Reilly. June 2002 [2018-11-10]. ISBN0-596-00352-8. （原始內容存檔於 2018-11-11）.

* Peter Patsis. UNIX AWK and SED Programmer's Interactive Workbook (UNIX Interactive Workbook). Prentice Hall. December 1998 [2018-11-10]. ISBN0-13-082675-8. （原始內容存檔於 2020-04-09）.

* Daniel Goldman. Definitive Guide to sed. EHDP Press. February 2013 [2018-11-10]. ISBN978-1-939824-00-4. （原始內容存檔於 2018-01-29）.

* Sourceforge.net（頁面存檔備份，存於網際網路檔案館） ，sed FAQ（2003 年 3 月）



外部連結


* `sed`– 命令與工具（Commands & Utilities）參考，單一 UNIX® 規範第 7 期，由國際開放標準組織發布

教程


* Sed - An Introduction and Tutorial（頁面存檔備份，存於網際網路檔案館）, by Bruce Barnett

* SED -- A Non-interactive Text Editor (1974)（頁面存檔備份，存於網際網路檔案館）, by Lee E. McMahon

* 31+ Examples For Sed Linux Command In Text Manipulation（頁面存檔備份，存於網際網路檔案館）, by Mokhtar Ebrahim

* Sed 教學（頁面存檔備份，存於網際網路檔案館）

範例


* Major sources for sed scripts, files, usage

* Roger Chang's SED and Shell Scripts (2012)（頁面存檔備份，存於網際網路檔案館）

* Top 'sed' commands – Usage examples

* Sed command examples in Unix & Linux（頁面存檔備份，存於網際網路檔案館）

其他連結


* GNU sed 首頁（包括 GNU sed 手冊）

* sed the Stream Editor（2004）（頁面存檔備份，存於網際網路檔案館） （Eric Pement）

* sed-users Yahoo 討論組（頁面存檔備份，存於網際網路檔案館）



參見


* Unix 實用程式列表

* AWK

* tr

* PowerShell