All Occurrences of Subarray in Array

Last Updated : 5 May, 2026

You are given two integer arrays a[] and b[]. Return all the starting indexes of all the occurrences of b[] as a subarray in a[].

Examples

Input: a[] = [2, 4, 1, 0, 4, 1, 1], b[] = [4, 1]
Output: [1, 4]
Explanation: b[] occurs as a subarray in a[] from index 1 to 2 and from index 4 to 5.

Input: a[] = [2, 4, 1, 0, 0, 3], b[] = [0]
Output: [3, 4]
Explanation: b[] occurs as a subarray in a[] from index 3 to 3 and from index 4 to 4.

Try It Yourself
redirect icon

[Naive Approach] Comparing All Subarrays - O(n * m) Time and O(1) Space

The idea is to check for all possible indices in a[] as starting index of subarray b[]. For each index, compare the subarray of a[] with b[] using a nested loop. If all the elements match, store the starting index in result. If any element does not match, break and check for next starting index.

Consider the following dry run: a = [2, 4, 1, 0, 4, 1, 1], b = [4, 1]

  • For i = 0 --> (2 ≠ 4) --> mismatch --> move to next i
  • For i = 1 --> (4 = 4, 1 = 1) --> match --> add index 1
  • For i = 2 --> (1 ≠ 4) --> mismatch --> move to next i
  • For i = 3 --> (0 ≠ 4) --> mismatch --> move to next i
  • For i = 4 --> (4 = 4, 1 = 1) --> match --> add index 4
  • For i = 5 --> (1 ≠ 4) --> mismatch --> move to next i

Final answer: [1, 4]

C++
#include <iostream>
#include <vector>
using namespace std;

vector<int> search(vector<int> &a, vector<int> &b) {
    int n = a.size(), m = b.size();
    vector<int> res;
  
    // Iterate over all possible 
    // starting indices
	for(int i = 0; i < n - m + 1; i++) {
        bool isSame = true;
    	for(int j = 0; j < m; j++) {
          
            // If any character does not match, break
            // and begin from the next starting index
        	if(a[i + j] != b[j]) {
            	isSame = false;
                break;
            }
        }
      
        // If all characters are matched, store the
        // starting index
        if(isSame)
            res.push_back(i);
    }
    return res;
}

int main() {
	vector<int> a = {2, 4, 1, 0, 4, 1, 1};
    vector<int> b = {4, 1};
  
    vector<int> res = search(a, b);
    for(int idx: res)
        cout << idx << " ";
}
Java
import java.util.ArrayList;

class GfG {

    static ArrayList<Integer> search(int[] a, int[] b) {
        int n = a.length, m = b.length;
        ArrayList<Integer> res = new ArrayList<>();
        
        // Iterate over all possible 
        // starting indices
        for (int i = 0; i <= n - m; i++) {
            boolean isSame = true;
            
            // Check if b matches starting 
            // from index i in a
            for (int j = 0; j < m; j++) {
                if (a[i + j] != b[j]) {
                    isSame = false;
                    break;
                }
            }
            
            // If all elements matched, 
            // add starting index
            if (isSame)
                res.add(i);
        }

        return res;
    }

    public static void main(String[] args) {
        int[] a = {2, 4, 1, 0, 4, 1, 1};
        int[] b = {4, 1};

        ArrayList<Integer> res = search(a, b);
        for (int idx : res)
            System.out.print(idx + " ");
    }
}
Python
def search(a, b):
    n = len(a)
    m = len(b)
    res = []
  
    # Iterate over all possible 
    # starting indices
    for i in range(n - m + 1):
        isSame = True
        for j in range(m):
          
            # If any character does not match, break
            # and begin from the next starting index
            if a[i + j] != b[j]:
                isSame = False
                break
        
        # If all characters are matched, 
        # store the starting index
        if isSame:
            res.append(i)
    
    return res

# Driver code
if __name__ == "__main__":
    a = [2, 4, 1, 0, 4, 1, 1]
    b = [4, 1]

    res = search(a, b)
    for idx in res:
        print(idx, end=" ")
C#
using System;
using System.Collections.Generic;

