Good String

Last Updated : 28 Jul, 2026

Given a string s, find if it is good. A string is considered good if the cyclic distance between every pair of adjacent characters is exactly 1.  Return true if it is good otherwise, return false.

  •  The cyclic distance between two characters is the minimum distance in a circular arrangement of characters from 'a' to 'z'.  For example, the distance between 'a' and 'c' is 2 and he distance between 'a' and 'y' is 2. 
  • A string of length 1 is always considered good.

Examples:

Input: s = "cbc"
Output: true
Explanation: The distance between 'c' and 'b' is 1, and the distance between 'b' and 'c' is also 1. Hence, the answer is true.

Input: s = "aaa"
Output: false
Explanation: The distance between 'a' and 'a' is 0. Hence, the answer is false.

Try It Yourself
redirect icon

Brute Force Approach - O(n) Time and O(1) Space

Each character in the circular alphabet has exactly two valid adjacent neighbors—one in the clockwise direction and one in the counterclockwise direction. We simply check whether every adjacent character in the string matches one of these two neighbors. If any pair fails this check, the string is not good.

  • If the string contains only one character, return true.
  • Traverse the string from the second character to the last.
  • For each previous character, determine its clockwise neighbor (next).
  • Also determine its counterclockwise neighbor (prev).
  • If the current character is neither next nor prev, return false.
  • If all adjacent pairs satisfy the condition, return true.
C++
#include <iostream>
#include <string>
using namespace std;

bool isGoodString(string &s)
{
    // A single-character string is always good.
    if (s.size() == 1)
        return true;

    // Check every adjacent pair.
    for (int i = 1; i < s.size(); i++)
    {
        char curr = s[i - 1];

        // Find the clockwise neighbor of the current character.
        char next = (curr == 'z') ? 'a' : curr + 1;

        // Find the counterclockwise neighbor of the current character.
        char prev = (curr == 'a') ? 'z' : curr - 1;

        // The next character must be either the clockwise
        // or the counterclockwise neighbor.
        if (s[i] != next && s[i] != prev)
            return false;
    }

    // Every adjacent pair satisfies the condition.
    return true;
}

int main()
{
    string s = "abc";

    if (isGoodString(s))
        cout << "true";
    else
        cout << "false";

    return 0;
}
Java
class GFG {

    static boolean isGoodString(String s)
    {
        // A single-character string is always good.
        if (s.length() == 1)
            return true;

        // Check every adjacent pair.
        for (int i = 1; i < s.length(); i++) {

            char curr = s.charAt(i - 1);

            // Find the clockwise neighbor of the current
            // character.
            char next
                = (curr == 'z') ? 'a' : (char)(curr + 1);

            // Find the counterclockwise neighbor of the
            // current character.
            char prev
                = (curr == 'a') ? 'z' : (char)(curr - 1);

            // The next character must be either the
            // clockwise or the counterclockwise neighbor.
            if (s.charAt(i) != next && s.charAt(i) != prev)
                return false;
        }

        // Every adjacent pair satisfies the condition.
        return true;
    }

    public static void main(String[] args)
    {
        String s = "abc";

        if (isGoodString(s))
            System.out.println("true");
        else
            System.out.println("false");
    }
}
Python
def isGoodString(s):
    # A single-character string is always good.
    if len(s) == 1:
        return True

    # Check every adjacent pair.
    for i in range(1, len(s)):

        curr = s[i - 1]

        # Find the clockwise neighbor of the current character.
        next_char = 'a' if curr == 'z' else chr(ord(curr) + 1)

        # Find the counterclockwise neighbor of the current character.
        prev_char = 'z' if curr == 'a' else chr(ord(curr) - 1)

        # The next character must be either the clockwise
        # or the counterclockwise neighbor.
        if s[i] != next_char and s[i] != prev_char:
            return False

    # Every adjacent pair satisfies the condition.
    return True


# Driver code
if __name__ == "__main__":
    s = "abc"

    if isGoodString(s):
        print("true")
    else:
        print("false")
C#
using System;

class Solution {
    static bool isGoodString(string s)
    {
        // A single-character string is always good.
        if (s.Length == 1)
            return true;

        // Check every adjacent pair.
        for (int i = 1; i < s.Length; i++) {
            char curr = s[i - 1];

            // Find the clockwise neighbor of the
            // current character.
            char next
                = (curr == 'z') ? 'a' : (char)(curr + 1);

            // Find the counterclockwise neighbor of the
            // current character.
            char prev
                = (curr == 'a') ? 'z' : (char)(curr - 1);

            // The next character must be either the
            // clockwise or the counterclockwise
            // neighbor.
            if (s[i] != next && s[i] != prev)
                return false;
        }

        // Every adjacent pair satisfies the condition.
        return true;
    }

