一.enumarate()函数
用来遍历一个集合对象,它在遍历的同时还可以得到当前元素的索引位置。
二.pop()函数
1.按索引删除元素
list.pop(index)#index不指定时默认删除最后一个元素
#也可返回被删除的元素
三.数组模拟单调队列
#数组模拟单调队列实现滑动窗口功能,求取所有子矩阵最大最小值的乘积
n,m,a,b=map(int,input().split())
A=[list(map(int,input().split())) for i in range(n)]
def get_max(num,size):
index = [] # 存放可能成为最大值的数的下标
ulti_max = [] # 存放最终的最大值
for i in range(0,len(num)):
while index and num[index[-1]]<num[i]:#后面来的元素大于前面的元素,那前面的元素就不可能再成为最大值
index.pop()
index.append(i)
if (i-index[0])>=size:#超出窗口大小,淘汰最老的选手
index.pop(0)
if i+1>=size:#已形成窗口,可以写入最大值
ulti_max.append(num[index[0]])
return ulti_max
def get_min(num,size):
index=[]#存放可能成为最小值的数的下标
ulti_min=[]#存放最终的最小值
for i in range(0,len(num)):
while index and num[index[-1]]>num[i]:#后面来的元素小于 前面的元素,那前面的元素就不可能再成为最小值
index.pop()
index.append(i)
if (i-index[0])>=size:#超出窗口大小,淘汰最老的选手
index.pop(0)
if i+1>=size:#已形成窗口,可以写入最小值
ulti_min.append(num[index[0]])
return ulti_min
row_max=[]
row_min=[]
for x in range(len(A)):
row_max.append(get_max(A[x],b))
row_min.append(get_min(A[x],b))
row_max_T=[[0 for i in range(len(row_max))] for j in range(len(row_max[0]))]
row_min_T=[[0 for i in range(len(row_min))]for j in range(len(row_min[0]))]
for i in range(len(row_max)):
for j in range(len(row_max[0])):
row_max_T[j][i]=row_max[i][j]
row_min_T[j][i]=row_min[i][j]
col_max=[]
col_min=[]
for x in range(len(row_max_T)):
col_max.append(get_max(row_max_T[x],a))
col_min.append(get_min(row_min_T[x],a))
col_max_T=[[0 for i in range(len(col_max))] for j in range(len(col_max[0]))]
col_min_T=[[0 for i in range(len(col_min))] for j in range(len(col_min[0]))]
for i in range(len(col_max)):
for j in range(len(col_max[0])):
col_max_T[j][i]=col_max[i][j]
col_min_T[j][i]=col_min[i][j]
value=0
for i in range(n-a+1):
for j in range(m-b+1):
value+=col_max_T[i][j]*col_min_T[i][j]
print(value%998244353)