从曲线外部的用户给定点求出曲线上的切点

时间:2015-04-26 17:36:34

标签: matlab geometry curve-fitting polynomials

我试图从闭合曲线外的给定点(不在曲线上)找到切线。该曲线被定义为点的2D x和y坐标,例如形状像不规则的椭圆。

如果用户给出一个点:(x0,y0)=(-30,80),我怎么知道曲线上的切点(显然是平滑曲线中离散点之间的最近点)(即切线来自(x0,y0)到曲线)?

1 个答案:

答案 0 :(得分:4)

一种可能性是使用数值微分来找到每个点处的切线,并确定它是否“足够接近”给定点。然而,人们必须认真思考“足够接近”以避免得不到匹配或太多。

这是另一种方法:考虑从给定点(x0,y0)指向曲线上的点的单位向量。找到它们之间的最大差距(命令convhull在这里有帮助)。间隙两侧的矢量确定切线。

一般来说,这只会找到两条切线,而不是全部切线。但如果曲线是凸的,那么无论如何只有两条切线。

这是一个棘手情况的例子,其中给定点位于曲线的凸包内。

tricky

产生上述图片的代码:

var routines = [NSManagedObject]()

override func viewWillAppear(animated: Bool) {

    self.navigationItem.leftBarButtonItem = self.editButtonItem()

    let appDelegate = UIApplication.sharedApplication().delegate as! AppDelegate
    let managedContext = appDelegate.managedObjectContext!

    let fetchRequest = NSFetchRequest(entityName: "Routine")

    var error: NSError?

    let fetchedResults = managedContext.executeFetchRequest(fetchRequest, error: &error) as! [NSManagedObject]?

    if let results = fetchedResults {
        routines = results
    } else {
        println("Could not fetch \(error), \(error!.userInfo)")
    }
}

另一种方法,如果(x0,y0)不在曲线的凸包内,则可以正常工作。

使用t = linspace(0,2*pi,100); x = 10*cos(t) + sin(7*t); y = 6*sin(t) + cos(13*t); % x,y describe the curve; x0 = 4; y0 = 5; % given point xn = (x-x0)./sqrt((x-x0).^2+(y-y0).^2); % unit vectors yn = (y-y0)./sqrt((x-x0).^2+(y-y0).^2); % from x0,y0 to points on the curve cvx = convhull(xn,yn); % convex hull of unit vectors [~,i] = max(diff(xn(cvx)).^2+diff(yn(cvx)).^2); % largest gap in the hull x1 = xn(cvx(i)); y1=yn(cvx(i)); % vectors on both sides x2 = xn(cvx(i+1)); y2=yn(cvx(i+1)); % of the gap plot(x,y) hold on s = linspace(0,10); plot(x0+s*x1, y0+s*y1, 'r') % output plot(x0+s*x2, y0+s*y2, 'r') hold off 查找曲线和给定点convhull的并集的凸包。凸出船体的两个入射到(x0,y0)的边缘与曲线相切:

convex hull

产生上述图片的代码:

(x0,y0)