[string] How to get the last character of a string in a shell?

I have written the following lines to get the last character of a string:

str=$1
i=$((${#str}-1))
echo ${str:$i:1}

It works for abcd/:

$ bash last_ch.sh abcd/
/

It does not work for abcd*:

$ bash last_ch.sh abcd*
array.sh assign.sh date.sh dict.sh full_path.sh last_ch.sh

It lists the files in the current folder.

This question is related to string bash shell

The answer is


Try:

"${str:$((${#str}-1)):1}"

For e.g.:

someone@mypc:~$ str="A random string*"; echo "$str"
A random string*
someone@mypc:~$ echo "${str:$((${#str}-1)):1}"
*
someone@mypc:~$ echo "${str:$((${#str}-2)):1}"
g

Single line:

${str:${#str}-1:1}

Now:

echo "${str:${#str}-1:1}"

another solution using awk script:

last 1 char:

echo $str | awk '{print substr($0,length,1)}'

last 5 chars:

echo $str | awk '{print substr($0,length-5,5)}'

echo $str | cut -c $((${#str}))

is a good approach


I know this is a very old thread, but no one mentioned which to me is the cleanest answer:

echo -n $str | tail -c 1

Note the -n is just so the echo doesn't include a newline at the end.


expr $str : '.*\(.\)'

Or

echo ${str: -1}

For portability you can say "${s#"${s%?}"}":

#!/bin/sh
m=bzzzM n=bzzzN
for s in \
    'vv'  'w'   ''    'uu  ' ' uu ' '  uu' / \
    'ab?' 'a?b' '?ab' 'ab??' 'a??b' '??ab' / \
    'cd#' 'c#d' '#cd' 'cd##' 'c##d' '##cd' / \
    'ef%' 'e%f' '%ef' 'ef%%' 'e%%f' '%%ef' / \
    'gh*' 'g*h' '*gh' 'gh**' 'g**h' '**gh' / \
    'ij"' 'i"j' '"ij' "ij'"  "i'j"  "'ij"  / \
    'kl{' 'k{l' '{kl' 'kl{}' 'k{}l' '{}kl' / \
    'mn$' 'm$n' '$mn' 'mn$$' 'm$$n' '$$mn' /
do  case $s in
    (/) printf '\n' ;;
    (*) printf '.%s. ' "${s#"${s%?}"}" ;;
    esac
done

Output:

.v. .w. .. . . . . .u. 
.?. .b. .b. .?. .b. .b. 
.#. .d. .d. .#. .d. .d. 
.%. .f. .f. .%. .f. .f. 
.*. .h. .h. .*. .h. .h. 
.". .j. .j. .'. .j. .j. 
.{. .l. .l. .}. .l. .l. 
.$. .n. .n. .$. .n. .n. 

For anyone interested in a pure POSIX method:

https://github.com/spiralofhope/shell-random/blob/master/live/sh/scripts/string-fetch-last-character.sh

#!/usr/bin/env  sh

string_fetch_last_character() {
  length_of_string=${#string}
  last_character="$string"
  i=1
  until [ $i -eq "$length_of_string" ]; do
    last_character="${last_character#?}"
    i=$(( i + 1 ))
  done

  printf  '%s'  "$last_character"
}


string_fetch_last_character  "$string"

Per @perreal, quoting variables is important, but because I read this post like 5 times before finding a simpler approach to the question at hand in the comments...

str='abcd/'
echo "${str: -1}"

Output: /

str='abcd*'
echo "${str: -1}"

Output: *

Thanks to everyone who participated in this above; I've appropriately added +1's throughout the thread!


Every answer so far implies the word "shell" in the question equates to Bash.

This is how one could do that in a standard Bourne shell:

printf $str | tail -c 1

Examples related to string

How to split a string in two and store it in a field String method cannot be found in a main class method Kotlin - How to correctly concatenate a String Replacing a character from a certain index Remove quotes from String in Python Detect whether a Python string is a number or a letter How does String substring work in Swift How does String.Index work in Swift swift 3.0 Data to String? How to parse JSON string in Typescript

Examples related to bash

Comparing a variable with a string python not working when redirecting from bash script Zipping a file in bash fails How do I prevent Conda from activating the base environment by default? Get first line of a shell command's output Fixing a systemd service 203/EXEC failure (no such file or directory) /bin/sh: apt-get: not found VSCode Change Default Terminal Run bash command on jenkins pipeline How to check if the docker engine and a docker container are running? How to switch Python versions in Terminal?

Examples related to shell

Comparing a variable with a string python not working when redirecting from bash script Get first line of a shell command's output How to run shell script file using nodejs? Run bash command on jenkins pipeline Way to create multiline comments in Bash? How to do multiline shell script in Ansible How to check if a file exists in a shell script How to check if an environment variable exists and get its value? Curl to return http status code along with the response docker entrypoint running bash script gets "permission denied"