Reputation: 11
I want to make a program which will create files named as characters from the ASCII table. So 128 files from 1 to 127
I did something like this:
#!/bin/bash
temp=0;
for (( x=0; $x <= 177; x++ )) ; do
temp=$((temp+1))
if [ "$temp" = 8 ]; then
temp=$((0))
x=$((x+3))
fi
echo "$x"
`touch $'\"$x"'`
done
I know that it's written very weirdly, but what this program does is:
counting from 0 to 127 in oct (so from 0 to 177oct). The problem is that touch $'\"$x"'
doesn't work properly.
Although touch $'\101'
will make a file named "A".
Can anybody help me?
Upvotes: 0
Views: 565
Reputation: 52431
This would work:
for num in {0..127}; do
printf -v fname "\x$(printf '%x' "$num")"
touch "$fname"
done
Notice that the null character and /
are not allowed in a file name.
Here is what this does:
the outer
printf -v fname '\xHH'
stores the byte with the hex value HH
(one or two digits) in the variable fname
. This gets around the problem where for the value 10 (ASCII newline), command substitution would strip the newline (as it did in the previous revision of this answer), leaving just the empty string.
The inner
printf '%x' "$num"
prints the value of num
as a hexadecimal number, which is then used as the HH
value of the outer printf
.
Say, for example, the value of num
is decimal 80. The inner substitution does this:
$ printf '%x' 80
50
So the value of the inner command substitution is 50 (hexadecimal for 80). Now the command becomes
printf -v fname "\x50"
and because of
$ printf "\x50"
P
the next command becomes
touch P
which is what we wanted.
Upvotes: 1
Reputation: 531948
bash
doesn't provide any particularly simple way to produce a character given an ASCII code point. printf
supports converting a decimal value to a hexadecimal representation:
$ printf '%x\n' 65
A
but you need a bash
extension to convert a decimal string to a hexadecimal string to use to construct the standard format:
# null characters not allows, start with x=1, not x=0
for ((x=1; x <= 177; x++)); do
h=$(printf '%x' "$x") # e.g. 65 -> 41
c=$(printf "\\x$h") # e.g. 41 -> A
[[ $c = "/" ]] && continue # / is not a valid character for file names
touch "$c"
done
Note that backquotes are only needed capture the output of the command to use in a larger expression.
Upvotes: 0