Python 3:测试一行中的连续数字
Python 3: test for contiguous numbers in one line
我有一个运行良好的算法,但我希望以另一种方式实现它以获得个人满意度。
简而言之:我有一些数组 obj_level
,它是一个布尔掩码,指示对象所在的坐标,所以类似于
obj_level = [ 0, 0, 1, 1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0 , 1, 1 ]
我想识别物体的底部和顶部。
我首先通过生成一个包含对象非零索引的数组来做到这一点,obj_idx
。如果数组不为空,则第一个值附加到 base
.
然后我循环测试索引+1的值是否等于obj_idx
中的下一个对象。如果是,没有找到边,继续。
否则,我找到了一条边,所以我追加到 base
和 top
。我可以推断在找到的边上同时存在顶部和底部,因为在 obj_idx
中有更多值,因为我正在针对 obj_idx[i+1]
.
进行测试
最后,我将最后一个值附加到 top
,因为如果有底部,对象必须有顶部。
base = []
top = []
obj_idx = np.flatnonzero(obj_level)
if obj_idx.size > 0:
base . append(obj_idx[0])
for i,idx in enumerate(obj_idx[:-1]):
if idx+1 == obj_idx[i+1]:
continue
else:
top.append(idx)
base.append(obj_idx[i+1])
top.append(obj_idx[-1])
我想用更少的行来完成这项工作。类似于:
base = [
idx + 1 == obj_idx[i+1] or idx+1
for i,idx in enumerate(obj_idx[:-1])
]
top = [
(idx+1 == obj_idx[i+1] or idx
for i,idx in enumerate(obj_idx[:-1])
]
np.insert(base,0,obj_idx[0])
np.insert(top,-1,obj_idx[-1])
但我最终得到了一个类似 [True, True, 3, True, True]
的混合数组
有没有比从混合数组中提取整数更简单的方法?
您可以只使用列表理解中的 'if' 子句,如此处 if/else in a list comprehension 所述,以过滤源可迭代对象。类似的东西(我避免使用 numpy 连接值只是为了组成一个单行,但当然它不会改变任何东西):
base = [obj_idx[0]] + [
obj_idx[i+1] for i in range(1, len(obj_idx)-1) if (obj_idx[i+1] != obj_idx[i] + 1)
]
top = [
obj_idx[i] for i in range(1, len(obj_idx)-1) if (obj_idx[i+1] != obj_idx[i] + 1)
] + [obj_idx[-1]]
我有一个运行良好的算法,但我希望以另一种方式实现它以获得个人满意度。
简而言之:我有一些数组 obj_level
,它是一个布尔掩码,指示对象所在的坐标,所以类似于
obj_level = [ 0, 0, 1, 1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0 , 1, 1 ]
我想识别物体的底部和顶部。
我首先通过生成一个包含对象非零索引的数组来做到这一点,obj_idx
。如果数组不为空,则第一个值附加到 base
.
然后我循环测试索引+1的值是否等于obj_idx
中的下一个对象。如果是,没有找到边,继续。
否则,我找到了一条边,所以我追加到 base
和 top
。我可以推断在找到的边上同时存在顶部和底部,因为在 obj_idx
中有更多值,因为我正在针对 obj_idx[i+1]
.
最后,我将最后一个值附加到 top
,因为如果有底部,对象必须有顶部。
base = []
top = []
obj_idx = np.flatnonzero(obj_level)
if obj_idx.size > 0:
base . append(obj_idx[0])
for i,idx in enumerate(obj_idx[:-1]):
if idx+1 == obj_idx[i+1]:
continue
else:
top.append(idx)
base.append(obj_idx[i+1])
top.append(obj_idx[-1])
我想用更少的行来完成这项工作。类似于:
base = [
idx + 1 == obj_idx[i+1] or idx+1
for i,idx in enumerate(obj_idx[:-1])
]
top = [
(idx+1 == obj_idx[i+1] or idx
for i,idx in enumerate(obj_idx[:-1])
]
np.insert(base,0,obj_idx[0])
np.insert(top,-1,obj_idx[-1])
但我最终得到了一个类似 [True, True, 3, True, True]
有没有比从混合数组中提取整数更简单的方法?
您可以只使用列表理解中的 'if' 子句,如此处 if/else in a list comprehension 所述,以过滤源可迭代对象。类似的东西(我避免使用 numpy 连接值只是为了组成一个单行,但当然它不会改变任何东西):
base = [obj_idx[0]] + [
obj_idx[i+1] for i in range(1, len(obj_idx)-1) if (obj_idx[i+1] != obj_idx[i] + 1)
]
top = [
obj_idx[i] for i in range(1, len(obj_idx)-1) if (obj_idx[i+1] != obj_idx[i] + 1)
] + [obj_idx[-1]]