    static void Main()
    {
        string s = "abc";

        if (isGoodString(s))
            Console.WriteLine("true");
        else
            Console.WriteLine("false");
    }
}
JavaScript
function isGoodString(s)
{
    // A single-character string is always good.
    if (s.length === 1)
        return true;

    // Check every adjacent pair.
    for (let i = 1; i < s.length; i++) {

        let curr = s[i - 1];

        // Find the clockwise neighbor of the current
        // character.
        let next = (curr === "z")
                       ? "a"
                       : String.fromCharCode(
                           curr.charCodeAt(0) + 1);

        // Find the counterclockwise neighbor of the current
        // character.
        let prev = (curr === "a")
                       ? "z"
                       : String.fromCharCode(
                           curr.charCodeAt(0) - 1);

        // The next character must be either the clockwise
        // or the counterclockwise neighbor.
        if (s[i] !== next && s[i] !== prev)
            return false;
    }

    // Every adjacent pair satisfies the condition.
    return true;
}

// Driver code
let s = "abc";

if (isGoodString(s))
    console.log("true");
else
    console.log("false");

Output
true

Linear Scan Using Cyclic Distance - O(n) Time and O(1) Space

Instead of explicitly finding the two neighboring characters, we directly compute the cyclic distance between every adjacent pair. If the minimum of the direct distance and the wrap-around distance is exactly 1 for every pair, the string is good.

  • Traverse the string from the second character to the last.
  • For each adjacent pair, compute the cyclic distance as min(diff, 26 - diff).
  • If the cyclic distance is not 1, return false.
  • If all adjacent pairs satisfy the condition, return true.
C++
#include <iostream>
#include <string>
using namespace std;

bool isGoodString(string &s)
{
    // Check every adjacent pair.
    for (int i = 1; i < s.size(); i++)
    {
        // Compute the direct distance between adjacent characters.
        int diff = abs(s[i] - s[i - 1]);

        // If the minimum cyclic distance is not 1,
        // the string is not good.
        if (min(diff, 26 - diff) != 1)
            return false;
    }

    // Every adjacent pair satisfies the condition.
    return true;
}

int main()
{
    string s = "abc";

    if (isGoodString(s))
        cout << "true";
    else
        cout << "false";

    return 0;
}
Java
class GFG {

    static boolean isGoodString(String s)
    {
        // Check every adjacent pair.
        for (int i = 1; i < s.length(); i++) {

            // Compute the direct distance between adjacent
            // characters.
            int diff
                = Math.abs(s.charAt(i) - s.charAt(i - 1));

            // If the minimum cyclic distance is not 1,
            // the string is not good.
            if (Math.min(diff, 26 - diff) != 1)
                return false;
        }

        // Every adjacent pair satisfies the condition.
        return true;
    }

    public static void main(String[] args)
    {
        String s = "abc";

        if (isGoodString(s))
            System.out.println("true");
        else
            System.out.println("false");
    }
}
Python
def isGoodString(s):

    # Check every adjacent pair.
    for i in range(1, len(s)):

        # Compute the direct distance between adjacent characters.
        diff = abs(ord(s[i]) - ord(s[i - 1]))

        # If the minimum cyclic distance is not 1,
        # the string is not good.
        if min(diff, 26 - diff) != 1:
            return False

    # Every adjacent pair satisfies the condition.
    return True


# Driver code
if __name__ == "__main__":
    s = "abc"

    if isGoodString(s):
        print("true")
    else:
        print("false")
C#
using System;

class GFG {
    
    static bool isGoodString(string s)
    {
        // Check every adjacent pair.
        for (int i = 1; i < s.Length; i++) {
            // Compute the direct distance between adjacent
            // characters.
            int diff = Math.Abs(s[i] - s[i - 1]);

            // If the minimum cyclic distance is not 1,
            // the string is not good.
            if (Math.Min(diff, 26 - diff) != 1)
                return false;
        }

        // Every adjacent pair satisfies the condition.
        return true;
    }

    static void Main()
    {
        string s = "abc";

        if (isGoodString(s))
            Console.WriteLine("true");
        else
            Console.WriteLine("false");
    }
}
JavaScript
function isGoodString(s)
{
    // Check every adjacent pair.
    for (let i = 1; i < s.length; i++) {

        // Compute the direct distance between adjacent
        // characters.
        let diff = Math.abs(s.charCodeAt(i)
                            - s.charCodeAt(i - 1));

        // If the minimum cyclic distance is not 1,
        // the string is not good.
        if (Math.min(diff, 26 - diff) !== 1)
            return false;
    }

    // Every adjacent pair satisfies the condition.
    return true;
}

// Driver code
let s = "abc";

if (isGoodString(s))
    console.log("true");
else
    console.log("false");

Output
true
Comment