手册页部分 1: 用户命令

退出打印视图

更新时间: 2014 年 7 月
 
 

red(1)

名称

ed , red - 文本编辑器

用法概要

/usr/bin/ed [-s | -] [-p string] [file]
/usr/xpg4/bin/ed [-s | -] [-p string] [file]
/usr/xpg6/bin/ed [-s | -] [-p string] [file]
/usr/bin/red [-s | -] [-p string] [file]

描述

ed 实用程序是一个标准文本编辑器。如果指定 fileed 将对指定的文件模拟 e 命令(请参见下文)。也就是说,将该文件读取到 ed 的缓冲区中,使其可以编辑。

ed 实用程序在其所编辑的文件的副本上进行操作。在指定 w(写入)命令之前,对该副本所做的更改对文件没有影响。被编辑的文本副本位于名为 buffer 的临时文件中。只有一个缓冲区。

red 实用程序是 ed 的受限版本。它仅允许编辑当前目录中的文件。red 禁止通过 !shell command 执行 shell 命令。试图绕过这些限制将导致出现错误消息 (restricted shell)(被限制的 shell)。

edred 都支持 fspec(4) 格式设置功能。缺省的终端模式是 stty –tabsstty tab3,其中制表停止位置设置在八列(请参见 stty(1))。但是,如果 file 的第一行包含一个规范,则该规范将覆盖缺省模式。例如,如果 file 的第一行包含以下内容,制表停止位置将设置为 5、10 和 15,并强制实施最大行长度 72:

<:t5,10,15 s72:>

ed 命令有一个简单的正规结构:零个、一个或两个地址后跟一个单字符的命令,还可能后跟该命令的参数。这些地址指定缓冲区中的一行或多行。需要地址的每个命令都有缺省地址,因此经常可以将地址省略。

一般情况下,一行上只能出现一个命令。有些命令允许输入文本。此文本放在缓冲区中的相应位置。ed 在接受文本时,应该处于输入模式。在此模式下不能识别任何命令;所有输入都是收集的。通过在行的开头键入一个句点 (.) 并立即跟一个回车,可以退出输入模式。

/usr/bin/ed

如果 ed 执行命令时使用参数,则使用缺省的 shell /usr/bin/sh(请参见 sh(1))。

/usr/xpg4/bin/ed and /usr/xpg6/bin/ed

如果 ed 执行命令时使用参数,则使用 /usr/xpg4/bin/sh(请参见 ksh88(1))。

正则表达式

ed 实用程序支持形式有限的正则表达式表示法。在地址中使用正则表达式来指定行,在有些命令(例如 s)中使用正则表达式指定行中要替换的部分。要了解 ed 中的寻址,必须知道在任何时候都有一个当前行。一般而言,当前行是受命令影响的最后一行。对当前行的具体影响在每个命令的说明中讨论。

国际化基本正则表达式用于所有系统提供的语言环境。请参见 regex(5)

ed 命令

命令可能需要零个、一个或两个地址。不需要地址的命令将存在地址视为错误。接受一个或两个地址的命令在指定的地址数量不足时将使用缺省地址;如果指定的地址多于该命令需要的地址,则使用最后一个(批)地址。

通常,地址用逗号 (,) 互相分隔。也可以用分号 (;) 分隔地址。在后一种情况下,将计算第一个地址,当前行 (.) 设置为该值,然后再计算第二个地址。此功能可用于确定向前和向后搜索的开始行(请参见上文的规则 5 和规则 6)。任何双地址序列的第二个地址必须对应于缓冲区中第一个地址所对应行后面的一行。

对于 /usr/xpg6/gbin/ed,逗号或分号分隔符任一侧的地址都可以省略,此时得到的地址对如下:

指定
结果
,
1 , $
, addr
1 , addr
addr ,
addr , addr
;
1 ; $
; addr
1 ; addr
addr ;
addr ; addr

地址、地址分隔符或地址偏移之间包含的任何 <blank> 都会被忽略。

在以下 ed 命令列表中,命令前面显示的括号不是地址的一部分。括号中显示的是命令的缺省地址。

