?*更新日志?
*2023-12-18 1.根據(jù)[美] 威廉·肖特斯 (Willian?shotts)所著《Linux命令行大全(第2版)》
? ? ? ? ? ? ? ? ? ? ? ? 更新了-e、-i、-r選項的說明? ? ? ? ? ? ? ? ? ? ? 2.更新了 2.8 的實例,增加了gif動圖
? ? ? ? ? ? ? ? ? ? ? 3.補充了-i的應用實例 2.12
目錄
- 目錄
- 0 前言
- 1 read命令的功能、格式、返回值和注意
-
- 1.1?命令功能
- 1.2 命令格式
- 1.3 返回值
- 1.4 注意事項
- 2?命令應用實例
-
- 2.1?一次讀入多個變量值
- 2.2?不指定變量名
- 2.3?測試read命令的返回值
- 2.3?指定輸入時限并進行相應處理
- 2.4 -t 指定結(jié)束符
- 2.5 -n 指定輸入字符個數(shù)
- 2.6 -N?指定輸入字符個數(shù)
- 2.7 -s不回顯來自終端的輸入
- 2.8 -e使用命令補全功能
- 2.9 -r?允許輸入的值中包含的反斜杠\也作為值輸出
- 2.10?-a 讀取數(shù)組值
- 2.11 -u指定文件說明符
- 2.12 -i 使用初始值
?
0 前言
在交互式編程中,有時我們需要用戶先通過鍵盤來輸入數(shù)據(jù),然后程序根據(jù)用戶輸入的數(shù)據(jù)來做相應的處理。
在之前的學習中,我們已經(jīng)使用read命令來讀取用戶通過鍵盤輸入的數(shù)據(jù),但對read命令沒有做進一步的說明。
現(xiàn)在我們來研究一下read命令的詳細用法。
1 read命令的功能、格式、返回值和注意
我們可以使用命令?help read??來查看seq命令的幫助信息:
purleEndurer @ bash ~ $ help read
read: read [-ers] [-a array] [-d delim] [-i text] [-n nchars] [-N nchars] [-p prompt] [-t timeout] [-u fd] [name ...]
? ? Read a line from the standard input and split it into fields.
? ??
? ? Reads a single line from the standard input, or from file descriptor FD
? ? if the -u option is supplied. ?The line is split into fields as with word
? ? splitting, and the first word is assigned to the first NAME, the second
? ? word to the second NAME, and so on, with any leftover words assigned to
? ? the last NAME. ?Only the characters found in $IFS are recognized as word
? ? delimiters.
? ??
? ? If no NAMEs are supplied, the line read is stored in the REPLY variable.
? ??
? ? Options:
? ? ? -a array ?assign the words read to sequential indices of the array
? ? ? ? ? ? ? ? variable ARRAY, starting at zero
? ? ? -d delim ?continue until the first character of DELIM is read, rather
? ? ? ? ? ? ? ? than newline
? ? ? -e ? ? ? ? ? ? ? ?use Readline to obtain the line in an interactive shell
? ? ? -i text ? Use TEXT as the initial text for Readline
? ? ? -n nchars return after reading NCHARS characters rather than waiting
? ? ? ? ? ? ? ? for a newline, but honor a delimiter if fewer than NCHARS
? ? ? ? ? ? ? ? characters are read before the delimiter
? ? ? -N nchars return only after reading exactly NCHARS characters, unless
? ? ? ? ? ? ? ? EOF is encountered or read times out, ignoring any delimiter
? ? ? -p prompt output the string PROMPT without a trailing newline before
? ? ? ? ? ? ? ? attempting to read
? ? ? -r ? ? ? ? ? ? ? ?do not allow backslashes to escape any characters
? ? ? -s ? ? ? ? ? ? ? ?do not echo input coming from a terminal
? ? ? -t timeout ? ? ? ?time out and return failure if a complete line of input is
? ? ? ? ? ? ? ? not read withint TIMEOUT seconds. ?The value of the TMOUT
? ? ? ? ? ? ? ? variable is the default timeout. ?TIMEOUT may be a
? ? ? ? ? ? ? ? fractional number. ?If TIMEOUT is 0, read returns success only
? ? ? ? ? ? ? ? if input is available on the specified file descriptor. ?The
? ? ? ? ? ? ? ? exit status is greater than 128 if the timeout is exceeded
? ? ? -u fd ? ? ? ? ? ? read from file descriptor FD instead of the standard input
? ??
? ? Exit Status:
? ? The return code is zero, unless end-of-file is encountered, read times out,
? ? or an invalid file descriptor is supplied as the argument to -u.
readarray: readarray [-n count] [-O origin] [-s count] [-t] [-u fd] [-C callback] [-c quantum] [array]
? ? Read lines from a file into an array variable.
? ??
? ? A synonym for `mapfile'.
readonly: readonly [-aAf] [name[=value] ...] or readonly -p
? ? Mark shell variables as unchangeable.
? ??
? ? Mark each NAME as read-only; the values of these NAMEs may not be
? ? changed by subsequent assignment. ?If VALUE is supplied, assign VALUE
? ? before marking as read-only.
? ??
? ? Options:
? ? ? -a ? ? ? ?refer to indexed array variables
? ? ? -A ? ? ? ?refer to associative array variables
? ? ? -f ? ? ? ?refer to shell functions
? ? ? -p ? ? ? ?display a list of all readonly variables and functions
? ??
? ? An argument of `--' disables further option processing.
? ??
? ? Exit Status:
? ? Returns success unless an invalid option is given or NAME is invalid.
purleEndurer @ bash ~ $?
?1.1?命令功能
從標準輸入或-u 選項指定的文件描述符讀取一行。該行被拆分為多個字段,就像單詞拆分一樣,第一個單詞分配給第一個?變量,第二個單詞分配給第二個?變量,依此類推,任何剩余的單詞都分配給最后一個?變量。如果未提供?變量名,則讀取的行存儲在 REPLY 變量中。
只有在 $IFS 中找到的字符才會被識別為單詞分隔符。
1.2 命令格式
?read [-ers] [-a?索引數(shù)組名] [-d 結(jié)束符] [-i 初始字符串] [-n 字符數(shù)] [-N 字符數(shù)] [-p 提示字符串] [-t 超時秒數(shù)] [-u 文件描述符] [變量名?...]
- 選項說明?
選項 | 說明 | 備注 |
---|---|---|
-a?索引數(shù)組名 | 將讀取的單詞從下標零開始分配給數(shù)組名指定的?索引數(shù)組,默認是以空格為分割符 | array |
-d 結(jié)束符 | 讀取數(shù)據(jù),直至結(jié)束符,而不是換行符 | delimiter |
-e | 使用 在交互式 shell 中獲取用戶輸入行,在輸入的時候可以使用命令補全功能 | |
-i 初始字符串 | 使用初始字符串作為 用戶輸入行 的初始值 需要與-e選項一起使用 |
initialize |
-n 字符數(shù) | 在讀取指定的字符數(shù)后返回,除非遇到定界符、換行符或讀取超時,定界符包括\t(tab鍵)。 | number |
-N 字符數(shù) | 在讀取指定的字符數(shù)后返回,除非遇到 EOF 或讀取超時 與 -n 不同的是,-N 會忽略任何定界符。 |
number |
-p 提示字符串 | 先輸出提示字符串,再讀取數(shù)據(jù) | prompt |
-r | 不允許反斜杠轉(zhuǎn)義任何字符 | raw mode |
-s | 不回顯來自終端的輸入 | silence |
-t 超時秒數(shù) | 指定輸入字符的等待時間。 如果在 超時秒數(shù) 內(nèi)未讀取完整的輸入行,則超時并返回失敗。 超時秒數(shù) 可以是小數(shù)。 |
timeout |
-u 文件描述符 | 從指定的文件描述符讀入數(shù)據(jù) | use |
1.3 返回值
命令正常執(zhí)行時返回值為零,
如果遇到文件末尾、讀取超時或提供無效文件描述符作為 -u 的參數(shù)時,返回值不為零。
如果讀取超時,返回值?將?大于 128。
1.4 注意事項
- 變量名列表?應該放在?命令的最后。
- 變量名之間以空格分隔。
- -i選項需要與-e選項一起使用才有用
2?命令應用實例
2.1?一次讀入多個變量值
例:提示用戶輸入3個整數(shù),作為a、c、c?三個變量的值
purpleEndurer @ bash ~ $ read -p "Enter there integers:" a ?b c
Enter there integers:1 2 3
purpleEndurer @ bash ~ $ echo a=$a b=$b c=$c
a=1 b=2 c=3
purpleEndurer @ bash ~ $ read -p "Enter there integers:" a ?b c
Enter there integers:1 2 3 4 5 6
purpleEndurer @ bash ~ $ echo a=$a b=$b c=$c
a=1 b=2 c=3 4 5 6
purpleEndurer @ bash ~ $?
當我們輸入1 2 3?這三個整數(shù)后,變量a的值為1,變量b的值為2,變量c的值為3。
當我們輸入1 2 3 4 5 6?這六個整數(shù)后,由于我們只給了a、b、c三個變理名,所以變量a的值為1,變量b的值為2,而變量c的值為:3 4 5 6。
2.2?不指定變量名
例:提示用戶輸入3個整數(shù),但沒指定變量名
purpleEndurer @ bash ~ $ echo $REPLY
purpleEndurer @ bash ~ $ read -p "Enter there integers:"
Enter there integers:1 2 3
purpleEndurer @ bash ~ $ echo $REPLY?
1 2 3
purpleEndurer @ bash ~ $?
由于我們沒有指定變量名,所以輸入的值1 2 3保存在變量REPLY中。
2.3?測試read命令的返回值
例:提示用戶輸入名字,輸入時間限定為10秒鐘
purpleEndurer @ bash ~ $ read -t 10 -p "Enter your name:"
Enter your name:pe
purpleEndurer @ bash ~ $ echo $?
0
purpleEndurer @ bash ~ $ read -t 10 -p "Enter your name:"
Enter your name:purpleEndurer @ bash ~ $ echo $?
142
purpleEndurer @ bash ~ $ read -t 10 -p "Enter your name:"
Enter your name:purpleEndurer @ bash ~ $ echo $?
1
purpleEndurer @ bash ~ $ read -t 10 -p "Enter your name:"
Enter your name:^C
purpleEndurer @ bash ~ $ echo $?
130
purpleEndurer @ bash ~ $?
當我們在10秒鐘內(nèi)輸入用戶名pe并回車,read命令正常執(zhí)行,返回值為0
當我們未在10秒鐘內(nèi)輸入用戶名,read命令返回值為142,大于128
當我們輸入^D時,read命令返回值為1
當我們輸入^C時,read命令返回值為130
2.3?指定輸入時限并進行相應處理
例:編寫一個腳本,提示用戶在5秒鐘內(nèi)輸入名字,如果用戶輸入名字,則對用戶進行問候,否則提示用戶沒有輸入名字。
腳本內(nèi)容如下:
read ?-t 5 -p "Enter you name in 5 seconds:" name # 提示用戶在5秒鐘內(nèi)輸入名字并保存在變量name中
if [ $? == 0 ]; then # 如果用戶在5秒鐘內(nèi)輸入了名字,那么read命令返回值為0
? ?echo Hello, $name. # 對用戶進行問候
else
? ?echo -e "\nYou do not enter your name." # 提示用戶沒有輸入名字
fi
purpleEndurer @ bash ~ $ cp /dev/stdin a.sh
read ?-t 5 -p "Enter you name in 5 seconds:" name
if [ $? == 0 ]; then
? ?echo Hello, $name.
else
? ?echo -e "\nYou do not enter your name."
fi
purpleEndurer @ bash ~ $ cat a.sh
read ?-t 5 -p "Enter you name in 5 seconds:" name
if [ $? == 0 ]; then
? ?echo Hello, $name.
else
? ?echo -e "\nYou do not enter your name."
fi
purpleEndurer @ bash ~ $ . a.sh
Enter you name in 5 seconds:pe
Hello, pe.
purpleEndurer @ bash ~ $ . a.sh
Enter you name in 5 seconds:
You do not enter your name.
purpleEndurer @ bash ~ $?
2.4 -t 指定結(jié)束符
例?讀取用戶輸入值存入變量a,指定#作為結(jié)束符
purpleEndurer @ bash ~ $ read -d '#' a
ab#purpleEndurer @ bash ~ $ echo $a
ab
purpleEndurer @ bash ~ $?
?
當我們輸入ab#時,讀取結(jié)束。變量a的值為ab。
2.5 -n 指定輸入字符個數(shù)
例?讀取5個字符,分別保存到變量a和b
purpleEndurer @ bash ~ $ read -n 5 a b
12345purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12345 b=
purpleEndurer @ bash ~ $ read -n 5 a b
12 34purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12 b=34
purpleEndurer @ bash ~ $ read -n 5 a b
1 ? ? ? 234purpleEndurer @ bash ~ $ echo a=$a b=$b
a=1 b=234
purpleEndurer @ bash ~ $ read -n 5 a b
12
purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12 b=
purpleEndurer @ bash ~ $ read -n 5 a b
123^C
purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12 b=
purpleEndurer @ bash ~ $?
當我們輸入12345時,變量a的值為12345,變量b值為空
當我們輸入12空格34時,變量a的值為12,變量b值為34
當我們輸入1[Tab]234時,變量a的值為1,變量b值為234
當我們輸入12回車時,變量a的值為12,變量b值為空
當我們輸入123^C時,read命令被終止了,所以變量a的值沒有變化,仍為12,變量b值沒有變化,仍為空
2.6 -N?指定輸入字符個數(shù)
例?讀取5個字符,分別保存到變量a和b
purpleEndurer @ bash ~ $ read -N 5 a b
12 ? ? ?34purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12 34 b=
purpleEndurer @ bash ~ $ read -N 5 a b
12 34purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12 34 b=
purpleEndurer @ bash ~ $ read -d '#' -N 5 a b
12#34purpleEndurer @ bash ~ $ echo a=$a b=$b
a=12#34 b=
purpleEndurer @ bash ~ $?
?
?當我們輸入12[Tab]34時,變量a的值為12? ? 34,變量b值為空
當我們輸入12空格34時,變量a的值為12 34,變量b值為空
即使我們用-t '#' 選項指定#作為結(jié)束符,輸入12#34,結(jié)果變量a的值為12#34,變量b值為空?
- 看來使用-N選項后,空格或[Tab]不再作為字符串值的分隔符,-t選項也不起作用,這樣只能將讀取值存到第1個變量中了。
2.7 -s不回顯來自終端的輸入
例:提示用戶輸入密碼,輸入時不回顯,輸入完成后再顯示用戶輸入的密碼。
purpleEndurer @ bash ~ $ read -s -p "Enter your password:" p
Enter your password:purpleEndurer @ bash ~ $ echo Your password is $p
Your password is abcd
purpleEndurer @ bash ~ $?
當用戶輸入密碼abcd時并不回顯,按回車鍵后,才顯示用戶輸入的密碼是abcd。
2.8 -e使用命令補全功能
PurpleEndurer @ bash ~ $ ls
Code
PurpleEndurer @ bash ~ $ read -e a
Code/
PurpleEndurer @ bash ~ $ echo $a
Code/
PurpleEndurer @ bash ~ $ read -e a
cde
PurpleEndurer @ bash ~ $ echo $a
cde
PurpleEndurer @ bash ~ $?
我們先用ls命令查看當前目錄內(nèi)容,存在一個名Code的文件或文件夾
然后我們用命令?read -e a?來讀取輸入存到變量a
在我們輸入大寫字符C后按Tab鍵啟用命令補全功能,輸入行的內(nèi)容就變?yōu)镃ode/,按下回車鍵。
再用echo $a?查看變量a的值為Code/
在我們輸入大寫字符C后按Tab鍵啟用命令補全功能,輸入行的內(nèi)容就變?yōu)镃ode/,我們用刪除鍵Backspace刪除Code/,輸入cde回車,再用echo $a?查看變量a的值為cde
2.9 -r?允許輸入的值中包含的反斜杠\也作為值輸出
purpleEndurer @ bash ~/Code $ read a
//\c
purpleEndurer @ bash ~/Code $ echo $a
//c
purpleEndurer @ bash ~/Code $ read -r a
//\c
purpleEndurer @ bash ~/Code $ echo $a
//\c
purpleEndurer @ bash ~/Code $?
對于命令 read a,輸入? ?//\c,存儲到變量a的值為 //C,不包含反斜杠\。
對于命令 rread -r a,輸入? ?//\c,存儲到變量a的值為 //\C,包含反斜杠\。
2.10?-a 讀取數(shù)組值
數(shù)組是最常用的一種數(shù)據(jù)結(jié)構(gòu),在之前的
Linux shell編程學習筆記15:定義數(shù)組、獲取數(shù)組元素值和長度、數(shù)組拼接或合并_linux獲取數(shù)組長度-CSDN博客https://blog.csdn.net/Purpleendurer/article/details/134009982
和
Linux shell編程學習筆記16:bash中的關(guān)聯(lián)數(shù)組-CSDN博客https://blog.csdn.net/Purpleendurer/article/details/134053506中我們學習了Lininux Shell編程中的數(shù)組的定義和賦值的方法,其中對數(shù)組元素的賦值方法 ,我們主要介紹了在定義數(shù)組時同時進行初始化和定義數(shù)組后用賦值語句來賦值兩種方法。
現(xiàn)在我們也可以用read命令來將用戶輸入的值存儲到數(shù)組
例:從鍵盤讀取輸入存入數(shù)組a
purpleEndurer @ bash ~/Code $ read -a a↙
1 2 3↙
purpleEndurer @ bash ~/Code $ echo ${a[*]}↙
1 2 3
purpleEndurer @ bash ~/Code $ echo ${a[0]}↙
1
purpleEndurer @ bash ~/Code $?
i當我們輸入 1 2 3,那么 a[0]=1,a[1]=2,a[2]=3
可惜的是,read命令不能將用戶輸入存儲到關(guān)聯(lián)數(shù)組
purpleEndurer @ bash ~/Code $ declare -A A↙
purpleEndurer @ bash ~/Code $ read -a A↙
a b c↙
bash: read: A: cannot convert associative to indexed array
purpleEndurer @ bash ~/Code $?
我們先用命令 聲明一個關(guān)聯(lián)數(shù)組A
然后用命令?來讀取用戶輸入存儲到關(guān)聯(lián)數(shù)組A,但是出錯了:bash: read: A: cannot convert associative to indexed array
2.11 -u指定文件說明符
例:將文件a.txt和b.txt的內(nèi)容逐行拼接顯示。
purpleEndurer @ bash ~ $ cp /dev/stdin a.txt↙
111↙
222↙
333↙
444↙
purpleEndurer @ bash ~ $ cp /dev/stdin b.txt↙
aaa↙
bbb↙
ccc↙
ddd↙
eee↙
purpleEndurer @ bash ~ $ while read -u3 i && read -u4 j;do echo $i $j; done 3<a.txt 4<b.txt↙
111 aaa
222 bbb
333 ccc
444 ddd
purpleEndurer @ bash ~ $?
如果我們希望在每一行前顯示行號,那么我們可以增加一個變量n用來記錄當前行數(shù):
purpleEndurer @ bash ~ $ n=1;while read -u3 i && read -u4 j;do echo Line $n: ?$i $j;n=$[ $n + 1 ]; ?done 3<a.txt 4<b.txt↙
Line 1: 111 aaa
Line 2: 222 bbb
Line 3: 333 ccc
Line 4: 444 ddd
purpleEndurer @ bash ~ $?
2.12 -i 使用初始值
例 提示用戶輸入用戶名 存儲到變量a中,用戶名初始值為?Anonymous
PurpleEndurer @ bash ~ $ read -p 'Enter your name:' -i 'Anonymous' a?
Enter your name:↙
PurpleEndurer @ bash ~ $ echo $aPurpleEndurer @ bash ~ $ read -p 'Enter your name:' -i 'Anonymous' -e a?
Enter your name:Anonymous↙
PurpleEndurer @ bash ~ $ echo $a↙
Anonymous
PurpleEndurer @ bash ~ $?read -p 'Enter your name:' -i 'Anonymous' -e a?
Enter your name:abc↙
PurpleEndurer @ bash ~ $ echo $a↙
abc
PurpleEndurer @ bash ~ $?
在執(zhí)行 命令? read -p 'Enter your name:' -i 'Anonymous' a??時,雖然我們使用 -i??'Anonymous'選項,但執(zhí)行時并沒有顯示初始值?Anonymous,我們直接回車,變量a的值為空
在執(zhí)行 命令? read -p 'Enter your name:' -i 'Anonymous' -e a???時,我們在上面的命令中增加了?-e選項,在執(zhí)行時就顯示出初始值?Anonymous,我們直接回車,變量a的值為就為?Anonymous文章來源:http://www.zghlxwxcb.cn/news/detail-760771.html
在執(zhí)行 命令? read -p 'Enter your name:' -i 'Anonymous' -e a???時,我們在上面的命令中增加了?-e選項,在執(zhí)行時就顯示出初始值?Anonymous,我們按刪除鍵Backspace刪除?Anonymous,輸入abc回車,變量a的值為abc文章來源地址http://www.zghlxwxcb.cn/news/detail-760771.html
到了這里,關(guān)于Linux shell編程學習筆記36:read命令的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!