最远点采样(FSP)是一种常用的采样算法,主要用于点云数据(如激光雷达点云数据、分子坐标等)的采样。

一:算法原理

最远点采样的研究对象是点云数据,即一堆离散的坐标点。广义上其它许多样本数据类型也可以使用FPS算法并进行最远点采样,如我们经常使用的iris、dry bean dataset等数据集的数据类型,这些数据可以把每一条看做p维空间中的一个点,并且也可以用各种距离度量方法计算各条数据之间的距离。兔兔在这里为了方便,只针对三维点云数据进行实例讲解。

FPS的核心思想是使得所有采样点之间的距离尽可能的远,也就是数据尽可能的离散均匀。例如对于数据(1,2,3,4,5,6,7,8,9),我们若需要采集3个点,第一个点为1,那么第二个点就需要选择与1最远的点,即9,第三个点需要与1和9都尽可能的远,即5。当然,如果我们继续取点,则需要与1,5,7距离都尽可能的远,即3或7。这个过程是我们的一种直观理解,对于这一类问题,我们需要一种确定的算法来进行采样。

1.首先,对于三维点云数据,我们一般采取欧式距离度量点之间距离,即空间中两点直线距离。

2.在对第一个点采样时,理论上我们可以随机从数据中选取一个点。另一种规范的做法是:求整个数据点(点云)的重心(即所有点坐标求和平均得到的坐标点),选取距离重心最远的点,记为P0。

3. 然后,我们继续选取剩余的所有点中距离P0最远的点,记为P1。

4. 对于剩下的每个点,分别计算到P0和P1的距离,并选取最短的那个作为这个点到P0,P1整体的距离。计算这些距离后选择距离最大的那个点,记为P2。

5. 依次重复操作,直到选取所需数目的点。例如:继续选取点,分别计算剩余各点到P0,P1,P2的距离,并选取最短的那个距离作为某点到P1,P2,P3整体的距离,然后选取这些点中距离最大的那个点,记为P3。

在算法实现的过程中,在第3步计算所有点到P0距离时,我们不妨定义一个一维数据L,L中各个位置的值表示各点到P0的距离,L中值最大的那个索引对应的点即为P1。寻找P2时,我们计算各点到P1距离,如果距离小于到P0的距离,就更新L数组中相应位置的值,否则不更改,计算好后L中值最大的那个索引对应的点即为P2,以此类推。

二:算法实现

import numpy as npdef distance(p1,p2):return np.sqrt(np.sum((p1-p2)**2))def FPS(sample,num):'''sample:采样点云数据,num:需要采样的数据点个数'''n=sample.shape[0]center=np.mean(sample,axis=0) #点云重心select_p=[] #储存采集点索引L=[]for i in range(n):L.append(distance(sample[i],center))p0=np.argmax(L)select_p.append(p0) #选距离重心最远点p0L=np.zeros(shape=n)for i in range(num-1):for p in range(n):d = []for j in select_p:d.append(distance(sample[j],sample[p]))d=min(d)L[p]=dselect_p.append(np.argmax(L))return select_p,sample[select_p]point=np.random.randint(0,20,size=(200,3))
index,select_sample=FPS(sample=point,num=100)
print(index,select_sample)

当然,上述代码虽然比较直观,并且能够实现FPS采样,但是每一次都需要重复计算点到各采样点的值,这样会使程序运行速度慢,兔兔运行时需要8.52s。

import numpy as npdef distance(p1,p2):return np.sqrt(np.sum((p1-p2)**2))def FPS(sample,num):'''sample:采样点云数据,num:需要采样的数据点个数'''n=sample.shape[0]center=np.mean(sample,axis=0) #点云重心select_p=[] #储存采集点索引L=[]for i in range(n):L.append(distance(sample[i],center))p0=np.argmax(L)select_p.append(p0) #选距离重心最远点p0L=[]for i in range(n):L.append(distance(p0,sample[i]))select_p.append(np.argmax(L))for i in range(num-2):for p in range(n):d=distance(sample[select_p[-1]],sample[p])if d<=L[p]:L[p]=dselect_p.append(np.argmax(L))return select_p,sample[select_p]index,select_sample=FPS(sample=point,num=100)
print(index,select_sample)

改进后代码的运行时间约为0.24s,时间明显缩短许多。

三:总结

FPS作为一种采样算法,够对一些数据进行有效的采样,在实际问题中具有广泛应用,例如:当今十分热门的PointNet++中也使用了这种方法,我想很多同学也是因为PointNet++等模型来学习FPS算法,但是FPS的应用远远不止局限于此,它的这种方法与思想仍可以更广泛地应用于其它方面。