class GfG {
    static List<int> search(int[] a, int[] b) {
        int n = a.Length, m = b.Length;
        List<int> res = new List<int>();
  
        // Iterate over all possible 
        // starting indices
        for (int i = 0; i < n - m + 1; i++) {
            bool isSame = true;
            for (int j = 0; j < m; j++) {
              
                // If any character does not match, break
                // and begin from the next starting index
                if (a[i + j] != b[j]) {
                    isSame = false;
                    break;
                }
            }
          
            // If all characters are matched, 
            // store the starting index
            if (isSame)
                res.Add(i);
        }
        return res;  
    }

    public static void Main() {
        int[] a = { 2, 4, 1, 0, 4, 1, 1};
        int[] b = { 4, 1 };
  
        List<int> res = search(a, b);
        foreach (int idx in res) {
            Console.Write(idx + " ");
        }
    }
}
JavaScript
function search(a, b)
{
    let n = a.length, m = b.length;
    let res = [];

    // Iterate over all possible
    // starting indices
    for (let i = 0; i < n - m + 1; i++) {
        let isSame = true;
        for (let j = 0; j < m; j++) {

            // If any character does not match, break
            // and begin from the next starting index
            if (a[i + j] !== b[j]) {
                isSame = false;
                break;
            }
        }

        // If all characters are matched,
        // store the starting index
        if (isSame)
            res.push(i);
    }
    return res;
}

// Driver code
let a = [ 2, 3, 0, 3, 0, 3, 0 ];
let b = [ 3, 0, 3, 0 ];

let res = search(a, b);
for (let idx of res) {
    console.log(idx + " ");
}

Output
1 4 

[Expected Approach] Using KMP Algorithm - O(m + n) Time and O(m) Space

The idea is to use the KMP algorithm by treating array a as the text and array b as the pattern. Instead of characters, we compare integers. We first build the LPS (Longest Prefix Suffix) array for the pattern, which helps us skip unnecessary comparisons when a mismatch occurs. Then, while scanning the text, we use this LPS information to efficiently find all occurrences of the pattern in O(n + m) time.

Consider this dry run for better understanding: a = [2, 4, 1, 0, 4, 1, 1], b = [4, 1]

  • Step 0: Build LPS for b --> b = [4, 1] --> lps = [0, 0]
  • Step 1: KMP Algorithm
    For i = 0, j = 0 --> 2 ≠ 4 --> j = 0, i++
    For i = 1, j = 0 --> 4 = 4 --> i = 2, j = 1
    For i = 2, j = 1 --> 1 = 1 --> match --> add (2 - 2 = 1) --> j = 0
    For i = 2, j = 0 --> 1 ≠ 4 --> i++
    For i = 3, j = 0 --> 0 ≠ 4 --> i++
    For i = 4, j = 0 --> 4 = 4 --> i = 5, j = 1
    For i = 5, j = 1 --> 1 = 1 --> match --> add (5 - 2 = 4) --> j = 0
    For i = 5, j = 0 --> 1 ≠ 4 --> i++
    For i = 6, j = 0 --> 1 ≠ 4 --> i++

Final answer: [1, 4]

C++
#include <iostream>
#include <vector>
using namespace std;

void constructLps(vector<int> &pat, vector<int> &lps)
{
    // len stores the length of longest
    // prefix which is also a suffix
    // for the previous index
    int len = 0;

    // lps[0] is always 0
    lps[0] = 0;

    int i = 1;
    while (i < pat.size())
    {
        // If numbers match, increment
        // the size of lps
        if (pat[i] == pat[len])
        {
            len++;
            lps[i] = len;
            i++;
        }
        else
        {
            if (len != 0)
            {
                // Update len to the previous lps value
                // to avoid reduntant comparisons
                len = lps[len - 1];
            }
            else
            {
                // If no matching prefix found,
                // set lps[i] to 0
                lps[i] = 0;
                i++;
            }
        }
    }
}

