CCharacter Functions (ctype.h)

Character Functions (ctype.h)

The <ctype.h> header provides small, fast functions for classifying and converting individual characters — checking whether a character is a letter, a digit, whitespace, and so on, plus converting between upper and lower case. These functions show up constantly when validating or transforming text one character at a time.
Classification Functions

Function

Returns true (nonzero) when the character is...

isalpha(c)

A letter, a-z or A-Z

isdigit(c)

A decimal digit, 0-9

isspace(c)

Whitespace: space, tab, newline, carriage return, etc.

isupper(c)

An uppercase letter, A-Z

islower(c)

A lowercase letter, a-z

isalnum(c)

A letter or a digit (alphanumeric)

ispunct(c)

A punctuation character (not alphanumeric, not whitespace, not a control character)

Case Conversion
toupper(c) returns the uppercase version of c if it is a lowercase letter (otherwise it returns c unchanged). tolower(c) does the reverse.

C
#include <stdio.h>
#include <ctype.h>

int main(void) {
    printf("%c\n", toupper('a')); // A
    printf("%c\n", toupper('A')); // A -- unchanged, already uppercase
    printf("%c\n", tolower('Z')); // z
    printf("%c\n", tolower('5')); // 5 -- unchanged, not a letter
    return 0;
}
Worked Example: Counting Vowels

C
#include <stdio.h>
#include <ctype.h>

int countVowels(const char *str) {
    int count = 0;
    for (int i = 0; str[i] != '\0'; i++) {
        char lower = (char) tolower((unsigned char) str[i]);
        if (lower == 'a' || lower == 'e' || lower == 'i' ||
            lower == 'o' || lower == 'u') {
            count++;
        }
    }
    return count;
}

int main(void) {
    printf("%d\n", countVowels("Hello, World!")); // 3
    return 0;
}
Worked Example: Validating an All-Digit String

C
#include <stdio.h>
#include <ctype.h>
#include <string.h>

int isAllDigits(const char *str) {
    if (str[0] == '\0') {
        return 0; // an empty string is not "all digits"
    }
    for (int i = 0; str[i] != '\0'; i++) {
        if (!isdigit((unsigned char) str[i])) {
            return 0;
        }
    }
    return 1;
}

int main(void) {
    printf("%d\n", isAllDigits("12345")); // 1 (true)
    printf("%d\n", isAllDigits("12a45")); // 0 (false)
    return 0;
}
These functions expect int, and a specific kind of int
Every <ctype.h> function technically takes an int parameter, and the standard says the argument must either be EOF or a value representable as unsigned char. On platforms where char is signed (very common), a character with the high bit set — such as many extended or non-ASCII bytes — becomes a negative value when stored in a plain char. Passing that negative value directly into a function like isalpha() or toupper() is technically undefined behavior, even though it often "happens to work" on many implementations. The reliable, portable fix is to always cast the character to unsigned char before passing it, as every example on this page does: isdigit((unsigned char) str[i]). This is a small habit that avoids a genuinely subtle class of bugs.
  • <ctype.h> provides isalpha, isdigit, isspace, isupper, islower, isalnum, ispunct for classifying characters

  • toupper/tolower convert case, leaving non-letter characters unchanged

  • These functions technically take an int, expecting EOF or an unsigned char-representable value

  • Passing a plain (possibly negative) char is technically undefined behavior on platforms with signed char

  • Always cast to (unsigned char) before calling these functions on a char value, e.g. isdigit((unsigned char) c)