编辑“︁
Sed
”︁
跳转到导航
跳转到搜索
Template:Editnotice load/content
警告:
您没有登录。如果您进行任何编辑,您的IP地址会公开展示。如果您
登录
或
创建账号
,您的编辑会以您的用户名署名,此外还有其他益处。
反垃圾检查。
不要
加入这个!
{{NoteTA|G1=IT}} {{about|Unix程式|縮寫SED的其他含義|SED}} {{Infobox programming language | name = sed | paradigm = [[脚本语言|脚本]] | released = {{start date and age|1974}} | designer = [[李·E·麥克馬洪]] | programming_language = [[C语言|C]] | influenced by = [[Ed (文本编辑器)|ed]] | influenced = {{tsl|en|Chomski}}, [[Perl]], [[AWK]] | screenshot = Sed stream editor cropped1.jpg | screenshot caption = GNU sed [[手册页|使用手冊]]的節錄 | website = }} {{lowercase|sed}} '''sed'''(意为'''流编辑器''',源自[[英语]]“{{lang|en|stream editor}}”的缩写)是一个使用简单紧凑的编程语言来解析和转换文本[[UNIX|Unix]]实用程序。 sed由[[贝尔实验室|贝尔实验室]]的[[李·E·麥克馬洪]]于1973年至1974年开发, <ref name="sed-faq-2.1">{{cite web | url=http://sed.sourceforge.net/sedfaq2.html#s2.1 | title=The sed FAQ, Section 2.1 | accessdate=2013-05-21 | archive-date=2018-06-27 | archive-url=https://web.archive.org/web/20180627160704/http://sed.sourceforge.net/sedfaq2.html#s2.1 | dead-url=no }}</ref> 并且现在大多数操作系统都可以使用。 <ref name="sed-faq-2.2">{{cite web | url=http://sed.sourceforge.net/sedfaq2.html#s2.2 | title=The sed FAQ, Section 2.2 | accessdate=2013-05-21 | archive-date=2018-06-27 | archive-url=https://web.archive.org/web/20180627160704/http://sed.sourceforge.net/sedfaq2.html#s2.2 | dead-url=no }}</ref> sed基于交互式编辑器ed(“editor”,1971)和早期qed(“quick editor”,1965-66)的脚本功能。sed是最早支持[[正则表达式|正则表达式]]的工具之一,至今仍然用于文本处理,特别是用于替换命令。用于纯文本字符串操作和“流编辑”的常用工具还有[[AWK|AWK]]和[[Perl|Perl]] 。 ==历史== sed是为命令行处理数据文件而构建的早期Unix命令之一,首次出现在Version 7 Unix中 。{{r|reader}}它很自然地演变成为流行的[[Grep|grep]]命令的后继。<ref name="early_history">{{cite web | title = On the Early History and Impact of Unix | url = http://www.columbia.edu/~rh120/ch001j.c11 | quote = "A while later a demand arose for another special-purpose program, gres, for substitution: g/re/s. Lee McMahon undertook to write it, and soon foresaw that there would be no end to the family: g/re/d, g/re/a, etc. As his concept developed it became sed…" | access-date = 2018-11-10 | archive-url = https://web.archive.org/web/20170907041104/http://www.columbia.edu/~rh120/ch001j.c11 | archive-date = 2017-09-07 | dead-url = yes }}</ref> 最初的动机与grep(g/re/p)的替换类似,因此称为“g/re/s”。<ref name="reader">{{cite techreport |first1=M. D. |last1=McIlroy |authorlink1=道格拉斯·麥克羅伊 |year=1987 |url=http://www.cs.dartmouth.edu/~doug/reader.pdf |title=A Research Unix reader: annotated excerpts from the Programmer's Manual, 1971–1986 |series=CSTR |number=139 |institution=Bell Labs |access-date=2018-11-10 |archive-date=2019-11-30 |archive-url=https://web.archive.org/web/20191130000850/https://www.cs.dartmouth.edu/~doug/reader.pdf |dead-url=no }}</ref> 考虑到这样的话还会出现针对每个命令的专用程序,例如g/re/d,李·E·麥克馬洪编写了一个通用的面向行的流编辑器,该编辑器后来成为了sed。<ref name="early_history"></ref> sed的语法,特别是把<code>/</code>用于模式匹配,把<code>s///</code>用于替换,起源于sed的前身ed(当时ed很常用)<ref name="early_history"></ref> 而且正则表达式语法影响了其他一些语言,特别是[[ECMAScript|ECMAScript]]和[[Perl|Perl]]。后来,更强大的语言[[AWK|AWK]]问世,这些工具相互补充,让通过shell脚本完成强大的文本处理成为可能。sed和AWK常被认为Perl的祖先和灵感来源,并且影响了Perl的语法和语义,尤其影响了匹配和替换运算符。 [[GNU|GNU]] sed添加了一些新功能,包括文件的就地编辑 。''Super-sed'' 是sed的扩展版本,包含与[[Perl|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选项和脚本命令获得,例如<code>d</code>删除模式空间,<code>q</code>退出,<code>N</code>立即将下一行添加到模式空间,等等。因此,sed脚本对应于循环体,循环体遍历流的行,其中循环本身和循环变量(当前行号)是隐式的并由sed维护。 可以在命令行上指定sed脚本( <code>-e</code>选项),也可以从单独的文件中读取( <code>-f</code>选项)。sed脚本中的命令可以采用行号或[[正则表达式|正则表达式]]的作为''地址'' 。该地址确定决定命令何时运行。例如,<code>2d</code>将仅在第二个输入行上运行<code>d</code>(删除)命令(打印除第二个输入行之外的所有行),而<code>/^ /d</code>将删除以空格开头的所有行。一些单独的特殊缓冲区,即''保持空间'',可以由几个sed命令使用,用于在循环之间保持和累积文本。sed的命令语言只有两个变量(“保持空间”和“模式空间”)和类似GOTO的分支功能;然而,这种语言是图灵完备的,<ref>{{cite web | title = Implementation of a Turing Machine as Sed Script | url = http://sed.sourceforge.net/grabbag/scripts/turing.txt | accessdate = 2018-11-10 | archive-date = 2018-02-20 | archive-url = https://web.archive.org/web/20180220011912/http://sed.sourceforge.net/grabbag/scripts/turing.txt | dead-url = no }}</ref><ref>{{cite web | title = Turing.sed | url = http://sed.sourceforge.net/grabbag/scripts/turing.sed | accessdate = 2018-11-10 | archive-date = 2018-01-16 | archive-url = https://web.archive.org/web/20180116201401/http://sed.sourceforge.net/grabbag/scripts/turing.sed | dead-url = no }}</ref> 用深奥sed脚本甚至写得出[[倉庫番|推箱子]]、[[快打磚塊|打砖块]]<ref name="gamez">{{cite web | url = http://sed.sourceforge.net/#gamez | title = The $SED Home - gamez | access-date = 2009-04-20 | archive-url = https://web.archive.org/web/20060208161216/http://sed.sourceforge.net/#gamez | archive-date = 2006-02-08 | dead-url = yes }}</ref>、[[國際象棋|国际象棋]]<ref>{{cite web|url=https://github.com/bolknote/SedChess|title=bolknote/SedChess|author=|date=|website=GitHub|accessdate=2018-11-10|archive-date=2018-12-02|archive-url=https://web.archive.org/web/20181202011820/https://github.com/bolknote/SedChess|dead-url=no}}</ref>和[[俄羅斯方塊|俄罗斯方块]]<ref name="tetris">{{cite web | url = https://github.com/uuner/sedtris | title = Sedtris, a Tetris game written for sed | accessdate = 2018-11-10 | archive-date = 2018-12-02 | archive-url = https://web.archive.org/web/20181202011821/https://github.com/uuner/sedtris | dead-url = no }}</ref>等游戏。 为输入流的每一行执行一次主循环,在输入的每一行上计算sed脚本。sed脚本的每一行都是模式-动作对,指示着要匹配的模式和要执行的操作,可以将其重新组合为条件语句。因为主循环、工作变量(模式空间和保持空间)、输入和输出流以及默认操作(复制行到模式空间、打印模式空间)是隐式的,所以可以编写简洁的[[單行小程式|单行程序]]。例如,以下sed程序: 10q 将打印输入的前10行,然后停止。 ==用法== ===替换命令=== 下面的示例显示了sed用于替换的典型(也是最常见的)用法。这种用法确实是sed的最初动机:<ref name="early_history"></ref> <syntaxhighlight lang=bash> sed 's/regexp/replacement/g' inputFileName > outputFileName </syntaxhighlight> 在某些版本的sed中,表达式的前面必须加上<code>-e</code>,以表示后面跟着一个表达式。<code>s</code>表示替换,而<code>g</code>表示全局,这意味着行中的所有匹配项都将被替换。要搜索的[[正则表达式|正则表达式]](即pattern)放在第一个分隔符号(此处为斜杠)之后,而要替换成的字符串跟在第二个分隔符号后面。斜杠(<code>/</code>)是传统的符号,起源于ed中的“搜索”字符,但其实在pattern和替换文本中都未出现的任何其他符号都可以用作分隔符号,使其可读性更强;这有助于避免“[[倾斜牙签综合征]]”。 替换命令源自ed中的搜索-替换,实现了简单的解析和模板化 。<code>regexp</code>提供模式匹配和通过子表达式保存文本的功能,而<code>replacement</code>可以是纯文本,也可以是包含“完全匹配”<code>&</code>,或第''n'' 个子表达式(从<code>\1</code>到<code>\9</code>)这种特殊[[转义序列|转义序列]]的格式字符串。例如, <syntaxhighlight lang=bash inline=true>sed -r "s/(cat|dog)s?/\1s/g"</syntaxhighlight>用“cat”或“dog”替换所有出现的“cats”或“dogs”,且不重覆复制出原文內已有的“s”:在正则表达式中,<code>(cat|dog)</code>是第一个(也是唯一)保存的子表达式,格式字符串中的<code>\1</code>将其替换到输出里。 ===其他sed命令=== 除了替换之外,使用大约25个sed命令可以进行其他形式的简单处理。例如,下面使用''d'' 命令删除空行或只包含空格的行: <syntaxhighlight lang=bash> sed '/^ *$/d' inputFileName </syntaxhighlight> 本例使用了下列[[正则表达式|正则表达式]]元字符(sed支持所有正则表达式): *脱字符( <code>^</code> )匹配行首。 *美元符号( <code>$</code> )匹配行尾。 *[[星號|星号]]( <code>*</code> )匹配前一个字符零次或多次出现。 可以有很复杂的sed结构,让sed用作一种简单但高度专业化的[[编程语言|编程语言]]。例如,可以通过使用标签(冒号后跟字符串)和分支指令<code>b</code>来管理控制流程。指令<code>b</code>后跟有效的标签名称,将把处理流程移动到该标签后面的块。 === sed用作过滤器 === 在Unix下,sed通常用作管道中的过滤器: <syntaxhighlight lang=console> $ generateData | sed 's/x/y/g' </syntaxhighlight> 也就是说,诸如“generateData”之类的程序生成数据,然后用sed把''x''替换成''y''。例如: <syntaxhighlight lang=console> $ echo xyz xyz | sed 's/x/y/g' yyz yyz </syntaxhighlight> {{NoteTag|name=quotes|在命令行使用中,表达式周围的引号不是必需的,只有在shell不会将表达式解释为单个字(标记)时才需要。由于脚本<code>s/x/y/g</code>没有歧义,所以<code>generateData <nowiki>|</nowiki> sed s/x/y/g</code>工作正常。然而,为了清楚起见,通常是要写引号的,特别是对于有空格的时候(例如,<code>'s/x x/y y/'</code>)。大多数情况下,使用单引号是为了避免shell将<code>$</code>解释为shell变量。使用双引号,如<code>"s/$1/$2/g"</code>,是为了让shell替换命令行参数或其他shell变量。}} ===基于文件的sed脚本=== 将几个sed命令(每行一个命令)放入脚本文件(例如<code>subst.sed</code>)中然后使用<code>-f</code>选项从文件中运行命令(例如<code>s/x/y/g</code>)通常很有用: <syntaxhighlight lang=bash> sed -f subst.sed inputFileName > outputFileName </syntaxhighlight> 可以在脚本文件中放置任意数量的命令,使用脚本文件也可以避免shell转义或替换的问题。 这样的脚本文件可以直接从命令行执行,方法是在其前面加上一个包含sed命令的"shebang行",并为该文件分配可执行权限。例如,可以使用以下内容创建文件<code>subst.sed</code>: <syntaxhighlight lang=bash> #!/bin/sed -f s/x/y/g </syntaxhighlight> 然后,当前用户可以使用<code>chmod</code>命令使文件可执行:<syntaxhighlight lang=bash> chmod u+x subst.sed </syntaxhighlight>然后可以直接从命令行执行该文件: <syntaxhighlight lang=bash> subst.sed inputFileName > outputFileName </syntaxhighlight> ===就地编辑=== GNU sed中引入的<code>-i</code>选项允许就地编辑文件(实际上,在后台创建了一个临时输出文件,然后将原始文件替换为临时文件)。例如: <syntaxhighlight lang=bash> sed -i 's/abc/def/' fileName </syntaxhighlight> ==示例== ===Hello, world! 例子=== <syntaxhighlight lang=console> # convert input text stream to "Hello, world!" s/.*/Hello, world!/ q </syntaxhighlight> 这个“Hello, world!”脚本位于文件(如script.txt)中,并使用<code>sed -f script.txt inputFileName</code>调用,其中“inputFileName”是输入文本文件。脚本将“inputFileName”第1行更改为“Hello, world!”然后退出,在sed退出之前打印结果。第1行后的任何输入行都不会被读取,也不会被打印。唯一的输出是“Hello, world!”。 这个例子强调了sed的许多关键特性: *sed是独一无二的。没有其他“Hello, world!”例子与之相似。 *典型的sed程序相当简短。 *sed脚本可以有注释(以<code>#</code>符号开头的行)。 *<code>s</code>(替换)命令是最重要的sed命令。 *sed允许使用<code>q</code>(退出)等命令进行简单编程。 *sed使用正则表达式,例如<code>.*</code> (任何字符的零个或多个)。 ===其他简单的例子=== <!-- please avoid the use of GNU sedisms. These are non-portable and lead to bad code --> 下面是各种sed脚本;可以把它们作为参数传递给sed,或者放入一个单独的文件并通过<code>-f</code>执行或通过使脚本本身可执行来执行。 要把文件中某个单词(例如IRC密码)替换为“REDACTED”,并保存结果: <syntaxhighlight lang=bash> sed -i s/yourpassword/REDACTED/ ./status.freenode.log </syntaxhighlight> 要删除包含“yourword”一词的所有行( ''地址'' 为“/yourword/”): <syntaxhighlight lang=bash> /yourword/ d </syntaxhighlight> 要删除所有“yourword”这个词: <syntaxhighlight lang=bash> s/yourword//g </syntaxhighlight> 要同时从文件中删除两个单词: <syntaxhighlight lang=bash> s/firstword//g s/secondword//g </syntaxhighlight> 为了在一行表示前面的示例,比如在命令行输入时,可以通过分号连接两个命令: <syntaxhighlight lang=bash> sed "s/firstword//g; s/secondword//g" inputFileName </syntaxhighlight> ===多行处理示例=== 在下一个示例中,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 这段脚本应按如下理解: *(<code>N</code>)将下一行添加到模式空间; *(<code>s/\n / /</code>)查找一个换行符后跟一个空格,替换为一个空格; *(<code>P</code>)打印模式空间的顶行; *(<code>D</code>)从模式空间中删除顶行并再次运行脚本。 这可以通过分号在一行中表示出来: sed 'N; s/\n / /; P; D' inputFileName ==限制和替代方案== 虽然sed具有简单性和局限性,但对于大量用途而言,它的功能已经足够强大。对于更复杂的处理,可以使用更强大的语言,如[[AWK|AWK]]或[[Perl|Perl]]或者PowerShell。虽然使用保持缓冲区理论上可以进行任意复杂的转换,但如果转换行的方式比正则表达式提取和模板替换更复杂,则使用一般会使用上面提到的更强大的语言。 相反,对于更简单的操作,[[Grep|grep]] (打印匹配模式的行),head(打印文件的第一部分),tail(打印文件的最后部分)和tr(翻译或删除字符)等专门的Unix实用程序通常更可取。对于设计用于执行的特定任务,此类专用实用程序通常比较一般的解决方案(如sed)更简单、清晰和快速。 ed/sed命令和语法继续用于派生程序,例如文本编辑器[[vi (文本编辑器)|vi]]和[[Vim|vim]]。sam/ssam与ed/sed类似,其中sam是[[貝爾實驗室九號計畫|Plan 9]]编辑器,ssam是它的流接口,其功能类似于sed。 == 注释 == {{NoteFoot}} ==参考文献== {{Reflist}} ==扩展阅读== * [http://man.cat-v.org/unix_8th/1/sed 贝尔实验室的第八版(约1985年)Unix sed(1)手册页]{{Wayback|url=http://man.cat-v.org/unix_8th/1/sed |date=20181111000121 }} * [http://www.unix.com/man-page/linux/1/sed/ GNU sed(1)手册页] * {{cite book|title=sed & awk|edition=2nd|date=March 1997|url=http://shop.oreilly.com/product/9781565922259.do|author=Dale Dougherty & Arnold Robbins|publisher=[[歐萊禮媒體|O'Reilly]]|isbn=1-56592-225-5|access-date=2018-11-10|archive-date=2018-11-02|archive-url=https://web.archive.org/web/20181102003349/http://shop.oreilly.com/product/9781565922259.do|dead-url=no}} * {{cite book|title=sed and awk Pocket Reference|edition=2nd|date=June 2002|url=http://shop.oreilly.com/product/9780596003524.do|author=Arnold Robbins|publisher=[[歐萊禮媒體|O'Reilly]]|isbn=0-596-00352-8|access-date=2018-11-10|archive-date=2018-11-11|archive-url=https://web.archive.org/web/20181111000000/http://shop.oreilly.com/product/9780596003524.do|dead-url=no}} * {{cite book|title=UNIX AWK and SED Programmer's Interactive Workbook (UNIX Interactive Workbook)|author=Peter Patsis|url=https://www.amazon.com/UNIX-AWK-Programmers-Interactive-Workbook/dp/0130826758|publisher=[[Prentice Hall]]|date=December 1998|isbn=0-13-082675-8|access-date=2018-11-10|archive-date=2020-04-09|archive-url=https://web.archive.org/web/20200409022215/https://www.amazon.com/UNIX-AWK-Programmers-Interactive-Workbook/dp/0130826758|dead-url=no}} * {{cite book|title=Definitive Guide to sed|url=https://www.ehdp.com/press/sed-book/|date=February 2013|author=Daniel Goldman|publisher=EHDP Press|isbn=978-1-939824-00-4|access-date=2018-11-10|archive-date=2018-01-29|archive-url=https://web.archive.org/web/20180129055808/https://www.ehdp.com/press/sed-book/|dead-url=no}} * [http://sed.sourceforge.net/sedfaq.html Sourceforge.net]{{Wayback|url=http://sed.sourceforge.net/sedfaq.html |date=20181030060231 }} ,sed FAQ(2003年3月) == 外部链接 == {{Wikibooks|en:sed}} * {{man|cu|sed|SUS}} ===教程=== * [http://www.grymoire.com/Unix/Sed.html Sed - An Introduction and Tutorial]{{Wayback|url=http://www.grymoire.com/Unix/Sed.html |date=20181112033551 }}, by Bruce Barnett * [http://sed.sourceforge.net/grabbag/tutorials/sed_mcmahon.txt SED -- A Non-interactive Text Editor (1974)]{{Wayback|url=http://sed.sourceforge.net/grabbag/tutorials/sed_mcmahon.txt |date=20190213193448 }}, by Lee E. McMahon * [https://likegeeks.com/sed-linux/ 31+ Examples For Sed Linux Command In Text Manipulation]{{Wayback|url=https://likegeeks.com/sed-linux/ |date=20181116085001 }}, by Mokhtar Ebrahim *[https://tw511.com/2/30/1113.html Sed教學]{{Wayback|url=https://tw511.com/2/30/1113.html |date=20200630143246 }} ===示例=== * [https://web.archive.org/web/20060208161216/http://sed.sourceforge.net/ Major sources for sed scripts, files, usage] * [http://main.rtfiber.com.tw/~changyj/sed/ Roger Chang's SED and Shell Scripts (2012)]{{Wayback|url=http://main.rtfiber.com.tw/~changyj/sed/ |date=20181102121450 }} * [https://web.archive.org/web/20181110200025/http://www.shell-fu.org/lister.php?tag=sed Top 'sed' commands – Usage examples] * [http://www.techsakh.com/2016/05/12/20160512use-sed-command-linux-unix/ Sed command examples in Unix & Linux]{{Wayback|url=http://www.techsakh.com/2016/05/12/20160512use-sed-command-linux-unix/ |date=20181028091936 }} ===其他链接=== *[//www.gnu.org/software/sed/ GNU sed主页](包括GNU sed手册) * [http://www.pement.org/sed/ sed the Stream Editor(2004)]{{Wayback|url=http://www.pement.org/sed/ |date=20181121140441 }} (Eric Pement) *[https://groups.yahoo.com/neo/groups/sed-users/info sed-users Yahoo讨论组]{{Wayback|url=https://groups.yahoo.com/neo/groups/sed-users/info |date=20191016115323 }} == 参见 == * [[Unix实用程序列表]] * [[AWK|AWK]] * [[Tr_(Unix)|tr]] * [[PowerShell]] {{-}} {{Unix commands}} {{程序设计语言}} [[Category:跨平台软件]] [[Category:模式匹配编程语言]] [[Category:脚本语言]] [[Category:标准Unix程序]] [[Category:面向文本编程语言]] [[Category:Unix文字处理实用工具]] [[Category:Unix SUS2008实用工具]] [[Category:控制台应用程序]]
摘要:
请注意,所有对Local Chinese Wikipedia的贡献均可能会被其他贡献者编辑、修改或删除。如果您不希望您的文字作品被随意编辑,请不要在此提交。
您同时也向我们承诺,您提交的内容为您自己所创作,或是复制自公共领域或类似自由来源(详情请见
Project:著作权
)。
未经许可,请勿提交受著作权保护的作品!
取消
编辑帮助
(在新窗口中打开)
导航菜单
个人工具
未登录
讨论
贡献
创建账号
登录
命名空间
页面
讨论
大陆简体
不转换
简体
繁體
大陆简体
香港繁體
澳門繁體
大马简体
新加坡简体
臺灣正體
查看
阅读
编辑
查看历史
更多
搜索
导航
首页
最近更改
随机页面
MediaWiki帮助
工具
链入页面
相关更改
特殊页面
页面信息