根据 python 中的 x、y 变化确定形状
determine shape from x,y change in python
我正在使用 python 跟踪鼠标在一段时间内的 x、y 变化以检测形状。例如,向西南延伸的对角线的 x-y 变化为 [1,1]
,而 v 形的图案可能为 [[1,1],[1,-1]]
.
当从与之前相同的方向和相同的点构建形状时,此方法效果很好,但是,您可以从四个不同的起始位置以顺时针或逆时针方式构建正方形。如果我们尝试检测所有可能的配置,列表将如下所示:
# Clockwise
[[0,1],[1,0],[0,-1],[-1,0]]
[[1,0],[0,-1],[-1,0],[0,1]]
[[0,-1],[-1,0],[0,1],[1,0]]
[[1,0],[0,1],[-1,0],[0,-1]]
# Counter-Clockwise
[[0,-1],[1,0],[0,1],[-1,0]]
[[-1,0],[0,-1],[1,0],[0,1]]
[[0,1],[-1,0],[0,-1],[1,0]]
[[-1,0],[0,1],[1,0],[0,-1]]
有没有一种方法可以测试给定的 x,y 变化列表是否会形成一个正方形,而无需为每种可能性进行查找 table?
您可以使用集合代替列表,使用元组代替列表来跟踪 xy 变化(您不能在集合内部使用列表,因为列表是可变的,因此不能被散列)。
square = {(0,-1), (1,0), (0,1), (-1,0)}
user_mov = {(1,0), (0,-1), (-1,0), (0,1)}
square == user_mov
# True
如果运动可能包含一个点两次,而您想确保它出现两次,则不能使用集合,而是可以对列表进行排序并进行比较
square = [[0,-1], [1,0], [0,1], [-1,0]]
user_mov = [[1,0], [0,-1], [-1,0], [0,1]]
sorted(square) == sorted(user_mov)
# True
是的,你可以!如果您希望形状由相同的 n
个点组成,但只是从任何起点按顺序或反向遍历,那么您可以检查是否可以在不跳过的情况下按顺序拉出所有点除了数组的末尾:
def verify_candidate(candidate, reference):
candidate_start = candidate[0]
if candidate_start not in reference or len(candidate) != len(reference):
return False
rfi = reference.index(candidate_start)
for pti in range(len(candidate)):
if candidate[pti] != reference[rfi]: # if, at any index, there is a mismatch, then fail.
return False
rfi = (rfi + 1) % len(reference) # avoid index error
return True
verify_candidate(user, square)
verify_candidate(user, list(reversed(square)))
我正在使用 python 跟踪鼠标在一段时间内的 x、y 变化以检测形状。例如,向西南延伸的对角线的 x-y 变化为 [1,1]
,而 v 形的图案可能为 [[1,1],[1,-1]]
.
当从与之前相同的方向和相同的点构建形状时,此方法效果很好,但是,您可以从四个不同的起始位置以顺时针或逆时针方式构建正方形。如果我们尝试检测所有可能的配置,列表将如下所示:
# Clockwise
[[0,1],[1,0],[0,-1],[-1,0]]
[[1,0],[0,-1],[-1,0],[0,1]]
[[0,-1],[-1,0],[0,1],[1,0]]
[[1,0],[0,1],[-1,0],[0,-1]]
# Counter-Clockwise
[[0,-1],[1,0],[0,1],[-1,0]]
[[-1,0],[0,-1],[1,0],[0,1]]
[[0,1],[-1,0],[0,-1],[1,0]]
[[-1,0],[0,1],[1,0],[0,-1]]
有没有一种方法可以测试给定的 x,y 变化列表是否会形成一个正方形,而无需为每种可能性进行查找 table?
您可以使用集合代替列表,使用元组代替列表来跟踪 xy 变化(您不能在集合内部使用列表,因为列表是可变的,因此不能被散列)。
square = {(0,-1), (1,0), (0,1), (-1,0)}
user_mov = {(1,0), (0,-1), (-1,0), (0,1)}
square == user_mov
# True
如果运动可能包含一个点两次,而您想确保它出现两次,则不能使用集合,而是可以对列表进行排序并进行比较
square = [[0,-1], [1,0], [0,1], [-1,0]]
user_mov = [[1,0], [0,-1], [-1,0], [0,1]]
sorted(square) == sorted(user_mov)
# True
是的,你可以!如果您希望形状由相同的 n
个点组成,但只是从任何起点按顺序或反向遍历,那么您可以检查是否可以在不跳过的情况下按顺序拉出所有点除了数组的末尾:
def verify_candidate(candidate, reference):
candidate_start = candidate[0]
if candidate_start not in reference or len(candidate) != len(reference):
return False
rfi = reference.index(candidate_start)
for pti in range(len(candidate)):
if candidate[pti] != reference[rfi]: # if, at any index, there is a mismatch, then fail.
return False
rfi = (rfi + 1) % len(reference) # avoid index error
return True
verify_candidate(user, square)
verify_candidate(user, list(reversed(square)))