Skip to content
Related Articles
Get the best out of our app
GeeksforGeeks App
Open App
geeksforgeeks
Browser
Continue

Related Articles

Find the Suffix Array of given String with no repeating character

Improve Article
Save Article
Like Article
Improve Article
Save Article
Like Article

Given a string str of size N, the task is to find the suffix array of the given string.

Note: A suffix array is a sorted array of all suffixes of a given string.

Examples: 

Input: str = “prince”
Output: 4 5 2 3 0 1
Explanation: The suffixes are
0 prince                                    4 ce
1 rince      Sort the suffixes       5 e  
2 ince         —————->    2 ince  
3 nce          alphabetically        3 nce    
4 ce                                          0 prince
5 e                                           1 rince

Input: str = “abcd”
Output: 0 1 2 3

 

Approach: The methods of suffix array finding for any string are discussed here. In this article, the focus is on finding suffix array for strings with no repeating character. It is a simple implementation based problem. Follow the steps mentioned below to solve the problem:

  • Count occurrence of each character.
  • Find prefix sum of it.
  • Find start array by start[0] = 0, start[i+1] = prefix[i] for all i > 0 .
  • Find start array containing the index of the substring (suffix) with starting character of the respective column.

Follow the illustration below for better understanding.

Illustration:

Consider string “prince”:
Given below is the suffix table 

charabcdefghijklmnopqrstuvwxyz
count00101000100001010100000000
prefix00112222333334455666666666
start00011222233333445566666666

For char ‘r’ start value is 5 . 
Implies substring (suffix) starting with char ‘r’ i.e. “rince” has rank 5 .
Rank is position in suffix array.  ( 1 “rince” ) implies 5th position in suffix array ), refer first table.
Similarly, start value of char ‘n’ is 3 . Implies ( 3 “nce” ) 3rd position in suffix array .

  Below is the implementation of the above approach

C++




// C++ code to implement above approach
#include <bits/stdc++.h>
using namespace std;
 
// Function to calculate the suffix array
void suffixArray(string str, int N)
{
    // arr[] is array to count
    // occurrence of each character
    int arr[30] = { 0 };
    for (int i = 0; i < N; i++) {
        arr[str[i] - 'a']++;
    }
 
    // Finding prefix count of character
    for (int i = 1; i < 30; i++) {
        arr[i] = arr[i] + arr[i - 1];
    }
 
    int start[30];
    start[0] = 0;
    for (int i = 0; i < 29; i++) {
        start[i + 1] = arr[i];
    }
 
    int ans[N] = { 0 };
 
    // Iterating string in reverse order
    for (int i = N - 1; i >= 0; i--) {
 
        // Storing suffix array in ans[]
        ans[start[str[i] - 'a']] = i;
    }
 
    for (int i = 0; i < N; i++)
        cout << ans[i] << " ";
}
 
// Driver code
int main()
{
    string str = "prince";
    int N = str.length();
 
    suffixArray(str, N);
    return 0;
}

Java




// Java program for the above approach
import java.io.*;
import java.lang.*;
import java.util.*;
 
class GFG {
 
 
  // Function to calculate the suffix array
  static void suffixArray(String str, int N)
  {
 
    // arr[] is array to count
    // occurrence of each character
    int arr[] = new int[30];
    for (int i = 0; i < N; i++) {
      arr[str.charAt(i) - 'a']++;
    }
 
    // Finding prefix count of character
    for (int i = 1; i < 30; i++) {
      arr[i] = arr[i] + arr[i - 1];
    }
 
    int start[] = new int[30];
    start[0] = 0;
    for (int i = 0; i < 29; i++) {
      start[i + 1] = arr[i];
    }
 
    int ans[]  = new int[N];
 
    // Iterating string in reverse order
    for (int i = N - 1; i >= 0; i--) {
 
      // Storing suffix array in ans[]
      ans[start[str.charAt(i) - 'a']] = i;
    }
 
    for (int i = 0; i < N; i++)
      System.out.print(ans[i] + " ");
  }
 
