我可以使用' sed '代替' read '在一个while循环的开始,从管道输入?



我想在while循环中处理来自管道的数据。但是,数据由3个正斜杠字符而不是换行符分隔,因为我希望脚本能够处理包含换行符的输入。

# The normal `read`-driven while loop
while read -r; do
echo "$REPLY"
done

我想用sed代替read,因为它允许更灵活的读取输入。我遇到的问题是,sed在第一次通过while循环从管道中吃掉所有数据,所以循环只运行一次。

我是这样测试的

(注1:使用fd,一个文件查找工具)

# Make some files
mkdir test-{1,2}
touch 'test-1/file' $'test-2/filenwith a newline'
# Find the files we just created
# note 2: there are some wide comments here ->>>
fd -t f . test-1/ test-2/ -Hx printf '%s///' '{}' |  # List all files in test-1 and test-2, putting "///" at the end of each one
sed 's/./n&/g' |  # prepend each character with a newline so it can be read by `sed` one character at a time
while v="$(sed -n ':loop; N; s|n(.)$|1|; ////$/!{b loop}; s|///$||; p;Q;')"; do
#       ^^^^^^ sed script that prints everything up to the "///"
#              that notates the end of the current path, then exits
#              without processing more than the first one (so the
#              rest can be processed in future loop iterations)
if [ -n "$v" ]; then
# print the file name
echo "$v"
else
# if v is empty
break
fi
done

这个的输出是

test-1/file

…表示sed只运行一次,因为输出应该是这样的:

test-1/file
test-2/file
with a newline

有没有办法让sed表现得像read,所以它可以在while循环中使用?是否有一个神奇的属性,允许read这样做,因为它是一个内置的?

我猜你是在问XY问题。

我希望脚本能够处理其中有换行符的输入。

使用零分隔流。

# I would do standard: find . -type f -print0 |
fd -H0t f . |
while IFS= read -r file; do
echo "$line"
done

要处理以3个斜杠分隔的流,您将用0字节替换3个斜杠,然后读取以0分隔的流。如果你的流中有实际的零字节,这可能是一个问题,但这是在文件名不可能的情况下。

... |
sed 's|///|x00|g' |
while IFS= read -r file; do

相关内容

  • 没有找到相关文章

最新更新