Suma de prefijo unidimensional para encontrar la suma de intervalo, suma de prefijo bidimensional para encontrar la suma de submatriz

Suma de prefijo unidimensional

La suma del prefijo es almacenar la suma de los primeros elementos i de cada i antes de una matriz a en la matriz s respectivamente, a saber: s [i] = s [i-1] + a [i]; de
acuerdo con la definición que puede hacerlo más fácil Encuentre la suma del intervalo, por
ejemplo, encuentre la suma entre [l, r] de la matriz a, si necesitamos atravesar una vez en circunstancias normales, for(int i = l; i <= r; i++)sum += a[i]esta complejidad de tiempo es O (n),
si el rango de intervalo dado en la pregunta Muy grande y eficiente en el tiempo. Si los prefijos y buscar e intervalo, el pretratamiento sesum[l , r] = s[r] - s[l - 1] puede lograr es O (n), la eficiencia del tiempo de interrogación O (1) que aumenta en gran medida la eficiencia.

modelo:

 s[i] = a[1] + a[2] + ... + a[i]
 a[l] + ... + a[r] = s[r] - s[l-1]

ejemplo:

Introduzca una secuencia de números enteros de longitud n.

Luego, ingrese m consultas e ingrese un par de l, r para cada consulta.

Para cada consulta, genere la suma desde el número 1 al número 6 en la secuencia original.

Formato de entrada La
primera línea contiene dos números enteros n y m.

La segunda fila contiene n números enteros, que representan una secuencia de números enteros.

En las siguientes m líneas, cada línea contiene dos números enteros lyr, que representan el rango de una consulta.

Formato de salida
Un total de m líneas, cada línea genera un resultado de consulta.

Rango de datos
1≤l≤r≤n,
1≤n, m≤100000,
−1000≤ El valor del elemento en la secuencia es ≤1000
Ejemplo de entrada:

5 3
2 1 3 6 4
1 2
1 3
2 4

Salida de muestra:

3
6
10

Implementación de código C ++:

#include<iostream>

using namespace std;

const int N =1e6+10; 

int n,m;
int a[N],s[N];

int main()
{
    
    

	scanf("%d%d",&n,&m);
	for(int i = 1;i <= n ;i++) scanf("%d",&a[i]);
	
	for(int i = 1;i <= n ;i++)
		s[i] = s[i-1] + a[i];  //前缀和的初始化 
	
	while(m--)
	{
    
    
		int l ,r;
		scanf("%d%d",&l,&r);
		printf("%d\n",s[r]-s[l]); //区间和的计算 
	}	
		
	return 0;
}

Suma de prefijo bidimensional

El principio de la suma del prefijo bidimensional es aproximadamente el mismo que el de la suma del prefijo unidimensional, excepto que se agrega la perspectiva bidimensional.
Primero pensemos en cómo encontrar el prefijo y la matriz S. Si la matriz bidimensional se usa como un sistema de coordenadas rectangular plano invertido ij.
Usamos el pensamiento matemático para obtener:s[i][j] = s[i-1][j] + s[i][j-1] - s[i-1][j-1] + a[i][j]

Inserte la descripción de la imagen aquí
Sabemos cómo obtener la matriz de suma de prefijos bidimensionales S. A continuación, tenemos que pensar en ¿qué pasa si solo necesitamos la suma de las submatrices?

Tome prestada una imagen en Internet para comprender:
Inserte la descripción de la imagen aquí
si necesitamos la suma de las matrices púrpuras en la Fig. 1, usamos la característica de la suma del prefijo para restar la suma de las matrices en la parte azul de la Fig. 3 y la Fig. 4 de la suma de las matrices amarillas en la figura 2 y encuentre En este momento, se resta una parte, que es la parte verde de la figura 4, por lo que debemos sumarla al final.
cual es:S = s[x2, y2] - s[x1 - 1, y2] - s[x2, y1 - 1] + s[x1 -1 , y1 - 1]

Al igual que lo anterior, la eficiencia del preprocesamiento es O (n) y la eficiencia de la consulta es O (1)

modelo:

S[i, j] = 第i行j列格子左上部分所有元素的和
S[i, j] = S[i-1][j] + S[i][j-1] - S[i-1][j-1] + a[i][j](x1, y1)为左上角,(x2, y2)为右下角的子矩阵的和为:
S[x2, y2] - S[x1 - 1, y2] - S[x2, y1 - 1] + S[x1 - 1, y1 - 1]

Ejemplo:
ingrese una matriz de enteros con n filas ym columnas, y luego ingrese q consultas. Cada consulta contiene cuatro enteros x1, y1, x2, y2, que representan las coordenadas de la esquina superior izquierda y la esquina inferior derecha de un sub- matriz.

Para cada consulta, genere la suma de todos los números en la submatriz.

Formato de entrada La
primera línea contiene tres números enteros n, m, q.

Las siguientes n filas, cada fila contiene m enteros, que representan una matriz de enteros.

En la siguiente línea q, cada línea contiene cuatro números enteros x1, y1, x2, y2, que representan un conjunto de consultas.

Formato de salida Hay
q líneas y cada línea genera un resultado de consulta.

Rango de datos
1≤n, m≤1000,
1≤q≤200000,
1≤x1≤x2≤n,
1≤y1≤y2≤m,
−1000≤ El valor del elemento en la matriz≤1000
Ejemplo de entrada:

3 4 3
1 7 2 4
3 6 2 8
2 1 2 3
1 1 2 2
2 1 3 4
1 3 3 4

Salida de muestra:

17
27
21

Código de implementación de C ++:

#include<iostream>

const int N = 1010;

using namespace std;

int n, m, q;
int a[N][N],s[N][N];

int main()
{
    
    
	scanf("%d%d%d",&n,&m,&q);
	for(int i = 1;i <= n;i++)
		for(int j = 1;j <= m ; j++)
			scanf("%d",&a[i][j]);
	
	for(int i = 1;i <= n ; i++)
		for(int j = 1; j <= m ;j++)
			s[i][j]	= s[i - 1][j] + s[i][j - 1] - s[i - 1][j - 1] + a[i][j];
	
	while(q --)
	{
    
    
		int x1, y1, x2, y2;
		scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
		printf("%d\n",s[x2][y2] - s[x1 - 1][y2] - s[x2][y1 - 1] + s[x1 -1][y1 -1]);
			
	}			
	return 0;	
} 

Supongo que te gusta

Origin blog.csdn.net/diviner_s/article/details/107348741
Recomendado
Clasificación