每个地址组成部分前面可以有零个或更多空白字符。命令字母前面可以有零个或更多空白字符。如果指定前缀字母 (lnp),则必须紧跟命令。

eEfrw 命令使用可选的 file 参数,用一个或多个空白字符与命令字母隔开。

如果自从上一个 w 命令写入整个缓冲区之后缓冲区中发生了变化,则当用户试图通过 eq 命令销毁缓冲区时,ed 将警告用户。ed 实用程序可将字符串:

"?\n"

(如果通过 H 命令启用了帮助模式,则后跟一条解释消息)写入标准输出,然后继续处于命令模式,当前行编号不变。如果重复 eq 命令时没有中间命令,则 ed 将生效。

如果在应该执行命令时在标准输入上检测到文件结尾,则 ed 实用程序的作用相当于输入了 q 命令。

一般情况下,在一行上出现多个命令是非法的。但是,任何命令(efrw 除外)可以加后缀 lnp;在这种情况下,会分别列出、编号或写入当前行,如下文中 lnp 命令下所述。

(.)a
<text>
.

a 附加命令接受零行或更多行文本,并将其附加到缓冲区中的寻址行之后。当前行 (.) 留在最后一个插入的行处;如果没有插入行,则留在寻址行处。地址 0 对此命令合法:它会导致将附加的文本放在缓冲区的开头。可从终端输入的最大字符数是每行 256 个(包括换行符)。

(.,.)c
<text>
.

c 更改命令可删除缓冲区中的寻址行,然后接受零行或更多行文本替换缓冲区中的这些行。当前行 (.) 留在最后一个行输入处;如果没有插入行,则留在未删除的第一个行处。如果删除的行原来在缓冲区的末尾,则当前行编号将设置为新的最后行的地址。如果缓冲区中没有剩余行,则当前行编号将设置为 0。

/usr/xpg4/bin/ed

地址 0 对此命令非法。

/usr/xpg6/bin/ed

地址 0 对此命令有效。地址 0 会被解释为像指定了地址 1 一样。

(.,.)d

d 删除命令可删除缓冲区中的寻址行。最后被删除的一行之后的行将成为当前行。如果删除的行原来在缓冲区的末尾,则新的最后行将成为当前行。如果缓冲区中没有剩余行,则当前行编号将设置为 0。

e file

e 编辑命令可删除缓冲区的整个内容,然后将 file 的内容读取到缓冲区中。当前行 (.) 设置为缓冲区的最后一行。如果未指定 file,则使用当前记住的已有文件名(请参见 f 命令)。读取的字节数将写入到标准输出,除非按以下格式指定 –s 选项:

"%d\n" <number of bytes read>

file 会被记住,在后续的 eErw 命令中可能会用作缺省文件名。如果将 file 替换为 !,则行的剩余部分将被视为一个 shell 命令 (sh(1)),其输出将被读取。这样的 shell 命令不会记为当前文件名。另请参见下文的“诊断”部分。所有标记都会在成功完成 e 命令时丢弃。如果自从上次写入整个缓冲区后缓冲区发生了变化,则用户会收到警告,如前文中所述。

E file

E 编辑命令类似于 e,但编辑器不检查自上一个 w 命令以来缓冲区是否发生变化。

f file

如果指定了 file,则 f 命令将当前记住的路径名更改为 file。不管名称是否变化,f 命令随后都会用以下格式将(可能是新的)当前记住的路径名写入到标准输出:

"%s\n"pathname

当前行编号不变。

(1,$)g/RE/command list

g 全局命令中,第一步是标记与指定的 RE 匹配的每行。然后,对于每个此类行,执行指定的 command list,当前行 (.) 最初设置为该行。g 命令完成时,当前行编号的值是命令列表中最后一个命令赋予的值。如果没有匹配行,则当前行编号不变。单个命令或者命令列表中的第一个命令与全局命令出现在同一行上。多行列表中除最后一行外的所有行必须以反斜杠 (\ ) 结尾;允许 aic 命令及关联的输入。如果 . 终止输入模式是 command list 的最后一行,则可将其省略。空的 command list 等效于 p 命令。gGvV! 命令允许出现在 command list 中。另请参见下文中的“附注”部分以及“文件”部分之前的最后一段。除了空格或换行符以外的任何字符都可以替代斜杠来分隔 RE。在 RE 内部,RE 分隔符本身就可用作文本字符(当它前面有一个反斜杠时)。

