栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

具有多段三次贝塞尔曲线和距离以及曲率约束的近似数据

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

具有多段三次贝塞尔曲线和距离以及曲率约束的近似数据

我找到了满足我的要求的解决方案。解决方案是,首先找到一个B样条曲线,该样条线在最小二乘方意义上近似点,然后将该样条曲线转换为多段贝塞尔曲线。B样条线确实具有以下优点:与贝塞尔曲线相反,它们不会通过控制点,并且提供了一种方法来指定近似曲线的所需“平滑度”。生成此类样条曲线所需的功能在scipy提供python绑定的FITPACK库中实现。让我们假设我读我的数据导入列表

x
y
的话,我可以这样做:

import matplotlib.pyplot as pltimport numpy as npfrom scipy import interpolatetck,u = interpolate.splprep([x,y],s=3)unew = np.arange(0,1.01,0.01)out = interpolate.splev(unew,tck)plt.figure()plt.plot(x,y,out[0],out[1])plt.show()

如果希望曲线更平滑,则可以将

s
参数增加到
splprep
。如果我希望近似值更接近数据,则可以减小
s
参数以减少平滑度。通过以
s
编程方式遍历多个参数,我可以找到适合给定要求的良好参数。

不过,问题是如何将结果转换为贝塞尔曲线。Zachary
Pincus在此电子邮件中的答案。我将在此处复制他的解决方案,以完整回答我的问题:

def b_spline_to_bezier_series(tck, per = False):  """Convert a parametric b-spline into a sequence of Bezier curves of the same degree.  Inputs:    tck : (t,c,k) tuple of b-spline knots, coefficients, and degree returned by splprep.    per : if tck was created as a periodic spline, per *must* be true, else per *must* be false.  Output:    A list of Bezier curves of degree k that is equivalent to the input spline.     Each Bezier curve is an array of shape (k+1,d) where d is the dimension of the    space; thus the curve includes the starting point, the k-1 internal control     points, and the endpoint, where each point is of d dimensions.  """  from fitpack import insert  from numpy import asarray, unique, split, sum  t,c,k = tck  t = asarray(t)  try:    c[0][0]  except:    # I can't figure out a simple way to convert nonparametric splines to     # parametric splines. Oh well.    raise TypeError("only parametric b-splines are supported.")  new_tck = tck  if per:    # ignore the leading and trailing k knots that exist to enforce periodicity     knots_to_consider = unique(t[k:-k])  else:    # the first and last k+1 knots are identical in the non-periodic case, so    # no need to consider them when increasing the knot multiplicities below    knots_to_consider = unique(t[k+1:-k-1])  # For each unique knot, bring it's multiplicity up to the next multiple of k+1  # This removes all continuity constraints between each of the original knots,   # creating a set of independent Bezier curves.  desired_multiplicity = k+1  for x in knots_to_consider:    current_multiplicity = sum(t == x)    remainder = current_multiplicity%desired_multiplicity    if remainder != 0:      # add enough knots to bring the current multiplicity up to the desired multiplicity      number_to_insert = desired_multiplicity - remainder      new_tck = insert(x, new_tck, number_to_insert, per)  tt,cc,kk = new_tck  # strip off the last k+1 knots, as they are redundant after knot insertion  bezier_points = numpy.transpose(cc)[:-desired_multiplicity]  if per:    # again, ignore the leading and trailing k knots    bezier_points = bezier_points[k:-k]  # group the points into the desired bezier curves  return split(bezier_points, len(bezier_points) / desired_multiplicity, axis = 0)

因此B样条曲线,FITPACK,numpy和scipy挽救了我的一天:)



转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/652834.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号