Difference Array | Range update query in O(1) (original) (raw)

Last Updated : 05 May, 2025

You are given an integer array arr[] and a list of queries. Each query is represented as a list of integers where:

You need to perform the queries in order.

**Examples :

**Input: arr[] = [10, 5, 20, 40], queries = [ [1, 0, 1, 10], [2], [1, 1, 3, 20], [1, 2, 2, 30], [2] ]
**Output: 20 15 20 40
20 35 70 60

Explanation: [1, 0, 1, 10]: Adds 10 to arr[0] and arr[1].
Array becomes [20, 15, 20, 40].

Table of Content

**[Naive Approach] **Using loops for each queries - O(n * q) time and O(1) space

A **simple solution is to do following :

  1. update(l, r, x) : Run a loop from l to r and add x to all elements from arr[l] to arr[r]
  2. printArray() : Simply print arr[].

C++ `

#include #include using namespace std;

void update(vector &arr, int l, int r, int x) { for (int i = l; i <= r; i++) { arr[i] += x; } }

void printArray(const vector &arr) { for (int num : arr) { cout << num << " "; } cout << endl; }

int main() { vector arr = {10, 5, 20, 40};

vector<vector<int>> queries = {{1, 0, 1, 10}, {2}, {1, 1, 3, 20}, {1, 2, 2, 30}, {2}};

for (const auto &query : queries)
{
    if (query[0] == 1)
    {
        // update operation
        int l = query[1];
        int r = query[2];
        int x = query[3];
        update(arr, l, r, x);
    }
    else if (query[0] == 2)
    {
        // print operation
        printArray(arr);
    }
}

return 0;

}

Java

import java.util.Arrays; import java.util.List;

public class GfG{ public static void update(int[] arr, int l, int r, int x) { for (int i = l; i <= r; i++) { arr[i] += x; } }

public static void printArray(int[] arr)
{
    for (int num : arr) {
        System.out.print(num + " ");
    }
    System.out.println();
}

public static void main(String[] args)
{
    int[] arr = { 10, 5, 20, 40 };

    int[][] queries = { { 1, 0, 1, 10 },
                        { 2 },
                        { 1, 1, 3, 20 },
                        { 1, 2, 2, 30 },
                        { 2 } };

    for (int[] query : queries) {
        if (query[0] == 1) {
            // update operation
            int l = query[1];
            int r = query[2];
            int x = query[3];
            update(arr, l, r, x);
        }
        else if (query[0] == 2) {
            // print operation
            printArray(arr);
        }
    }
}

}

Python

def update(arr, l, r, x): for i in range(l, r + 1): arr[i] += x

def print_array(arr): print(' '.join(map(str, arr)))

if name == 'main': arr = [10, 5, 20, 40]

queries = [[1, 0, 1, 10], [2], [1, 1, 3, 20], [1, 2, 2, 30], [2]]

for query in queries:
    if query[0] == 1:
        # update operation
        l, r, x = query[1], query[2], query[3]
        update(arr, l, r, x)
    elif query[0] == 2:
        # print operation
        print_array(arr)

C#

using System; using System.Collections.Generic;

class GfG{ static void Update(int[] arr, int l, int r, int x) { for (int i = l; i <= r; i++) { arr[i] += x; } }

static void PrintArray(int[] arr)
{
    foreach(int num in arr)
    {
        Console.Write(num + " ");
    }
    Console.WriteLine();
}

static void Main()
{
    int[] arr = new int[] { 10, 5, 20, 40 };

    List<List<int>> queries = new List<List<int>>{
        new List<int>{ 1, 0, 1, 10 },
        new List<int>{ 2 },
        new List<int>{ 1, 1, 3, 20 },
        new List<int>{ 1, 2, 2, 30 }, new List<int>{ 2 }
    };

    foreach(var query in queries)
    {
        if (query[0] == 1) {
            // update operation
            int l = query[1];
            int r = query[2];
            int x = query[3];
            Update(arr, l, r, x);
        }
        else if (query[0] == 2) {
            // print operation
            PrintArray(arr);
        }
    }
}

}

JavaScript

function update(arr, l, r, x) { for (let i = l; i <= r; i++) { arr[i] += x; } }

function printArray(arr) { console.log(arr.join(" ")); }

const arr = [ 10, 5, 20, 40 ];

const queries = [ [ 1, 0, 1, 10 ], [ 2 ], [ 1, 1, 3, 20 ], [ 1, 2, 2, 30 ], [ 2 ] ];

queries.forEach(query => { if (query[0] === 1) { // update operation const [_, l, r, x] = query; update(arr, l, r, x); } else if (query[0] === 2) { // print operation printArray(arr); } });

`

