【三种计算样本欧氏距离的方法——样本数据表示为矩阵】

这篇具有很好参考价值的文章主要介绍了【三种计算样本欧氏距离的方法——样本数据表示为矩阵】。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

三种计算样本欧氏距离的方法——样本数据表示为矩阵

背景

近期在看CS231n课程,作业中有关于计算图像样本间Kmeans距离的代码编写,涉及到的距离例如为欧氏距离,计算的三种方法效率由低到高,在学习的过程中令我收益匪浅。

假设图像大小为32*32*3=3072,提供5000个训练样本,500个测试样本,将图像矩阵展开为一维向量,则训练样本为5000*3072矩阵,测试样本为500*3072矩阵。

训练样本的标签已知,现要求计算每个测试样本与每个训练样本的欧氏距离,作为测试样本的分类依据,将计算的距离结果存放在dist矩阵中,dist[i][j]表示第i个测试样本与第j个训练样本的欧氏距离。


方法一:双循环逐个计算

对于500个测试样本,5000个训练样本,可以简单的通过两个嵌套的循环遍历计算样本之间的欧氏距离。这是最直观简单的想法,也最容易实现。

def cal_dist_two_loops(train, test):
	"""
	使用两层循环计算欧氏距离
	train为训练样本矩阵,大小为5000*3072
	test为测试样本矩阵,大小为500*3072
	dist为存放样本间距离的矩阵,dist[i][j]表示测试样本i与训练样本j之间的距离
	"""
	num_train = train.shape(0)	# 本文中为5000
	num_test = test.shape(0)	# 本文中为500

	for i in range(num_test):
		for j in range(num_train):
			dist[i][j] = np.sqrt(np.sum(np.square(test[i]-train[j])))

	return dist

在上述代码中,每次取traintest的一行进行相减,实际是1*3072向量每个对应位置的元素相减,之后平方求和即为欧氏距离。


方法二:单循环+部分向量化

单循环即只用到一次循环,部分向量化其实是利用了python中矩阵运算的性质。

	def cal_dist_one_loop(train, test):
		"""
		使用一层循环计算欧氏距离
		变量同cal_dist_two_loops
		"""
		num_train = train.shape(0)
		num_test = test.shape(0)
		
		for i in range(num_test):
			dist[i] = np.sqrt(np.sum(np.square(train - test[i]), axis=1))
	
	return dist

在上述代码中,train是一个5000*3072的矩阵,test[i]1*3072的矩阵(向量),两者大小不同进行相减,在python中会先将test[i]扩展至5000*3072,即一行复制5000份,之后对应位置元素相减,同样平方求和开方得到欧氏距离。
注意:这里一次循环就计算了单个测试样本分别与5000个训练样本之间的距离,axis=1在水平(一行)方向求和,列数化为1,结果为5000*1的向量,赋值给dist[i]


方法三:不使用循环+纯向量化计算

使用循环计算的效率远不如矩阵运算,因此应尽量使用矩阵运算代替循环。对于每一个3072单位大小的图像样本,欧氏距离就是每个像素值相减平方求和再开方,我们将该数学式展开,这样反而有利于我们利用矩阵计算。

( x 1 − y 1 ) 2 + ( x 2 − y 2 ) 2 + . . . + ( x 3072 − y 3072 ) 2 \sqrt{(x_1-y_1)^2+(x_2-y_2)^2+...+(x_{3072}-y_{3072})^2} (x1y1)2+(x2y2)2+...+(x3072y3072)2
x 1 2 + x 2 2 + . . + y 1 2 + y 2 2 + . . . − 2 x 1 y 1 − 2 x 2 y 2 − . . . \sqrt{x_1^2+x_2^2+..+y_1^2+y_2^2+...-2x_1y_1-2x_2y_2-...} x12+x22+..+y12+y22+...2x1y12x2y2...

	def cal_dist_no_loop(train, test):
		"""
		不使用循环计算欧氏距离
		"""
		num_train = train.shape(0)
		num_test = test.shape(0)

		dist += np.sum(np.square(test),axis=1).reshape(num_test, 1)
		dist += np.sum(np.square(train), axis=1).reshape(1, num_train)
		dist -= 2 * np.dot(test, train.T)
		dist = np.sqrt(dist)
		
		return dist
  • np.sum(np.square(test),axis=1)对应测试样本的平方项求和,reshape(500, 1),此时dist大小为500*1,每一个元素都是单样本的3072个平方项和。
  • np.sum(np.square(train), axis=1)对应训练样本的平方项求和,reshape(1,5000),每个元素都是单样本的3072个平方项求和,与dist相加,同样利用python中矩阵相加,大小不一致先扩展,相加后dist大小为500*5000
  • 之后减去两倍交叉项,利用矩阵乘法得到交叉项乘积和,最后求平方根。

总结

利用矩阵的性质进行计算,能够大大提高计算的效率。而如何深入理解矩阵运算,就不得不提到线性代数的重要性了,同时矩阵在python中的运算也有其特点,加以了解并运用才能更好地达成我们的目的。
【三种计算样本欧氏距离的方法——样本数据表示为矩阵】文章来源地址https://www.toymoban.com/news/detail-407517.html