  // Driver code
  public static void main (String[] args)
  {
    String str = "prince";
    int N = str.length();
 
    suffixArray(str, N);
  }
}
 
// This code is contributed by hrithikgarg03188

Python3




# Python code for the above approach
 
# Function to calculate the suffix array
def suffixArray(str, N):
   
    # arr[] is array to count
    # occurrence of each character
    arr = [0] * 30
    for i in range(N):
        arr[ord(str[i]) - ord('a')] += 1
 
    # Finding prefix count of character
    for i in range(1, 30):
        arr[i] = arr[i] + arr[i - 1]
 
    start = [0] * 30
    start[0] = 0
    for i in range(29):
        start[i + 1] = arr[i]
 
    ans = [0] * N
 
    # Iterating string in reverse order
    for i in range(N - 1, 0, -1):
 
        # Storing suffix array in ans[]
        ans[start[ord(str[i]) - ord('a')]] = i
 
    for i in range(N):
        print(ans[i], end=" ")
 
# Driver code
str = "prince"
N = len(str)
 
suffixArray(str, N)
 
# This code is contributed by gfgking

C#




// C# code to implement above approach
using System;
class GFG
{
   
    // Function to calculate the suffix array
    static void suffixArray(string str, int N)
    {
        // arr[] is array to count
        // occurrence of each character
        int[] arr = new int[30];
        for (int i = 0; i < N; i++) {
            arr[str[i] - 'a']++;
        }
 
        // Finding prefix count of character
        for (int i = 1; i < 30; i++) {
            arr[i] = arr[i] + arr[i - 1];
        }
 
        int[] start = new int[30];
        start[0] = 0;
        for (int i = 0; i < 29; i++) {
            start[i + 1] = arr[i];
        }
 
        int[] ans = new int[N];
 
        // Iterating string in reverse order
        for (int i = N - 1; i >= 0; i--) {
 
            // Storing suffix array in ans[]
            ans[start[str[i] - 'a']] = i;
        }
 
        for (int i = 0; i < N; i++) {
            Console.Write(ans[i]);
            Console.Write(" ");
        }
    }
 
    // Driver code
    public static int Main()
    {
        string str = "prince";
        int N = str.Length;
 
        suffixArray(str, N);
        return 0;
    }
}
 
// This code is contributed by Taranpreet

Javascript




<script>
     // JavaScript code for the above approach
 
 
     // Function to calculate the suffix array
     function suffixArray(str, N) {
         // arr[] is array to count
         // occurrence of each character
         let arr = new Array(30).fill(0);
         for (let i = 0; i < N; i++) {
             arr[str[i].charCodeAt(0) - 'a'.charCodeAt(0)]++;
         }
 
         // Finding prefix count of character
         for (let i = 1; i < 30; i++) {
             arr[i] = arr[i] + arr[i - 1];
         }
 
         let start = new Array(30)
         start[0] = 0;
         for (let i = 0; i < 29; i++) {
             start[i + 1] = arr[i];
         }
 
         let ans = new Array(N).fill(0)
 
         // Iterating string in reverse order
         for (let i = N - 1; i >= 0; i--) {
 
             // Storing suffix array in ans[]
             ans[start[str[i].charCodeAt(0) - 'a'.charCodeAt(0)]] = i;
         }
 
         for (let i = 0; i < N; i++)
             document.write(ans[i] + " ")
     }
 
     // Driver code
 
     let str = "prince";
     let N = str.length;
 
     suffixArray(str, N);
 
 
      // This code is contributed by Potta Lokesh
 </script>

 
 

Output

4 5 2 3 0 1 

 

Time Complexity: O(N)
Auxiliary Space: O(N)

 


My Personal Notes arrow_drop_up
Last Updated : 24 Feb, 2022
Like Article
Save Article
Similar Reads
Related Tutorials