(1,$)G/RE/

在交互式 G 全局命令中,第一步是标记与指定的 RE 匹配的每行。然后,对于每一个此类行,将该行写入到标准输出,将当前行 (.) 更改为该行,并且任何一个命令(不包括 acigGvV 命令中的一个)都可以是输入并被执行。在执行了该命令后,写入下一个标记的行,依此类推。换行符的作用相当于一个空命令。& 会导致重新执行在当前调用 G 时执行的最新非空命令。注意:执行 G 命令过程中的命令输入可以寻址和影响缓冲区中的任何行。当前行编号的最后值是最后一个成功执行的命令设置的值。(请注意,如果命令失败或者指定了空命令,则最后一个成功执行的命令是 G 命令本身。)如果没有匹配行,则当前行编号不变。可以通过 SIGINT 信号终止 G 命令。可以通过中断信号(ASCII DEL 或 BREAK)终止 G 命令。除了空格或换行符以外的任何字符都可以替代斜杠来分隔 RE。在 RE 内部,RE 分隔符本身就可用作文本字符(当它前面有一个反斜杠时)。

h

help 命令会提供一条简短的错误消息,解释最近的 ? 诊断的原因。当前行编号不变。

H

Help 命令会导致 ed 进入一种模式,在该模式下,将为所有后续的 ? 诊断写入错误消息。该命令还会解释上一个 ?(如果有)。H 命令还可以打开和关闭此模式;此模式最初是关闭的。当前行编号不变。

(.,.)i
<text>
.

insert 命令接受零行或更多行文本,并将其插入到缓冲区中的寻址行之前。当前行 (.) 留在最后一个插入的行处;如果没有插入行,则留在寻址行处。此命令不同于 a 命令之处仅在于输入文本的位置。可从终端输入的最大字符数是每行 256 个(包括换行符)。

/usr/xpg4/bin/ed

地址 0 对此命令非法。

/usr/xpg6/bin/ed

地址 0 对此命令有效。地址 0 会被解释为像指定了地址 1 一样。

(.,.+1)j

j 联接命令通过删除相应的换行符来联接邻近的行。如果只提供了一个地址,则此命令不执行任何操作。如果联接了行,则当前行编号将设置为联接后的行的地址。否则,当前行编号不变。

(.)kx

k 标记命令标记名称为 x 的寻址行,x 必须是一个小写 ASCII 字母 (az)。然后,地址 ´x 会在该行寻址。当前行 (.) 不变。

(.,.)l

l 命令以明确的形式将寻址行写入到标准输出。字符 (\\, \a, \b, \f, \r, \t , \v) 以对应的转义序列写入。该表中的 \n 不适用。不在该表中的非可输出字符以字符中每个字节的三位数的八进制数字形式写入(前面带反斜杠字符),最重要的字节在最前面。

长行会折叠,折叠点通过写入反斜杠/换行符表示。折叠出现的长度未指定,但应适合输出设备。每行的末尾用一个 $ 标记。在使用 /usr/xpg6/bin/ed 命令时,每行的末尾由于折叠而用一个 $ 标记,文本中的 $ 字符在写入时前面带一个反斜杠。l 命令可以附加到其他任何命令末尾,但 eEfqQrw! 除外。当前行编号设置为最后写入的行的地址。

(.,.)ma

m 移动命令将寻址行重新定位到 a 寻址的行之后。地址 0 对 a 合法,会导致将寻址行移到文件的开头。如果地址 a 在被移动的行的范围内,则出现错误。当前行 (.) 留在移动的最后一行处。

(.,.)n

n 编号命令写入寻址行,每行前面是其行编号和一个制表符。当前行 (.) 留在写入的最后一行处。n 命令可以附加到其他任何命令末尾,但 eEfqQrw! 除外。