最远点采样(Farthest Point Sampling,FPS)算法详解相关推荐

  1. 最远点采样(Farthest Point Sampling)

    简介 以下我们将最远点采样(Farthest Point Sampling)简记为FPS.这种采样方法我觉得非常有趣.个人觉得比随机采样得到的数据能够表现更多的"轮廓性",其次用的 ...

  2. 最远点采样(Farthest Point Sampling)介绍

    最远点采样(Farthest Point Sampling)是一种非常常用的采样算法,由于能够保证对样本的均匀采样,被广泛使用,像3D点云深度学习框架中的PointNet++对样本点进行FPS采样再聚 ...

  3. ChatGPT模型采样算法详解

    ChatGPT模型采样算法详解 ChatGPT所使用的模型--GPT(Generative Pre-trained Transformer)模型有几个参数,理解它们对文本生成任务至关重要.其中最重要的 ...

  4. 基于 CADisplayLink 的 FPS 指示器详解

    前言 之前在开发中有使用到计时器NSTimer,后来了解到iOS中不同的计时方法,其中就包括了CADisplayLink.基于CADisplayLink以屏幕刷新频率同步绘图的特性,尝试根据这点去实现 ...

  5. php下载文件代码详解,php将远超文件下载到本地的示例代码详解

    注:这个demo适用的是yii框架,如果您使用的不是yii框架,这个方法也适用您,简单的了解一下思路/** * 保存文件到本地 * @param 文件路径 $url * @param 保存本地路径 $ ...

  6. Matlab库中过采样函数rcosflt参数及源代码详解(翻译)

    函数定义 rcosflt函数作为MATLAB即将被替换的函数,在MATLAB R2018b中还可以使用,但是已经查不到帮助文档:虽说是要即将被替换,但是函数内部的原理其实都是一样的,这个函数搞懂了,不 ...

  7. FPS游戏通用自瞄与透视算法详解!!

    自瞄算法与实现: 1:首先我们要找到一个敌人的三维坐标. 2:我们还要找到自己的三维坐标. 3:我们还要找到自己的鼠标坐标X与Y(这里的鼠标坐标X与Y是角度,X为360,Y正中间为0向上减少到负90度 ...

  8. FPS(farthest_point_sample) 最远点采样并可视化(附open3d python代码)

    最远点采样(Farthest Point Sampling)是一种非常常用的采样算法,由于能够保证对样本的均匀采样,被广泛使用. 一句话概括就是不断迭代地选择距离已有采样点集合的最远点. FPS算法原 ...

  9. 图解点云深度学习中FPS(Farthest Point Sampling)--最远点采样算法

    一.回忆Farthest Point Sampling算法过程(建议详细看完) 我们选取一个点云,我们假设整个点集为一共有n个点,来进行算法的讲解. 随机在整个点集中选取一个点作为起始点,并且放入集合 ...

最新文章

  1. aspnetcore mvc 异常处理_深入探究ASP.NET Core异常处理中间件
  2. java synchronized关键字_Java:手把手教你全面学习神秘的Synchronized关键字
  3. 2021年 第12届 蓝桥杯【备赛直播公开课 —— 软件类(本科组、高职高专组)】
  4. Python学习:函数
  5. JavaScript实现数除以二divideByTwo算法(附完整源码)
  6. linux ll 转数组,List、Set、数组之间的转换
  7. nginx禁止访问目录中可执行文件
  8. 图表展示结果开发(一)
  9. 方法的重写、重载及隐藏
  10. CTS,CLS,CLR解释
  11. Java中的抽象类与abstract关键字
  12. 3D数学---坐标空间
  13. 数字图像处理(19): 边缘检测算子(Roberts算子、Prewitt算子、Sobel算子 和 Laplacian算子)
  14. 【优化算法】模拟退火算法简介
  15. 安装VMware虚拟机及镜像文件
  16. HTC M8t unlock Bootloader/Root/S-OFF/解网络锁笔记
  17. 华为的提倡大家学雷锋,绝不让雷锋吃亏
  18. 无法从共享目录中映射段 linux,在Linux中Varnish无法启动:无法从共享对象映射段:不允许操作...
  19. win10系统qq远程不能控制怎么办?
  20. [Linux] sed命令详解

热门文章

  1. Coursera - Algorithm (Princeton) - 课程笔记 - Week 12
  2. Python的内置函数(三十)、iteritems()
  3. 连接docker中postgresql数据库出现Connection matched pg_hba.conf line 99: “host all all all md5“
  4. java彩虹雨_Java字符串分割
  5. oracle数据库怎么更改表名,oracle如何修改表名_数据库
  6. JAVA 文件url转存本地
  7. 第五次笔记:SRAM和DRAM 栅极电容 双稳态触发器 DRAM和SRAM比较 DRAM刷新 DRAM地址复用技术
  8. https通信加密过程
  9. 6126. 设计食物评分系统
  10. 反向传播的直观理解 (以及为什么反向传播是一种快速的算法)