反转文本文件中的任何行(执行rev命令)

问题描述 投票:2回答:3

我试着编写一个代码来旋转文本文件中的每一行。例如,给出下一行:

a b c

输出将是:

c b

此脚本只作为参数获取一个参数 - 文本文件的名称。另外,我想这样做会对额外的空间有所帮助。即,给出下一行:

a b c

输出将是:

c b a

注释:输出将在一个同名的新文件中,后缀为.rotate

我的代码:

#!/bin/bash

name_of_file=$1

first_step=1

while read line; do
    length_of_line=`echo -n "${line}" | wc -c`
    rotate_line=()
    index_of_line=0
    index_of_rotate=$(( length_of_line - 1 ))
        while (( ${index_of_line} < ${length_of_line} )); do
        rotate_line[${index_of_rotate}]="${line[@]:${index_of_line}:1}"
        let index_of_line++
        let index_of_rotate--
        done

        if (( ${first_step} == 1 )); then
            echo "${rotate_line[@]}" > $1.rotate1
            first_step=0
        else
            echo "${rotate_line[@]}" >> $1.rotate1
        fi
done < ${name_of_file}

问题: 我不知道为什么,但是,鉴于这一行:

a b c

输出是:

c b a

多余的空间在哪里?

评论:当我逐个字母地检查旋转数组时,它没关系(没有额外的空格) - 但是,当我用"${rotate_line[@]}"打印它时,它会添加一个新空间..为什么?

bash shell scripting
3个回答
0
投票

如果你使用declare -p rotate_line,你会看到数组实际上包含期望的值(没有额外的空格):

declare -a rotate_line='([0]="c" [1]=" " [2]="b" [3]=" " [4]="a")'

但是,在您的代码中,您使用echo "${rotate_line[@]}" > file将数组打印到文件中。这扩展到echo <item1> <item2> ...echo的默认行为是输出由空格分隔的这些参数。

一些可能的解决方法:

(IFS=; echo "${rotate_line[*]}") > file
printf '%s' "${rotate_line[@]}" $'\n' > file

您的代码还有其他几个问题,例如while read line。这可能会删除前导和尾随空格,它会破坏反斜杠。请改用while IFS= read -r line


2
投票

echo ${rotate_line[@]}在数组的每个元素之间放置一个分隔符。

while read line; do
    // get rid of old-fashioned backticks, we're sick of explaining.
    length_of_line=$(echo -n "${line}" | wc -c)
    rotate_line=()
    index_of_line=0
    index_of_rotate=$(( length_of_line - 1 ))
    while (( ${index_of_line} < ${length_of_line} ));
    do
        rotate_line[${index_of_rotate}]="${line[@]:${index_of_line}:1}"
        let index_of_line++
        let index_of_rotate--
    done
    // output characterwise
    for i in $(seq 0 $((length_of_line - 1)))
    do
        // deactivated file-in and out for easy debugging 
        echo -n "${rotate_line[i]}" # >> $1.rotate1
    done
    // for multiple lines, we need an echo here:
    echo
done # < ${name_of_file}

在这种调试友好的方式,我们可以回应单行或做

cat file | nih-rev.sh > file.rotate1 

快速测试可以快速获得答案。

因为我们通过char输出数组char,所以我们可以这样做,同时向后读取行,从而摆脱整个第二个数组,但是你想知道,什么在你的方法中不起作用,本来应该是如果我进一步重构了代码,那就模糊了。


0
投票

使用纯

x='abc'
for ((i=${#x}; i>0; i--)); do echo -n ${x:$i:1}; done

输出:

cba
© www.soinside.com 2019 - 2024. All rights reserved.