我想读取一个文件并将其保存在变量中,但我需要保留这个变量,而不是直接打印出文件。 我怎样才能做到这一点呢?我已经写了这个脚本,但它并不是我所需要的。
#!/bin/sh
while read LINE
do
echo $LINE
done <$1
echo 11111-----------
echo $LINE
在我的脚本中,我可以把文件名作为一个参数,因此,如果文件包含"aaaa",例如,它会打印出这个。
aaaa
11111-----
但这只是把文件打印到屏幕上,而我想把它保存到一个变量中!有什么简单的方法可以做到吗? 有什么简单的方法可以做到这一点吗?
在跨平台中,你使用的是最低公称的`sh'。
#!/bin/sh
value=`cat config.txt`
echo "$value"
在bash
或zsh
中,将整个文件读入一个变量,而不调用cat
。
#!/bin/bash
value=$(<config.txt)
echo "$value"
在bash
或zsh
中调用cat
来读取文件,会被认为是无用的猫的使用。
请注意,不需要引用命令替换来保留新行。
两个重要的隐患
到目前为止,其他答案都忽略了这一点。
1.从命令扩展中删除尾部换行 1.去除NUL字符
从命令扩展中删除尾部新行。
这是个问题。
value="$(cat config.txt)"
类型的解决方案,但对于基于 "读 "的解决方案则没有问题。
命令扩展会删除尾部的新行。
S="$(printf "a\n")"
printf "$S" | od -tx1
输出。
0000000 61
0000001
这就打破了从文件中读取的天真方法。
FILE="$(mktemp)"
printf "a\n\n" > "$FILE"
S="$(<"$FILE")"
printf "$S" | od -tx1
rm "$FILE"
POSIX解决方法:在命令扩展中附加一个额外的字符,然后再将其删除。
S="$(cat $FILE; printf a)"
S="${S%a}"
printf "$S" | od -tx1
输出。
0000000 61 0a 0a
0000003
几乎是POSIX的解决方法。ASCII编码。见下文。
NUL字符删除
这影响了扩展和读
的解决方案,我不知道有什么好的解决方法。
例子。
printf "a\0b" | od -tx1
S="$(printf "a\0b")"
printf "$S" | od -tx1
输出。
0000000 61 00 62
0000003
0000000 61 62
0000002
哈,我们的NUL不见了!
解决办法。
ASCII编码。见下文。
使用bash扩展的$""
字样。
S=$"a0b"。
printf "$S" | od -tx1
只对字面意义起作用,所以对从文件中读取信息没有用。
解决隐患的方法。
在变量中存储一个uuencode base64编码的文件版本,并在每次使用前进行解码。
FILE="$(mktemp)"
printf "a\0\n" > "$FILE"
S="$(uuencode -m "$FILE" /dev/stdout)"
uudecode -o /dev/stdout <(printf "$S") | od -tx1
rm "$FILE"
输出。
0000000 61 00 0a
0000003
uuencode和udecode是POSIX 7,但在Ubuntu 12.04中默认没有(sharutils
包)...除了写到另一个文件外,我没有看到POSIX 7对bash进程<()
替换扩展的替代方案...
当然,这样做既慢又不方便,所以我想真正的答案是:如果输入文件可能包含NUL字符,就不要使用Bash。