BASH:如何将带有空列的制表符分隔行从文件读取到数组中

StO*_*cha 0 arrays bash tabs

应分析 txt 文件:它有许多行,每行有 20 个字段,由制表符分隔,每个字段可以包含任何类型的数据(整数、浮点数、日期时间、文本也包含空白和“”等),除此之外字段可以是空的,例如这样的一行会像

111TABTABWalterTAB11.1234TABThis is a sample TextTAB"Another sample"TABTABTAB555...
Run Code Online (Sandbox Code Playgroud)

如何将文件的每一行读入具有 20 列的数组 arrLine,例如

  • arrLine(0)=111
  • arrLine(1)=
  • arrLine(2)=沃尔特
  • ...

我想这个建议

while IFS=$'\t' read -r -a arrLine; do
    echo "${#arrLine[@]} items: ${arrLine[@]}"
    echo "${arrLine[3]} || ${arrLine[4]} || ${arrLine[5]}"
done < "test.txt"
Run Code Online (Sandbox Code Playgroud)

但空列不会填充到数组中。

谢谢!

Soc*_*owi 5

随着IFS="anyWithespaceCharacter" read有没有办法读其他两个领域之间的空场; 对于非空白字符,这会起作用。这种不一致的行为是由posix决定的:

术语“IFS 空格”用于表示 IFS 值中的任何空格字符序列(零个或多个实例)(例如,如果 IFS 包含 <space>/<comma>/<tab>,任何<space> 和 <tab> 字符序列被视为 IFS 空白)。

  • IFS 空白在输入的开头和结尾应被忽略。
  • 非 IFS 空格的 IFS 字符输入中的每个出现,以及任何相邻的 IFS 空格,都应界定一个字段,如前所述。
  • 非零长度的 IFS 空白应界定一个字段。

但是您仍然可以使用mapfile将每一行拆分为字段:

while IFS= read -r line; do
    mapfile -td $'\t' arrLine < <(printf %s "$line")
    declare -p arrLine # prints the array for debugging
done < test.txt
Run Code Online (Sandbox Code Playgroud)

或者,将空白分隔符(在本例中为制表符)替换为未出现在输入中的任何其他非空白字符。在这种情况下,我们使用 ascii 符号“单位分隔符” \037

while IFS=$'\037' read -ra arrLine; do
    declare -p arrLine # prints the array for debugging
done < <(tr \\t \\037 < test.txt)
Run Code Online (Sandbox Code Playgroud)

  • 为了可视化数组 arrLine 的内容,我建议:`declare -p arrLine` (3认同)