vector<int> search(vector<int> &a, vector<int> &b)
{
    int n = a.size();
    int m = b.size();

    vector<int> lps(m);
    vector<int> res;

    constructLps(b, lps);

    // Pointers i and j, for traversing
    // a[] and b[]
    int i = 0;
    int j = 0;

    while (i < n)
    {
        // If elements match, move
        // both pointers forward
        if (a[i] == b[j])
        {
            i++;
            j++;

            // If all elements of b[] are matched
            // store the start index in result
            if (j == m)
            {
                res.push_back(i - j);

                // Use LPS of previous index to
                // skip unnecessary comparisons
                j = lps[j - 1];
            }
        }

        // If there is a mismatch
        else
        {
            // Use lps value of previous index
            // to avoid redundant comparisons
            if (j != 0)
                j = lps[j - 1];
            else
                i++;
        }
    }
    return res;
}

int main()
{
    vector<int> a = {2, 4, 1, 0, 4, 1, 1};
    vector<int> b = {4, 1};

    vector<int> res = search(a, b);
    for (int idx : res)
        cout << idx << " ";
}
Java
import java.util.ArrayList;

class GfG {

    // Function to construct LPS array
    static void constructLps(int[] pat, int[] lps)
    {
        // len stores the length of longest
        // prefix which is also a suffix
        // for the previous index
        int len = 0;

        // lps[0] is always 0
        lps[0] = 0;

        int i = 1;
        while (i < pat.length) {

            // If numbers match, increment
            // the size of lps
            if (pat[i] == pat[len]) {
                len++;
                lps[i] = len;
                i++;
            }
            else {
                if (len != 0) {

                    // Update len to the previous lps value
                    // to avoid reduntant comparisons
                    len = lps[len - 1];
                }
                else {

                    // If no matching prefix found,
                    // set lps[i] to 0
                    lps[i] = 0;
                    i++;
                }
            }
        }
    }

    static ArrayList<Integer> search(int[] a, int[] b)
    {
        int n = a.length;
        int m = b.length;

        int[] lps = new int[m];
        ArrayList<Integer> res = new ArrayList<>();

        constructLps(b, lps);

        int i = 0, j = 0;
        // If elements match, move
        // both pointers forward
        while (i < n) {
            if (a[i] == b[j]) {
                i++;
                j++;
                // If all elements of b[] are matched
                // store the start index in result
                if (j == m) {
                    res.add(i - j);
                    j = lps[j - 1];
                    // Use LPS of previous index to
                    // skip unnecessary comparisons
                }
            }
            else {
                if (j != 0) {
                    j = lps[j - 1];
                }
                else {
                    i++;
                }
            }
        }

        return res;
    }

    public static void main(String[] args)
    {
        int[] a = { 2, 4, 1, 0, 4, 1, 1 };
        int[] b = { 4, 1 };

        ArrayList<Integer> res = search(a, b);
        for (int idx : res)
            System.out.print(idx + " ");
    }
}
Python
def constructLps(pat, lps):
    # len stores the length of longest
    # prefix which is also a  suffix
    # for the previous index
    length = 0

    # lps[0] is always 0
    lps[0] = 0

    i = 1
    while i < len(pat):

        # If numbers match, increment
        # the size of lps
        if pat[i] == pat[length]:
            length += 1
            lps[i] = length
            i += 1

        else:
            if length != 0:

                # Update length to the previous lps value
                # to avoid redundant comparisons
                length = lps[length - 1]
            else:

                # If no matching prefix found,
                # set lps[i] to 0
                lps[i] = 0
                i += 1


def search(a, b):
    n = len(a)
    m = len(b)

    lps = [0] * m
    res = []

    constructLps(b, lps)

    # Pointers i and j, for
    # traversing a[] and b[]
    i = 0
    j = 0

    while i < n:

        # If elements match, move both
        # pointers forward
        if a[i] == b[j]:
            i += 1
            j += 1

            # If all elements of b[] are matched
            # store the start index in result
            if j == m:
                res.append(i - j)

                # Use LPS of previous index to
                # skip unnecessary comparisons
                j = lps[j - 1]
        else:

            # If there is a mismatch
            # Use lps value of previous index
            # to avoid redundant comparisons
            if j != 0:
                j = lps[j - 1]
            else:
                i += 1

    return res