(.,.)p

p 输出命令可将寻址行写入到标准输出。当前行 (.) 留在写入的最后一行处。p 命令可以附加到其他任何命令末尾,但 eEfqQrw! 除外。例如,dp 删除当前行并写入新的当前行。

P

P 命令会导致 ed 用星号 (*)(或字符串,在指定了 –p 的情况下)提示所有后续命令。P 命令还可以打开和关闭此模式;如果指定了 –p 选项,则模式最初是打开的,否则是关闭的。当前行不变。

q

q 退出命令会导致 ed 退出。如果自从上次写入整个缓冲区后缓冲区发生了变化,则用户会收到警告。请参见“诊断”部分。

Q

编辑器会退出,但不检查自上一次执行 w 命令以来缓冲区中是否发生变化。

($)r file

r 读取命令将 file 的内容读取到缓冲区中。如果未指定 file,则使用当前记住的已有文件名(请参见 ef 命令)。除非 file 是自从调用 ed 以来提及的第一个文件名,否则当前记住的文件名变。地址 0 对 r 合法,会导致在缓冲区的开头读取文件。如果读取成功,并且未指定 –s 选项,则读取的字符数会用以下格式写入到标准输出:

%d\n, <number of bytes read>

当前行 (.) 设置为读取的最后一行。如果将 file 替换为 !,则行的剩余部分将被视为一个 shell 命令 (sh(1)),其输出将被读取。例如,$r !ls 将当前目录附加到正在编辑的文件的末尾。这种 shell 命令不会记为当前文件名。

(.,.)s/RE/replacement/
(.,.)s/RE/replacement /count, count=[1-2047]
(.,.)s/RE/replacement/g
(.,.)s/ RE/replacement/l
(.,.)s/RE/replacement/n
(.,.)s/RE /replacement/p

s 替换命令在每个寻址行中搜索指定的 RE。可以指定零个或更多替换命令。如果在命令后出现了全局替换指示符 g,则在找到匹配项的每个行中,所有(非重叠的)匹配字符串会替换成 replacement。如果未出现该全局指示符,则仅替换出现的第一个匹配字符串。如果在命令行出现一个数字 count,则仅替换每个寻址行上出现的第 count 个匹配字符串。如果所有寻址行上的替换都失败,则显示错误。除了空格或换行符以外的任何字符都可用于替代斜杠 (/) 来分隔 REreplacement。当前行 (.) 留在发生替换的最后一行处。在 RE 内部,RE 分隔符本身就可用作文本字符(当它前面有一个反斜杠时)。另请参见下文中“文件”部分之前的最后一段。