到了这里,关于【三种计算样本欧氏距离的方法——样本数据表示为矩阵】的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 通过一个实际例子说明Django中的数据库操作方法法ForeignKey()的用法【数据表“一对多”关系】

    当使用Django进行数据库操作时,ForeignKey(外键)是一种非常有用的字段类型。它允许在数据库表之间创建关联关系,类似于其他数据库系统中的外键概念。通过ForeignKey字段,我们可以建立一个模型与另一个模型的一对多关系。 以下是一个实际例子,使用ForeignKey字段在Djang

    2024年02月12日
    浏览(43)
  • 通过一个实际例子说明Django中的数据库操作方法OneToOneField()的用法【数据表“一对一”关系】

    当我们在Django中定义一个模型时,可以使用 OneToOneField 来建立一个一对一的关系。这种关系表示两个模型之间的一种特殊关联,其中一个模型的实例只能与另一个模型的实例关联。 让我们以一个简单的示例来说明 OneToOneField 的用法。假设我们正在构建一个简单的博客应用,其

    2024年02月13日
    浏览(45)
  • PHP自己的框架PDO数据表前缀、alias、model、table、join方法实现(完善篇九--结束)

    一、实现功能,数据表前缀、alias、model、table、join方法实现    二、表前缀实现 1、config.php增加表前缀  2、增加表前缀方法function.php 3、PDO数据表增加表前缀ModelBase.php 三、alias数据表别名和join实现实现ModelBase.php 四、控制器实现,数据表前缀、alias、model、table、join方法查询

    2024年02月10日
    浏览(33)
  • 数据库实验2 创建数据表修改数据表和删除数据表

    实验2 创建数据表修改数据表和删除数据表 实验类型: ●验证性实验  ○综合性实验  ○设计性实验 实验目的:      (1)了解数据表的结构特点。      (2)掌握表中列定义时所用到的各种数据类型。      (3)学会使用企业管理器(即MSSMS-----Microsoft SQL Server Manag

    2024年02月07日
    浏览(54)
  • oracle数据表转换为mysql数据表

    oracle数据表转换为mysql数据表,或者反过来,我们可以借助navica的工具 1.打开navicat的工具-数据传输 2.选择源数据库以及目标数据库 目标可以选择数据库也可以选择文件,目标数据库需要提前建好表,这里是选择文件,注意选择一个文件,sql格式即为目标数据库类型,这里不

    2024年02月16日
    浏览(48)
  • MySql基础教程(三):创建数据表、数据增删改查、删除数据表

    创建MySQL数据表需要以下信息: 表名 表字段名 定义每个表字段 1.1 语法 下面是创建MySQL数据表的SQL通用语法: 以下例子在 nobug 数据库中创建数据表 nobug_user : 实例解析: 如果你不想字段为 NULL 可以设置字段的属性为 NOT NULL, 在操作数据库时如果输入该字段的数据为NULL ,

    2024年02月11日
    浏览(45)
  • OpenCV学堂 | CV开发者必须懂的9种距离度量方法,内含欧氏距离、切比雪夫距离等(建议收藏)

    本文来源公众号“ OpenCV学堂 ”,仅用于学术分享,侵权删,干货满满。 原文链接:CV开发者必须懂的9种距离度量方法,内含欧氏距离、切比雪夫距离等 在数据挖掘中,我们经常需要计算样本之间的相似度,通常的做法是计算样本之间的距离。在本文中,数据科学家 Maarten

    2024年02月20日
    浏览(33)
  • 实现一个MYSQL工具类,包含判断创建数据表是否存在,创建数据表

    可以使用Python的MySQLdb模块来实现一个MYSQL工具类。下面是一个简单的实现示例: 使用示例: 在上面的示例中,我们首先创建了一个MySQLTool类,并在初始化方法中传入了数据库的连接信息。然后使用connect方法连接到数据库。 table_exists方法用于判断给定的数据表是否存在,它执

    2024年01月15日
    浏览(43)
  • 【MySQL】MySQL 数据类型,数值、日期和时间、字符串类型,创建数据表,删除数据表

    作者简介: 辭七七,目前大一,正在学习C/C++,Java,Python等 作者主页: 七七的个人主页 文章收录专栏: 七七的闲谈 欢迎大家点赞 👍 收藏 ⭐ 加关注哦!💖💖 MySQL 中定义数据字段的类型对你数据库的优化是非常重要的。 MySQL 支持多种类型,大致可以分为三类:数值、日

    2024年02月15日
    浏览(53)
  • excel vba 将多张数据表的内容合并到一张数据表

    功能描述:  一个Excel文件有很多个 样式相同 的数据表, 需要将多张数据表的内容合并到一张数据表里。 vba实现代码如下:  文件链接:数据表合并.bas 下载后直接在excel 查看代码处导入文件即可。

    2024年02月11日
    浏览(32)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包