notas título Escova - e o prefixo

Prefixo e é rápido para atacar uma matriz estática um método dentro de um determinado intervalo eo número de todos. Se ocorre uma mudança no processo de determinação da matriz, então Fenwick árvore, linha de árvore e outros métodos podem ser utilizados.

Exemplos 1 e unidimensional prefixo

Introduzir uma sequência de comprimento n é um número inteiro.
Em seguida, e em seguida, a pesquisa de entrada m, cada par de pesquisa de entrada l, r.
Para cada consulta, a saída a partir do número de sequência original para o número de L e R.
Formato de entrada
A primeira linha contém dois números inteiros n e m.
A segunda linha contém n inteiro que representa o número da coluna um número inteiro.
Subsequentemente m linhas, cada linha contendo dois inteiros L e R, que representa o intervalo intervalo de uma consulta.
Formato de Saída de
co m linhas, cada linha produz um resultado do inquérito.

Intervalo de dados

\ (\ 1≤l≤r≤n)
\ (1 ≦ n, m≤100000 \)
\ (- valor do número de elementos em 1000≤ ≤1000 \)

#include <cstring>
#include <cstdio>
#include <iostream>
#include <algorithm>
using namespace std;
const int N = 100010;
int n,m;
int s[N];
int a[N];
int main(void)
{
    scanf("%d%d",&n,&m);
    for(int i = 1;i <= n;i++)
    {
        scanf("%d",&a[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-1]);
    }
    return 0;
    
}

Exemplo 2 prefixo e dimensional

Introduzir uma matriz inteiro de n linhas e m colunas, em seguida, introduzir uma consulta q, cada desafio compreendendo quatro inteiros X1, Y1, X2, Y2, coordenadas superior esquerdo e inferior direito coordenadas representa um sub-matrizes.
Para cada matriz de saída sub-consulta e todos os números.
Formato de entrada
A primeira linha contém três inteiros n, m, q.
Próximo n linhas, cada linha contém números inteiros m representa um número inteiro de matriz.
linhas q próximos, cada linha que compreende quatro inteiros X1, Y1, X2, Y2, representa um grupo de consulta.
Formato de Saída de
linhas q colegas, cada linha produz um resultado do inquérito.
O intervalo de dados
\ (1 ≦ n, m≤1000 \)
\ (1≤q≤200000 \)
(\ 1≤x1≤x2≤n) \
\ (- 1000≤ matriz valores de elementos dentro ≤1000 \)

#include <cstring>
#include <cstdio>
#include <iostream>
#include <algorithm>
using namespace std;

const int N = 1010;
int a[N][N];
int s[N][N];
int n,m,q;
int main(void)
{
    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]);
            s[i][j] = s[i -1][j] + s[i][j-1] - s[i-1][j-1] + a[i][j];
        }
    while(q--)
    {
        int x1,x2,y1,y2;
        scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
        printf("%d\n",s[x2][y2] - s[x2][y1-1] - s[x1-1][y2] + s[x1-1][y1-1]);
    }
    return 0;
    
            

}

Exercício 1 K tempos de intervalo

Dado um comprimento do número de colunas de N, em que se uma subsequência contígua é um múltiplo da soma de K, a que chamamos esse intervalo [i, j] é K vezes o intervalo.
Você pode encontrar o número de colunas no número total de K vezes o intervalo é?

Intervalo de dados

\ (1≤N, K≤100000 \)
\ (1≤Ai≤100000 \)

ideias:

  1. Por posições duplas start loop e final da sequência de controlo, cada pedido de passagem de cada subsequência e S [r] - S [L -1]% K é igual a 0, a complexidade de tempo é \ (O (n ^ 2) \) , sobre \ (10 ^ 9 \) da ordem, é necessário considerar uma redução do tempo de complexidade.
    2. A forma geral é a de reduzir a complexidade do tempo de espaço para o tempo .
  2. S [r] - S [L -1]% k == 0 é equivalente a s [n] o% k == s [L-1]% K, é possível para declarar uma matriz utilizada para armazenar um resto de s [i] k% do número, de modo que apenas uma é circulado.
    4. Note-se que os dados de excesso

código:

#include <cstring>
#include <cstdio>
#include <iostream>
#include <algorithm>
using namespace std;
typedef long long LL;
const int N = 100010;
int n,k;
LL s[N],cnt[N];
int main(void)
{
    scanf("%d %d",&n,&k);
    //计算前缀和
    for(int i = 1; i <= n;i++){
        scanf("%lld",&s[i]);     //注意LL的读取
        s[i] += s[i-1];
    }
    LL ans = 0;                 //注意答案可能溢出
    for(int i = 0;i <= n;i++)   //考虑和为0也也是k倍区间,所以从0开始遍历
    {
        //假设已经有两个S[i]的余数为x,则又有一个S[i]%k == x时,会产生两个新的答案,所以有下面两句
        ans += cnt[s[i] % k];
        cnt[s[i] % k]++;
    }
    printf("%lld",ans);
    return 0;
}

Acho que você gosta

Origin www.cnblogs.com/zy200128/p/12616856.html
Recomendado
Clasificación