huashui
huashui

Reputation: 1858

Error about the tr command of linux shell

When I type this command :

$ echo 1234567890 | tr '9-0' '9876'

It says "tr: range-endpoints of '9-0' are in reverse collating sequence order". What does this mean? Does it means I can only type like "0-9"?

Upvotes: 2

Views: 6636

Answers (2)

Kajukenbo
Kajukenbo

Reputation: 275

POSIX character classes are "in order" and cannot be reversed in such a manner.

Make a new "class" of your own and put it in the order you need.

You can use your customized class in tr as a variable.

Remember that classes are essentially positional, not ordinal:

$ nums="0123456789" && rev="9876543210" ; echo $nums ; echo $rev
0123456789
9876543210

$ rev="9876543210" && echo 54321 | tr "$nums" "$rev"
45678

In other words, 5-4-3-2-1 does not automatically "flip" into 1-2-3-4-5.

This should give you the idea about "reversing" a class:

#!/bin/sh

LC_ALL=C
i=0
true > members
while [ "$i" -le 127 ]
do
    echo "$i" | awk '{ printf "%c", $0 }' | awk '/[[:digit:]]/ { print }'
    # echo "$i" | awk '{ printf "%c", $0 }' | grep '[[:digit:]]' 
    i=$(( i + 1 ))
done >> members

str=`printf "%s\n" "$(tr -d '\n' < members)"`
rev=""

# finding the length of string
len="${#str}"

# traverse the string in reverse order
while [ $len -ne 0 ]
do
    rev="${rev}"`echo "${str}" | cut -c $len`
    len=$(( len -1 ))
done

echo "$str"
echo "$rev"

Reverse sequence for tr

Upvotes: 0

Paul Tomblin
Paul Tomblin

Reputation: 182762

Yes, that's exactly what it means. '9-0' isn't a range, anymore than 'z-a' is a range. Otherwise, how does it know whether you mean 0-9 or the entire unicode range starting from 9, going to the top of the range and wrapping around back to 0?

Upvotes: 5

Related Questions