Skip to content
SysTutorials
  • SysTutorialsExpand
    • Linux & Systems Administration Academy
    • Web3 & Crypto Academy
    • Programming Academy
    • Systems & Architecture Academy
  • Subscribe
  • Linux Manuals
  • Search
SysTutorials
Linux & Systems Administration

Getting the Next ASCII Character in Bash

ByDavid Yang Posted onMar 24, 2018Apr 11, 2026 Updated onApr 11, 2026

Sometimes you need to find the ASCII character that comes after a given character. This is useful for generating sequences, creating substitution ciphers, or manipulating character ranges in shell scripts.

Using printf with ASCII Values

The most portable and straightforward approach uses printf to convert between characters and their ASCII numeric values:

#!/bin/bash

get_next_char() {
    local char="$1"
    local ascii

    # Get ASCII value of the character
    ascii=$(printf '%d' "'$char")

    # Increment and convert back to character
    printf "\\$(printf '%03o' $((ascii + 1)))"
}

# Example usage
echo "Next char after 'A' is: $(get_next_char 'A')"
echo "Next char after 'z' is: $(get_next_char 'z')"
echo "Next char after '9' is: $(get_next_char '9')"

The printf '%d' "'$char" syntax extracts the ASCII value by treating the character as a string literal. The single quote before the character forces printf to interpret it as an ASCII value.

Handling Edge Cases

When working near the boundaries of the ASCII table, you may want to validate or handle wraparound:

#!/bin/bash

get_next_char_safe() {
    local char="$1"
    local ascii

    ascii=$(printf '%d' "'$char")

    # Check if we're at ASCII 127 (DEL character)
    if [[ $ascii -ge 127 ]]; then
        echo "Warning: Character at ASCII boundary" >&2
        return 1
    fi

    printf "\\$(printf '%03o' $((ascii + 1)))"
}

# Generate a character range
generate_range() {
    local start="$1"
    local end="$2"
    local current="$start"
    local current_ascii end_ascii

    current_ascii=$(printf '%d' "'$current")
    end_ascii=$(printf '%d' "'$end")

    while [[ $current_ascii -le $end_ascii ]]; do
        printf "\\$(printf '%03o' $current_ascii)"
        ((current_ascii++))
    done
}

# Generate a-z
echo "Lowercase letters:"
generate_range 'a' 'z'
echo ""

Using od for Inspection

To verify ASCII values and see the relationship between characters:

# See ASCII value of a character
echo -n 'A' | od -An -td1

# See multiple characters
echo -n 'ABC' | od -An -td1

Practical Example: ROT13-style Cipher

Here’s a real-world use case that rotates characters within their range:

#!/bin/bash

rotate_char() {
    local char="$1"
    local shift="${2:-1}"
    local ascii new_ascii

    ascii=$(printf '%d' "'$char")
    new_ascii=$((ascii + shift))

    # For lowercase letters, wrap around
    if [[ $ascii -ge 97 && $ascii -le 122 ]]; then
        new_ascii=$(( (ascii - 97 + shift) % 26 + 97 ))
    # For uppercase letters, wrap around
    elif [[ $ascii -ge 65 && $ascii -le 90 ]]; then
        new_ascii=$(( (ascii - 65 + shift) % 26 + 65 ))
    fi

    printf "\\$(printf '%03o' $new_ascii)"
}

# Test
echo "$(rotate_char 'a' 1)$(rotate_char 'b' 1)$(rotate_char 'c' 1)"  # bcd
echo "$(rotate_char 'z' 1)$(rotate_char 'Z' 1)"  # aA (wraps around)

Performance Considerations

For processing large strings character-by-character, the printf approach works but can be slow. Use tools like tr when possible:

# Simple character substitution (much faster for bulk operations)
echo "Hello" | tr 'a-z' 'b-za'

# Or with sed for more complex transformations
echo "Hello" | sed 's/./\\x27/g'  # Replace with single quotes

Compatibility

The printf method works reliably across Bash 3.0+, making it suitable for scripts that need to run on older systems. The $(...) command substitution syntax is POSIX-compliant. If you need maximum portability, avoid [[ conditionals and use [ ] instead, though [[ is standard in Bash.

Post Tags: #ASCII#Bash#C#Command#compatibility#convert#How to#Linux#performance#POSIX#Programming#shell#systems#Tutorial#www#X

Post navigation

Previous Previous
Disabling DHCP in dnsmasq on Linux
NextContinue
Configuring Zimbra Web Service Hostname and Port

Categories

  • AI Engineering (4)
  • Algorithms & Data Structures (14)
  • Blockchain & Cryptocurrency (16)
  • Code Optimization (8)
  • Databases & Storage (11)
  • Design Patterns & Architecture (18)
  • Development Best Practices (104)
  • Functional Programming (4)
  • Languages & Frameworks (97)
  • Linux & Systems Administration (726)
  • Linux Manuals (56,856)
    • Linux Manuals session 1 (13,267)
    • Linux Manuals session 2 (502)
    • Linux Manuals session 3 (32,502)
    • Linux Manuals session 4 (117)
    • Linux Manuals session 5 (1,724)
    • Linux Manuals session 7 (887)
    • Linux Manuals session 8 (4,721)
    • Linux Manuals session 9 (3,136)
  • Linux System Configuration (33)
  • Object-Oriented Programming (4)
  • Programming Languages (129)
  • Scripting & Utilities (68)
  • Security & Cryptography (17)
  • System Administration & Cloud (33)
  • Systems & Architecture (36)
  • Testing & DevOps (33)
  • Web Development (25)

SysTutorials, Terms, Privacy

  • SysTutorials
    • Linux & Systems Administration Academy
    • Web3 & Crypto Academy
    • Programming Academy
    • Systems & Architecture Academy
  • Subscribe
  • Linux Manuals
  • Search