Last Updated: 25 Apr, 2021

Squares Sum

Hard
Asked in company
Flipkart limited

Problem statement

Given an array of ‘N’ integers and ‘q’ queries. The query is defined as below:-

Given two integers ‘l’ and ‘r’ ( ‘l’ >=0 and ‘r’ <= ‘N’) Find the sum of squares of all elements of the array with index in the range ‘l’ and ‘r’ (Inclusive).

Given three integers ‘l’ ,’r’ and ‘x’ ( ‘l’ >=0 and ‘r’ <= ‘N’) .Update the elements of the array by incrementing ‘x’ to all array elements with index in the range ‘l’ and ‘r’.

Given three integers ‘l’ ,’r’ and ‘x’ ( ‘l’ >=0 and ‘r’ <= ‘N’) .Update the elements of the array by setting ‘x’ to all array elements with index in the range ‘l’ and ‘r’.

Input Format :
The first line contains ‘T,’ denoting the number of test cases.

The first line of the test case contains a single integer ‘N’  denoting the size of the ‘arr’ array.

The second line of each test case contains ‘N’ space-separated integers denoting the array ‘arr’.

The third line of each test case contains an integer ‘q’ denoting the number of queries.

The next ‘q’  lines of each test case contain 3 or 4 space-separated integers denoting the following:

1 The first integer denotes the type of query.It can be either ‘0’ , ‘1’ , ‘2’.  ‘0’ denotes the range update query by adding ‘x’ to all array elements within the index range. ‘1’ denotes the range update query by setting ‘x’ to all array elements within the index range. ‘2’ denotes sum of squares type query. 

2 If the query is of ‘0’ and ‘1’ type then second, third and fourth integers in the same line denotes  ‘l’ ,’r’ and ‘x’ denotes the range for which to update the values.

3 If the query is of ‘2’ type then second and third integers in the same line denote ‘l’ and ‘r’  denotes the range for which to calculate the sum of squares.
Output Format :
For each query of type ‘2’  print the sum of squares .in the range of ‘l’ and ‘r’. For update query do not print anything just update the values in an array.
Constraints :
1 <= ’T’ <= 10
1 <= ‘N’ <= 1000
1 <= q <= 1000
1 <= arr[i] <= 1000
1 <= ‘x’ <= 1000

Where ‘i’ varies from 0 to ‘n’ -1  where ‘n’ is the length of the array ‘arr’,q is the number of queries ‘arr[i]’ is the value of the element at index ‘i’. ‘x’ is the number for updating the range. 


Time Limit: 1 sec

Approaches

01 Approach

The key idea is to process the queries as follows. For queries of type 2 simply run a loop from ‘l’ to ‘r’ find the sum of squares and print it.

 

For queries of type 0 and 1 run a loop from ‘l’ to ‘r’ and simply update the value.

02 Approach

The main idea is to process the queries efficiently we will use a segment tree. To know more about segment tree refer to this:- https://cp-algorithms.com/data_structures/segment_tree.html

At each node, we will store two values

 

  1. Sum:- The sum of all numbers in the subsegment which a particular node denotes to.

Sum_of_Squares:- The sum of squares of all numbers in the subsegment which a particular node denotes to.

Using these two values we can get the answer for query of type 2  for any segment.

Now to combine the answer from two child nodes we have to do the following:-

The Sum for the parent node will be:-

  • parent.Sum = leftChild.sum + rightChild.sum
  • parent.Sum_of_Squares = leftChild.Sum_of_Sqaures + rightChild.Sum_of_Squares

 

 

 2.    For Update query of type 0

We will use lazy_propogation.

For a particular segment that lies within the range of update query:-

Before update :

  • segment[index].Sum_of_Square = a1^2 +a2^2 +a3^2…

After Update 

  • segment[index].Sum_of_Square = (a1+x)^2 + (a2+x)^2 +(a3+x)^2….

  a1^2 + a2^2 … + (Number of values in segment)*x^2 + 2*(Sum of value before update in segment)*x

segment[index].Sum_of_Square = (Sum of Square before update) + 2*(Sum of values before update)*x + (Number of values in segment)*x^2.

Similarly 

  • Segment[index].Sum = (Sum of values before update) +  (Number of values in segment)*x .

 

 

 3.    For Update query of type 1

We will use lazy_propogation.

For a particular segment that lies within the range of update query:-

Before update :

  • segment[index].Sum_of_Square = a1^2 +a2^2 +a3^2…

After Update 

  • segment[index].Sum_of_Square = (x)^2 + (x)^2 +(x)^2….
  • segment[index].Sum_of_Square = (number of values in segment)*(x^2).

Similarly 

  • Segment[index].Sum = (Number of values in segment)*x .

We will set lazy values for its left and right child of type 1. We will remove the lazy values of its left and right of type 0 since it does not need to be updated.