# Driver code
if __name__ == "__main__":
    a = [2, 4, 1, 0, 4, 1, 1]
    b = [4, 1]

    res = search(a, b)
    for idx in res:
        print(idx, end=" ")
C#
using System;
using System.Collections.Generic;

class GfG {
    // Function to construct the LPS
    // array (Longest Prefix Suffix)
    static void ConstructLps(int[] pat, int[] lps)
    {
        // len stores the length of the longest
        // prefix which is also a suffix
        // for the previous index
        int len = 0;

        // lps[0] is always 0
        lps[0] = 0;

        int i = 1;
        while (i < pat.Length) {
            // If numbers match, increment the size of lps
            if (pat[i] == pat[len]) {
                len++;
                lps[i] = len;
                i++;
            }
            // If there is a mismatch
            else {
                if (len != 0) {
                    // Update len to the previous lps value
                    // to avoid redundant comparisons
                    len = lps[len - 1];
                }
                else {
                    // If no matching prefix found,
                    // set lps[i] to 0
                    lps[i] = 0;
                    i++;
                }
            }
        }
    }

    // Function to search for the subarray
    static List<int> search(int[] a, int[] b)
    {
        int n = a.Length;
        int m = b.Length;

        int[] lps = new int[m];
        List<int> res = new List<int>();

        ConstructLps(b, lps);

        // Pointers i and j, for
        // traversing a[] and b[]
        int i = 0;
        int j = 0;

        while (i < n) {
            // If elements match, move
            // both pointers forward
            if (a[i] == b[j]) {
                i++;
                j++;

                // If all elements of b[] are matched
                // store the start index in result
                if (j == m) {
                    res.Add(i - j);

                    // Use LPS of previous index to
                    // skip unnecessary comparisons
                    j = lps[j - 1];
                }
            }
            else {
                // Use lps value of previous index
                // to avoid redundant comparisons
                if (j != 0)
                    j = lps[j - 1];
                else
                    i++;
            }
        }

        return res;
    }

    public static void Main()
    {
        int[] a = { 2, 4, 1, 0, 4, 1, 1 };
        int[] b = { 4, 1 };

        List<int> res = search(a, b);
        foreach(int idx in res)
        {
            Console.Write(idx + " ");
        }
    }
}
JavaScript
// function to search subarray b in array a
function search(a, b)
{
    let n = a.length;
    let m = b.length;

    let lps = new Array(m);
    let res = [];

    constructLps(b, lps);

    // Pointers i and j, for traversing a[] and b[]
    let i = 0;
    let j = 0;

    while (i < n) {

        // If elements match, move
        // both pointers forward
        if (a[i] === b[j]) {
            i++;
            j++;

            // If all elements of b[] are matched
            // store the start index in result
            if (j === m) {
                res.push(i - j);

                // Use LPS of previous index to
                // skip unnecessary comparisons
                j = lps[j - 1];
            }
        }
        else {

            // Use lps value of previous index
            // to avoid redundant comparisons
            if (j !== 0)
                j = lps[j - 1];
            else
                i++;
        }
    }

    return res;
}

// function to construct lps
function constructLps(pat, lps)
{
    // len stores the length of longest prefix which
    // is also a suffix for the previous index
    let len = 0;

    // lps[0] is always 0
    lps[0] = 0;

    let i = 1;
    while (i < pat.length) {

        // If numbers match, increment the size of lps
        if (pat[i] === pat[len]) {
            len++;
            lps[i] = len;
            i++;
        }
        else {
            if (len !== 0) {

                // Update len to the previous lps value
                // to avoid redundant comparisons
                len = lps[len - 1];
            }
            else {

                // If no matching prefix found,
                // set lps[i] to 0
                lps[i] = 0;
                i++;
            }
        }
    }
}

// Driver Code
let a = [ 2, 4, 1, 0, 4, 1, 1 ];
let b = [ 4, 1 ];

let res = search(a, b);

let ans = "";
for (let idx of res) {
    ans += idx + " ";
}

console.log(ans.trim());

Output
1 4 

Related Topic: Subarrays, Subsequences, and Subsets in Array

Comment