除此efficient algorithm for list edits之外,我正在为另一个“循环计算”寻找更有效的算法。 这次我有一个矩阵:
grid_z1 = [[1,2,3],
[4,5,6],
[7,8,9]]
并且用户可以输入几个参数:目标是,将矩阵内的值更改为次高的参数值(如果矩阵值高于max(参数),则将其更改为nan例如,当用户输入“4”和“7”时,矩阵值“5”将变为“7”(=输入值的下一个最高值)。 例如:
h = [2, 7, 4] # user entered this three values
grid_z1 = [[2, 2, 4],
[4, 7, 7],
[7, nan, nan]] # this should be my output
此外,我想计算更改为给定值的值的数量。在我的例子中,这应该是[2,2,3] - > 2x2,2x4,3x7
h.sort()
h.reverse()
count = [0]*len(h)
for i in range(len(grid_z1)):
for j in range(len(grid_z1[0])):
if grid_z1[i][j] > max(h):
grid_z1[i][j] = float('NaN')
else:
for k in range(len(h)-1):
if grid_z1[i][j] <= h[k] and grid_z1[i][j] > h[k+1]:
grid_z1[i][j] = h[k]
count[k] += 1
if grid_z1[i][j] <= min(h):
grid_z1[i][j] = min(h)
count[-1] += 1
print grid_z1
print count
但又一次很慢。遗憾的是,我不理解zip方法足以将其用于更复杂的算法。
答案 0 :(得分:2)
使用bisect模块:
from bisect import bisect_left
def solve(matrix, param):
param.sort() #Sort the params passed by user
maxx = param[-1] #Find max
for row in matrix:
# If item in the row is greater than `maxx` then use Nan
# else use bisect_right to get the next highest item from
# params in O(log N) time.
yield [float('nan') if item > maxx else
param[bisect_left(param, item)] for item in row]
grid_z1 = [[1,2,3],
[4,5,6],
[7,8,9]]
print list(solve(grid_z1, [2, 7, 4]))
输出
[[2, 2, 4], [4, 7, 7], [7, nan, nan]]
答案 1 :(得分:0)
for i,row in enumerate(g):
g[i] = [float('nan') if item > max(h) else min([x for x in h if x >= item]) for item in row]