[二维树状数组]计数问题

题目描述

 一个n*m的方格,初始时每个格子有一个整数权值。接下来每次有2种操作:
改变一个格子的权值;
求一个子矩阵中某种特定权值出现的个数。

输入

第一行有两个数n,m。
接下来n行,每行m个数,第i+1行第j个数表示格子(i,j)的初始权值。
接下来输入一个整数q。
接下来q行,每行描述一个操作。
操作1:“1 x y c”(不含双引号)。表示将格子(x,y)的权值改成c(1<=x<=n,1<=y<=m,1<=c<=100)。
操作2:“2 x1 x2 y1 y2 c”(不含双引号,x1<=x2,y1<=y2)。表示询问所有满足格子权值为c,且x1<=x<=x2,y1<=y<=y2的格子(x,y)的个数。

输出

对于每个操作2,按照在输入中出现的顺序,依次输出一行一个整数表示所求得的个数。

样例输入

3 3
1 2 3
3 2 1
2 1 3
3
2 1 2 1 2 1
1 2 3 2
2 2 3 2 3 2

样例输出

1
2

提示

对于30%的数据n,m<=30,q<=10000
对于100%的数据 n,m<=300,q<=100000,1<=c<=100

思路:求询问区间内某一个值出现的次数;
单点更新:若在某个位置(i,j)出现了某个数k则标记为1(三位数组c[i][j][k]记录这个信息),原先的数标记为0;
区间求和:求区间内某个数k出现次数即调用getsum(i,j,k)求和c[..][..][k]数组得到(1,1)-(i,j)内k出现的次数;结果是getsum(xx,yy,k)-getsum(xx,y-1,k)-getsum(x-1,yy,k)+getsum(x-1,y-1,k);(容斥原理)
AC代码:
#include <iostream>
#include<cstdio>
#define lowbit(x) x&(-x)
using namespace std;

int n,m;
int Map[310][310];
int c[310][310][110];

void add(int x,int y,int k,int val){
   for(int i=x;i<=n;i+=lowbit(i)){
     for(int j=y;j<=m;j+=lowbit(j)){
        c[i][j][k]+=val;
     }
   }
}

int getsum(int x,int y,int k){
   int ret=0;
   for(int i=x;i>0;i-=lowbit(i)){
     for(int j=y;j>0;j-=lowbit(j)){
        ret+=c[i][j][k];
     }
   }
   return ret;
}

int main()
{
    scanf("%d%d",&n,&m);
    for(int i=1;i<=n;i++){
        for(int j=1;j<=m;j++){
            scanf("%d",&Map[i][j]);
            add(i,j,Map[i][j],1);
        }
    }
    int q;
    scanf("%d",&q);
    while(q--){
        int op;
        scanf("%d",&op);
        if(op==1){
            int x,y,k;
            scanf("%d%d%d",&x,&y,&k);
            add(x,y,Map[x][y],-1);
            add(x,y,k,1);
            Map[x][y]=k;
        }
        if(op==2){
            int x,xx,y,yy,k;
            scanf("%d%d%d%d%d",&x,&xx,&y,&yy,&k);
            printf("%d\n",getsum(xx,yy,k)-getsum(x-1,yy,k)-getsum(xx,y-1,k)+getsum(x-1,y-1,k));
        }
    }
    return 0;
}
 

转载于:https://www.cnblogs.com/lllxq/p/9095555.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 好的,关于python二维数组多条件计数,我可以给您一些思路和代码实现。假设我们有一个二维数组arr,现在需要按照多个条件进行计数。以两个条件为例:如果arr[i][j]满足条件A并且满足条件B,则计数器count加1。可以使用双重循环遍历二维数组,使用if语句判断条件A和条件B是否同时满足,满足则count加1。 示例代码如下: count = 0 for i in range(len(arr)): for j in range(len(arr[i])): if 条件A and 条件B: count += 1 其中,条件A和条件B需要根据具体业务逻辑来定义和实现。 希望能帮到您,还有需要我回答的问题吗? ### 回答2: 要实现 Python 二维数组的多条件计数,可以通过遍历数组元素并应用条件进行计数的方式来实现。 首先,可以创建一个变量来记录满足条件的元素数量,初始值设为 0。然后,使用嵌套的 for 循环来遍历二维数组的每个元素。在每个元素上,进行多条件的判断,如果满足所有条件,就将计数变量加 1。最后,返回计数结果。 以下是一个简单的示例代码: ```python def count_multi_condition(array, condition1, condition2): count = 0 for row in array: for element in row: if condition1(element) and condition2(element): count += 1 return count ``` 在这个示例中,`array` 是二维数组,`condition1` 和 `condition2` 是两个用于判断元素是否满足条件的函数。函数 `count_multi_condition` 返回满足所有条件的元素数量。 假设有一个二维数组 `matrix`,我们想要统计满足两个条件的元素数量,条件是元素的值大于 5,且能被 3 整除。我们可以定义两个条件判断函数,并调用 `count_multi_condition` 来进行计数: ```python def greater_than_5(num): return num > 5 def divisible_by_3(num): return num % 3 == 0 matrix = [[1, 2, 3], [6, 7, 8], [9, 10, 11]] count = count_multi_condition(matrix, greater_than_5, divisible_by_3) print(count) # 输出结果为 2 ``` 这个例子输出的结果为 2,因为满足条件的元素有 6 和 9。所以我们可以使用 `count_multi_condition` 函数来计算二维数组中满足多个条件的元素数量。 ### 回答3: 在Python中,可以使用二维数组来存储数据,并且可以使用多个条件来计数。 首先,我们需要创建一个二维数组,可以使用列表嵌套的方式来创建。例如,我们可以创建一个3x3的二维数组: ```python matrix = [[1, 2, 3], [4, 5, 6], [7, 8, 9]] ``` 接下来,我们可以使用两个嵌套的循环来遍历二维数组中的每一个元素,并通过判断条件来计数。例如,假设我们要计数二维数组中值为偶数且大于5的元素个数,可以使用如下代码: ```python count = 0 # 计数器变量 # 遍历二维数组 for row in matrix: for num in row: # 判断条件 if num % 2 == 0 and num > 5: count += 1 print(count) # 输出符合条件的元素个数 ``` 这段代码的运行结果将是2,因为二维数组中值为6和8的元素同时满足条件。 通过以上的方法,我们可以使用Python来实现对二维数组进行多条件的计数。这种方法适用于其他类型的判断条件,只需要修改判断条件的逻辑即可。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值