Output

20 15 20 40 20 35 70 60

**Time Complexity: O(n * q), O(n) for each queries
**Space Complexity: O(1)

[Expected Approach] Using Difference Array

**Difference array d[i] of a given array arr[i] is defined as d[i] = arr[i] - arr[i-1] (for 0 < i < n) and d[0] = arr[0] considering 0 based indexing. Difference array can be used to perform range update queries "l r x" where l is left index, r is right index and x is value to be added and after all queries you can return original array from it. Where update range operations can be performed in O(1) complexity.

  1. update(l, r, x) : Add x to d[l] and subtract it from d[r+1], i.e., we do d[l] += x, d[r+1] -= x
  2. printArray() : Do a[0] = d[0] and print it. For rest of the elements, do arr[i] = arr[i-1] + d[i] and print them****.**

**Illustration: Let us understand this with an example arr = [2, 5, 7, 9, 6]. The difference array would be d = [2, 3, 2, 2, -3]. After an update say update(1, 3, 4), we add 4 to index 1 and subtract from index 4, the difference array would become d = [2, 7, 2, 2, -7]. Now to print array, we print 2, 2 + 7 = 9, 9 + 2 = 11, 11 + 2 = 13, 13 + (-7) = 6

C++ `

#include #include using namespace std;

vector initDiffArray(vector &arr) { int n = arr.size();

// Initialize difference array with an extra element
vector<int> d(n + 1, 0);

d[0] = arr[0];
for (int i = 1; i < n; i++)
{
    d[i] = arr[i] - arr[i - 1];
}
return d;

}

void update(vector &d, int l, int r, int x) { d[l] += x; d[r + 1] -= x; }

void printArray(vector &arr, vector &d) { for (int i = 0; i < arr.size(); i++) { if (i == 0) arr[i] = d[i]; else arr[i] = d[i] + arr[i - 1];

    cout << arr[i] << " ";
}
cout << endl;

}

int main() { vector arr{10, 5, 20, 40};

vector<int> d = initDiffArray(arr);

vector<vector<int>> queries = {{1, 0, 1, 10}, {2}, {1, 1, 3, 20}, {1, 2, 2, 30}, {2}};

for (const auto &query : queries)
{
    if (query[0] == 1)
    {
        // If it's an update query: update(l, r, x)
        int l = query[1];
        int r = query[2];
        int x = query[3];
        update(d, l, r, x);
    }
    else if (query[0] == 2)
    {
        // If it's a print query: printArray()
        printArray(arr, d);
    }
}

return 0;

}

Java

import java.util.Arrays; import java.util.List; import java.util.ArrayList;

public class GfG{ public static int[] initDiffArray(int[] arr) { int n = arr.length; int[] d = new int[n + 1]; d[0] = arr[0]; for (int i = 1; i < n; i++) { d[i] = arr[i] - arr[i - 1]; } return d; }

public static void update(int[] d, int l, int r, int x) {
    d[l] += x;
    d[r + 1] -= x;
}

public static void printArray(int[] arr, int[] d) {
    for (int i = 0; i < arr.length; i++) {
        if (i == 0)
            arr[i] = d[i];
        else
            arr[i] = d[i] + arr[i - 1];
        System.out.print(arr[i] + " ");
    }
    System.out.println();
}

public static void main(String[] args) {
    int[] arr = {10, 5, 20, 40};
    int[] d = initDiffArray(arr);
    List<int[]> queries = new ArrayList<>();
    queries.add(new int[]{1, 0, 1, 10});
    queries.add(new int[]{2});
    queries.add(new int[]{1, 1, 3, 20});
    queries.add(new int[]{1, 2, 2, 30});
    queries.add(new int[]{2});

    for (int[] query : queries) {
        if (query[0] == 1) {
            // If it's an update query: update(l, r, x)
            int l = query[1];
            int r = query[2];
            int x = query[3];
            update(d, l, r, x);
        } else if (query[0] == 2) {
            // If it's a print query: printArray()
            printArray(arr, d);
        }
    }
}

}

Python

def init_diff_array(arr): n = len(arr) d = [0] * (n + 1) d[0] = arr[0] for i in range(1, n): d[i] = arr[i] - arr[i - 1] return d

def update(d, l, r, x): d[l] += x d[r + 1] -= x

def print_array(arr, d): for i in range(len(arr)): if i == 0: arr[i] = d[i] else: arr[i] = d[i] + arr[i - 1] print(arr[i], end=' ') print()

if name == 'main': arr = [10, 5, 20, 40] d = init_diff_array(arr) queries = [[1, 0, 1, 10], [2], [1, 1, 3, 20], [1, 2, 2, 30], [2]]

for query in queries:
    if query[0] == 1:
        # If it's an update query: update(l, r, x)
        l, r, x = query[1], query[2], query[3]
        update(d, l, r, x)
    elif query[0] == 2:
        # If it's a print query: print_array()
        print_array(arr, d)

C#

using System; using System.Collections.Generic;

class GfG{ static int[] InitDiffArray(int[] arr) { int n = arr.Length; int[] d = new int[n + 1]; d[0] = arr[0]; for (int i = 1; i < n; i++) { d[i] = arr[i] - arr[i - 1]; } return d; }

static void Update(int[] d, int l, int r, int x)
{
    d[l] += x;
    d[r + 1] -= x;
}

static void PrintArray(int[] arr, int[] d)
{
    for (int i = 0; i < arr.Length; i++) {
        if (i == 0)
            arr[i] = d[i];
        else
            arr[i] = d[i] + arr[i - 1];
        Console.Write(arr[i] + " ");
    }
    Console.WriteLine();
}

static void Main()
{
    int[] arr = { 10, 5, 20, 40 };
    int[] d = InitDiffArray(arr);
    List<int[]> queries = new List<int[]>{
        new int[] { 1, 0, 1, 10 }, new int[] { 2 },
        new int[] { 1, 1, 3, 20 },
        new int[] { 1, 2, 2, 30 }, new int[] { 2 }
    };

    foreach(var query in queries)
    {
        if (query[0] == 1) {
            // If it's an update query: update(l, r, x)
            int l = query[1];
            int r = query[2];
            int x = query[3];
            Update(d, l, r, x);
        }
        else if (query[0] == 2) {
            // If it's a print query: printArray()
            PrintArray(arr, d);
        }
    }
}

}

JavaScript

function initDiffArray(arr) { const n = arr.length; const d = new Array(n + 1).fill(0); d[0] = arr[0]; for (let i = 1; i < n; i++) { d[i] = arr[i] - arr[i - 1]; } return d; }

function update(d, l, r, x) { d[l] += x; d[r + 1] -= x; }

function printArray(arr, d) { for (let i = 0; i < arr.length; i++) { if (i === 0) arr[i] = d[i]; else arr[i] = d[i] + arr[i - 1]; process.stdout.write(arr[i] + " "); } console.log(); }

const arr = [ 10, 5, 20, 40 ]; const d = initDiffArray(arr); const queries = [ [ 1, 0, 1, 10 ], [ 2 ], [ 1, 1, 3, 20 ], [ 1, 2, 2, 30 ], [ 2 ] ];

queries.forEach(query => { if (query[0] === 1) { // If it's an update query: update(l, r, x) const l = query[1]; const r = query[2]; const x = query[3]; update(d, l, r, x); } else if (query[0] === 2) { // If it's a print query: printArray() printArray(arr, d); } });

`

**Output:

20 15 20 40 20 35 70 60

**Time complexity:
For update here is improved to O(1).
For printArray() still takes O(n) time.
**Auxiliary Space: O(n)