Python 阵列中两点之间的最长路径

Python 阵列中两点之间的最长路径,python,algorithm,Python,Algorithm,我有一个代码,使用旋转卡尺的算法,定义了两个距离最远的点 代码在第一行中取点的数量N,然后N次取点X、Y的坐标。之后显示最长距离的长度 例如: INPUT 6 1 1 -1 0 -3 -1 -2 -2 2 3 4 -2 OUTPUT 7.0710678119 INPUT 6 2 2 0 -3 5 7 3 3 2 1 -1 1 OUTPUT 4.47213595499958 #my comment: from (3,3) to (5,7) 但在某些情况下,3个或多个点位于一条直线上。 那我

我有一个代码,使用旋转卡尺的算法,定义了两个距离最远的点

代码在第一行中取点的数量N,然后N次取点X、Y的坐标。之后显示最长距离的长度

例如:

INPUT
6
1 1
-1 0
-3 -1
-2 -2
2 3
4 -2

OUTPUT
7.0710678119

INPUT
6
2 2
0 -3
5 7
3 3
2 1
-1 1

OUTPUT
4.47213595499958 #my comment: from (3,3) to (5,7)
但在某些情况下,3个或多个点位于一条直线上。 那我该怎么做呢

from math import *

def rast(x1, x2, y1, y2):
        x = x2-x1
        y = y2-y1
        l = sqrt(pow(fabs(x), 2)+pow(fabs(y), 2));
        return l

def orientation(p,q,r):
    '''Return positive if p-q-r are clockwise, neg if ccw, zero if colinear.'''
    return (q[1]-p[1])*(r[0]-p[0]) - (q[0]-p[0])*(r[1]-p[1])

def hulls(Points):
    '''Graham scan to find upper and lower convex hulls of a set of 2d points.'''
    U = []
    L = []
    Points.sort()
    for p in Points:
        while len(U) > 1 and orientation(U[-2],U[-1],p) <= 0: U.pop()
        while len(L) > 1 and orientation(L[-2],L[-1],p) >= 0: L.pop()
        U.append(p)
        L.append(p)
    return U,L

def rotatingCalipers(Points):
    '''Given a list of 2d points, finds all ways of sandwiching the points
between two parallel lines that touch one point each, and yields the sequence
of pairs of points touched by each pair of lines.'''
    U,L = hulls(Points)
    i = 0
    j = len(L) - 1
    while i < len(U) - 1 or j > 0:
        yield U[i],L[j]

        # if all the way through one side of hull, advance the other side
        if i == len(U) - 1: j -= 1
        elif j == 0: i += 1

        # still points left on both lists, compare slopes of next hull edges
        # being careful to avoid divide-by-zero in slope calculation
        elif (U[i+1][1]-U[i][1])*(L[j][0]-L[j-1][0]) > \
                (L[j][1]-L[j-1][1])*(U[i+1][0]-U[i][0]):
            i += 1
        else: j -= 1

def diameter(Points):
    '''Given a list of 2d points, returns the pair that's farthest apart.'''
    diam,pair = max([((p[0]-q[0])**2 + (p[1]-q[1])**2, (p,q))
                     for p,q in rotatingCalipers(Points)])
    return pair

n=int(input())
dots = []
for i in range(n):
    tmp = [int(j) for j in input().split()]
    dots.append([tmp[0],tmp[1]])
tmp = diameter(dots)
d1,d2=tmp[0],tmp[1]
print(rast(d1[0],d2[0],d1[1],d2[1]))
从数学导入*
def rast(x1、x2、y1、y2):
x=x2-x1
y=y2-y1
l=sqrt(功率(晶圆(x),2)+功率(晶圆(y),2));
返回l
def方向(p、q、r):
“如果p-q-r为顺时针方向,则返回正值;如果为逆时针方向,则返回负值;如果为共线方向,则返回零。”
返回(q[1]-p[1])*(r[0]-p[0])-(q[0]-p[0])*(r[1]-p[1])
def外壳(点):
“Graham扫描以找到一组2d点的上下凸包。”
U=[]
L=[]
Points.sort()
对于p in点:
而len(U)>1和取向(U[-2],U[-1],p)1和取向(L[-2],L[-1],p)>=0:L.pop()
美国(p)
L.1(p)
返回U,L
def旋转卡钳(点):
''给定一个2d点列表,找到所有夹点的方法
在两条平行线之间,每条线接触一个点,并产生序列
由每对线接触的点对组成
U、 L=船体(点)
i=0
j=len(L)-1
当i0时:
收益率U[i],L[j]
#如果一直穿过船体的一侧,则推进另一侧
如果i==len(U)-1:j-=1
elif j==0:i+=1
#在两个列表中都保留点,比较下一个外壳边缘的坡度
#在坡度计算中小心避免被零除
elif(U[i+1][1]-U[i][1])*(L[j][0]-L[j-1][0])>\
(L[j][1]-L[j-1][1])*(U[i+1][0]-U[i][0]):
i+=1
其他:j-=1
def直径(点):
''给定2d点列表,返回相距最远的一对。''
直径,对=最大值([((p[0]-q[0])**2+(p[1]-q[1])**2,(p,q))
对于旋转卡钳中的p、q(点)])
返回对
n=int(输入())
点=[]
对于范围(n)中的i:
tmp=[int(j)表示输入中的j().split()]
dots.append([tmp[0],tmp[1]])
tmp=直径(点)
d1,d2=tmp[0],tmp[1]
打印(rast(d1[0],d2[0],d1[1],d2[1]))

制作凸面外壳后,需要按最长的长度对线条进行排序。在我的示例中,您将看到红线,然后是带箭头的蓝色


取最长的线(红色)并获取其角度。对于凸包中的每个点,检查S和P之间的线是否等于角度。如果是,请计算两条线SP和EP的距离,如果其中一条线比蓝线长,即最长的线,则可以停止。否则,忽略红线,选择下一条最长的。当没有相等的角度时,您可以停止。

您可以展示一些有效和无效的输入示例吗?添加到主题中,您可以解释“3个或多个点位于一条直线上”时的确切问题吗?这就是您如何看待现实。。任何点之间的最长距离在1,1和4,4之间。但你看到的是一条“路径”,当它们超过2个点在一条直线上排列时..我有点困惑。为什么从(2,2)到(4,4)的距离要比从(1,1)到(4,4)的距离长?