Check if Two Strings are Anagrams - Visualization

Visualization Player

Problem Statement

Given two strings s1 and s2, determine whether they are anagrams of each other.

  • Two strings are considered anagrams if they contain the same characters with the same frequency, but possibly in a different order.
  • The comparison should be case-insensitive, and spacing or punctuation is not ignored unless explicitly stated.

If either string is empty or null, handle appropriately.

Examples

s1 s2 Are Anagrams? Description
"listen" "silent" true Characters match in count and type
"Listen" "Silent" true Case-insensitive comparison
"triangle" "integral" true Same characters in different order
"abc" "def" false Completely different characters
"aabbcc" "abccba" true Same letters and same frequency
"aabbcc" "abc" false Frequencies do not match
"hello" "helloo" false Different lengths
"" "" true Both strings are empty
"" "abc" false One string is empty
"" "" true Empty strings are technically anagrams of each other

Solution

Understanding the Problem

We are given two strings and asked to determine if they are anagrams. That means we need to check whether the two strings contain the same characters with the same frequency, but possibly in a different order. Think of it like this: Can we rearrange the letters of the first string to form the second one?

We also need to ignore the case of letters (uppercase vs lowercase), and carefully handle cases like different lengths or empty strings.

Step-by-Step Solution with Example

Step 1: Convert both strings to lowercase

This ensures that 'A' and 'a' are treated as the same character. For example, if we are comparing "Listen" and "Silent", we first convert both to "listen" and "silent".

Step 2: Check the lengths

If the strings have different lengths, they cannot be anagrams. For example, "hello" and "helloo" are not anagrams because one has an extra character.

Step 3: Count the frequency of each character

We use a dictionary (also called a map) to count how many times each character appears in each string.

Example: Compare "listen" and "silent".

  • 'l': appears once in both
  • 'i': once in both
  • 's': once in both
  • 't': once in both
  • 'e': once in both
  • 'n': once in both

Since every character and its count matches, they are anagrams.

Step 4: Compare both frequency maps

If the dictionaries for both strings are equal, the strings are anagrams. If even one character count is different, they are not.

Example: "aabbcc" vs "abc" → Not anagrams, because "aabbcc" has two of each letter, while "abc" has only one.

Edge Cases

  • Empty strings: Two empty strings are considered anagrams because they contain the same (no) characters.
  • One empty, one non-empty: Not anagrams.
  • Case sensitivity: Convert to lowercase before comparison to ensure fair evaluation.
  • Completely different letters: For example, "abc" and "xyz" → Not anagrams.

Finally

This problem tests your understanding of strings, maps, and case handling. By walking through the example step-by-step and handling edge cases carefully, you ensure a solid and beginner-friendly solution.

The overall time complexity of the solution is O(n), where n is the length of the strings, because we loop through each string a limited number of times.

Algorithm Steps

  1. If the lengths of s1 and s2 are different, return false immediately.
  2. Convert both strings to lowercase to handle case-insensitivity.
  3. Initialize two hash maps: map1 and map2.
  4. Loop through each character in s1 and count frequency in map1.
  5. Loop through each character in s2 and count frequency in map2.
  6. If the number of unique keys in map1 and map2 differ, return false.
  7. Check each key in map1 and compare its count with map2. If any mismatch, return false.
  8. If all checks pass, return true.

Code

C
C++
Python
Java
JS
Go
Rust
Kotlin
Swift
TS
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <stdbool.h>

bool isAnagram(const char* s1, const char* s2) {
    if (strlen(s1) != strlen(s2)) return false;

    int freq1[26] = {0};
    int freq2[26] = {0};

    for (int i = 0; s1[i]; i++) {
        freq1[tolower(s1[i]) - 'a']++;
        freq2[tolower(s2[i]) - 'a']++;
    }

    for (int i = 0; i < 26; i++) {
        if (freq1[i] != freq2[i]) return false;
    }

    return true;
}

int main() {
    printf("%d\n", isAnagram("listen", "silent")); // 1
    printf("%d\n", isAnagram("Hello", "Olelh"));   // 1
    printf("%d\n", isAnagram("Hi", "Bye"));       // 0
    return 0;
}

Time Complexity

CaseTime ComplexityExplanation
Best CaseO(n)We scan both strings once to populate the maps and compare them.
Average CaseO(n)Each character is processed once in both strings and looked up in hash maps.
Worst CaseO(n)All characters are processed and map comparisons done linearly.

Space Complexity

O(1)

Explanation: At most 26 characters are stored in the maps (for alphabetic strings), making space constant for English letters.


Comments

💬 Please keep your comment relevant and respectful. Avoid spamming, offensive language, or posting promotional/backlink content.
All comments are subject to moderation before being published.


Loading comments...