出现在 replacement 中的和符号 (&) 替换成当前行上匹配 RE 的字符串。在此上下文中 & 的特殊意义被其前面的 \  所抑制。作为较普通的一项功能,字符 \n(其中 n 是一个数字)被替换成指定的 RE 的第 n 个子正则表达式(括在 \(\) 之间)匹配的文本。当存在嵌套在括号中的子表达式时,n 取决于从左侧开始的 \( 出现个数。当字符 %replacement 中的唯一字符时,大多数最近替换的命令中使用的 replacement 会用作当前替换命令中的 replacement。如果之前没有任何替换命令,则按此方式使用 % 将出现错误。如果 % 在包含多个字符的替换字符串中或者前面带一个 \ ,则将失去其特殊含义。对于在从头至尾的 replacement 扫描中遇到的每个反斜杠 (\),以下字符将失去其特殊含义(如果有的话)。未指定赋予除 &\% 或数字以外的任何字符的特殊含义。

可以通过在行中替换进一个换行符来拆分行。replacement 中的换行符必须在前面加 \ 进行转义。此类替换不能在 gv 命令列表中完成。当前行编号设置为执行替换的最后一行的地址。如果未执行任何替换,则当前行编号不变。如果拆分了行,可认为对每个新行执行了替换操作,以便确定新的当前行编号。即使替换字符串与其替换的字符串完全相同,也认为执行了替换。

替换命令支持以下指示符:

count

仅替换在每个寻址行上出现的第 countREcount 必须介于 1-2047 之间。

g

全局替换 RE 的所有非重叠实例,而不是仅替换第一个。如果同时指定 gcount,则不指定结果。

l

将发生替换的最后一行写入到标准输出。写入该行时所用的格式是为 l 命令指定的格式。

n

将发生替换的最后一行写入到标准输出。写入该行时所用的格式是为 n 命令指定的格式。

p

将发生替换的最后一行写入到标准输出。写入该行时所用的格式是为 p 命令指定的格式。

(.,.)ta

此命令的作用就像是 m 命令,但会将寻址行的一个副本放在地址 a(可能为 0)之后。当前行 (.) 留在复制的最后一行处。

u

u 撤消命令可以废除修改了缓冲区中的任何内容的最近命令(即最近的 acdgijmrstuvGV 命令)产生的效果。gGvV 全局命令对缓冲区所做的所有更改都作为一项更改被撤消。如果全局命令未做任何更改(例如使用 g/ RE/p),则 u 命令不会有任何效果。当前行编号设置为被撤消的命令启动前该行具有的编号。

(1,$)v/RE/command list

此命令与全局命令 g 相同,但在第一步中标记的行是与 RE 匹配的行。

(1,$)V/RE/

此命令与全局命令 G 相同,但在第一步中标记的行是与 RE 匹配的行。

(1,$)w file

w 写入命令可将寻址行写入到 file 中。如果 file 不存在,那么,除非您的文件创建掩码有其他指示,否则将使用模式 666(每个人都可读写)创建一个。请参见 sh(1) 上对 umask 特殊命令的说明。除非 file 是自从调用 ed 以来提及的第一个文件名,否则当前记住的文件名变。如果未指定文件名,则使用当前记住的已有文件名(请参见 ef 命令)。当前行 (.) 不变。如果读取成功,那么,除非用以下格式指定了 –s 选项,否则将输出写入的字符数:

"%d\n",<number of bytes written>

如果将 file 替换为 !,则行的剩余部分将被视为一个 shell 命令 (sh(1)),其标准输入为寻址行。这样的 shell 命令不会记为当前路径名。使用写入命令时带 ! 会被视为“写入整个缓冲区的最后一个 w 命令”。

(1,$)W file

此命令与上文中的 w 写入命令相同,但它将寻址行附加到 file(如果存在)的末尾。如果 file 不存在,则将创建一个,如上文中对 w 的说明中所述。

($)=

寻址行的行编号用以下格式写入到标准输出:

"%d\n"<line number>

此命令不改变当前行编号。

!shell command

行中 ! 之后的剩余部分会发送到 UNIX 系统 shell(请参见 sh(1))解释为一个命令。在该命令的文本中,未转义的字符 % 会替换成记住的文件名。如果 ! 是 shell 命令的第一个字符,则会将其替换成上一个 shell 命令的文本。因此,!! 会重复上一个 shell 命令。如果替换了 %!,则会先将修改后的行写入到标准输出,然后再执行 command! 命令在完成时将以下内容:

"!\n"

写入标准输出(除非指定了 –s 选项)。当前行编号不变。

(.+1)<new-line>

一行上只有一个地址会导致写入寻址行。只有一个换行符等效于 .+1p。这可用于在缓冲区中步进。当前行编号将设置为写入行的地址。

如果发送了一个中断信号(ASCII DEL 或 BREAK),则 ed 将写入一个 "?\n" 并返回到它的命令级别。

ed 实用程序对所有信号执行标准操作,但存在以下例外:

SIGINT

ed 实用程序中断其当前活动,将字符串 "?\n" 写入到标准输出,并返回到命令模式。

SIGHUP

如果缓冲区不为空,并且自上次写入后发生了更改,则 ed 实用程序将尝试在一个文件中写入缓冲区的一个副本。首先,使用当前目录中的名为 ed.hup 的文件。如果该操作失败,则使用 HOME 环境变量指定的目录中名为 ed.hup 的文件。在任一情况下,ed 实用程序都会退出,但不返回到命令模式。

有些大小限制会生效:一行中 512 个字符,一个全局命令列表中 256 个字符,一个文件的路径名中 255 个字符(包括斜杠)。对行数的限制取决于用户的内存量。每行占用 1 个字。

在读取文件时,ed 会放弃 ASCII 和 NUL 字符。

如果文件不以换行符终止,则 ed 将添加一个换行符,并显示一条消息解释其操作。

如果 RE 或替换字符串(例如 /)的封闭分隔符是换行符之前的最后一个字符,则将忽略该分隔符,此时将写入寻址行。以下命令对是等效的:

s/s1/s2

s/s1/s2/p

g/s1

g/s1/p

?s1

?s1?

如果输入了一个无效命令,ed 将以下字符串:

"?\n"

(如果通过 H 命令启用了帮助模式,则后跟一条解释消息)写入标准输出,然后继续处于命令模式,当前行编号不变。

选项

–pstring

允许用户指定提示字符串。缺省情况下,没有提示字符串。

–s | –;

抑制写入 erw 命令的字符计数、eq 命令的诊断以及 !shell command 后的 ! 提示。

操作数

支持下列操作数:

file

如果指定了 file,则 ed 会对路径名 file 指定的文件模拟 e 命令,然后再接受来自标准输入的命令。

用法

有关 edred 遇到大于或等于 2 GB(231 字节)文件时行为的说明,请参见 largefile(5)

环境变量

有关影响 ed 执行的以下环境变量的描述,请参见 environ(5):HOME、LANG、LC_ALL、LC_CTYPE、LC_COLLATE、LC_MESSAGES 和 NLSPATH。

退出状态

将返回以下退出值:

0

成功完成,没有任何文件或命令错误。

>0

出现错误。

文件

$TMPDIR

如果此环境变量不是 NULL,则使用其值代替 /var/tmp 作为临时工作文件的目录名称。

/var/tmp

如果存在 /var/tmp,则将其用作临时工作文件的目录名称。

/tmp

如果环境变量 TMPDIR 不存在或者为 NULL,并且 /var/tmp 不存在,则使用 /tmp 作为临时工作文件的目录名称。

ed.hup

终端挂起时,工作保存在此处。

属性

有关下列属性的说明,请参见 attributes(5)

/usr/bin/ed, /usr/bin/red

属性类型
属性值
可用性
system/core-os
CSI
Enabled(已启用)

/usr/xpg4/bin/ed

属性类型
属性值
可用性
system/xopen/xcu4
CSI
Enabled(已启用)
接口稳定性
Committed(已确定)
标准
请参见 standards(5)

/usr/xpg6/bin/ed

属性类型
属性值
可用性
system/xopen/xcu6
CSI
Enabled(已启用)
接口稳定性
Standard(标准)

另请参见

bfs(1)edit(1)ex(1)grep(1)ksh88(1)sed(1)sh(1)stty(1)umask(1)vi(1)fspec(4)attributes(5)environ(5)largefile(5)regex(5)standards(5)

诊断

?

用于命令错误。

?file

用于不可访问文件。使用 hH 帮助命令获得详细说明。

如果自从上一个 w 命令写入整个缓冲区之后缓冲区中发生了变化,则当用户试图通过 eq 命令销毁 ed 的缓冲区时,ed 将警告用户。它会写入 ? 并允许继续编辑。另一个 eq 命令将在此时生效。–s 命令行选项禁止此功能。

附注

选项虽然仍受支持,但在文档中已替换成遵循命令语法标准–s 选项(请参见 Intro(1))。

! 命令无法用于 gv 命令。

如果编辑器是从受限的 shell 调用的,则无法使用 ! 命令和 erw 命令中的 ! 转义(请参见 sh(1))。

RE 中的序列 \n 不匹配换行符。

如果编辑器输入来自于命令文件(例如 ed file < ed_cmd_file),则编辑器会在第一次失败时退出。

使用环境变量 LD_PRELOAD 装入备用的 malloc() 库可能会导致 /usr/bin/ed 出问题。