优化我们的程序(数据篇):自空间复用

自空间复用

当遍历的元素恰好在一条cache线上时,称之为自空间复用,在前面我们已经知道了矩阵的秩就是数据的空间维度,也就是相对独立变量的个数。

当矩阵的秩小于循环嵌套深度时,此时一定是可以进行优化的。

例如:

for(i=0; i<100; i++){for(j=0; j<100; j++){for(k=0; k<100; k++){Z[i+j+k] = 0;}}
}

对于这个例子,矩阵的秩为:
( 1 1 1 ) \begin{pmatrix} 1&1&1 \end{pmatrix} (111)

观察程序我们也可以发现,只需要一个变量其实就可以完成遍历。

矩阵的秩

因此,我们再一次强调矩阵的秩的含义:它代表了数据遍历所需要的空间维度。数据本身就有维度,以数组为例,有一维数组、二维数组、三维数组等等,对于不同维度的数组,我们需要不同个数的独立变量才可以遍历全部元素,一维需要一个变量、二维需要两个、、以此类推。

我们假设每个独立变量只在不同的一层循环中出现,且变量作用维度不同,那么此时矩阵的秩刚好等于循环嵌套深度,也就是独立变量的个数。

发现自空间复用的技巧是不考虑矩阵的最后一行,对于假设情况,此时截断后的矩阵的秩小于循环嵌套深度,又因为数据的空间维度相对独立,因此截断的维度会线性改变数组的下标,也就是说,它迭代时,元素处于同一条cache线上,此时自空间复用是可行的。

看过了假设的例子,先明确一个结论:矩阵的秩不可能大于循环嵌套深度,而是等于或小于循环嵌套深度。

例如:数据是二维的,但是对于需要遍历的数据,它们的分布其实是线性的,所以矩阵的秩是一,最终会等于循环嵌套深度

for(i=0; i<50; i++){Z[i][i+1]=0;
}

原因很简单,矩阵的秩代表了数据遍历时的空间维度,循环嵌套深度是具体的迭代产生者,如果秩大于循环嵌套深度,那么就意味着有些维度是无法被迭代到的,这种程序不可能出现!

例如:j代表了另外一个维度的遍历,但是此时循环迭代程序必须更新,这种程序不可能出现!

for(i=0; i<10; i++){Z[i][j]=0;
}

不过矩阵的秩是可以小于循环嵌套深度的,

例如:

for(i=0; i<10;i++){for(j=0; j<10; j++){Z[i+j]=0;}
}

这个矩阵的秩为1,循环嵌套深度为2,但是j变量是多余的,本质上它遍历的元素还是在一条cache线上,也就是同一个维度。

也就是说,如果矩阵的秩一开始就小于循环嵌套深度,那么一定可以发生自空间复用。

发现自空间复用

发现自空间复用的技巧是不考虑矩阵的最后一行,从上面我们可以得出,正常情况下,矩阵的秩小于或等于循环嵌套的深度。

当矩阵的秩小于循环嵌套的深度时,截断后的矩阵仍然满足矩阵的秩小于循环嵌套深度的关系,此时一定可以发生自空间复用。

当矩阵的秩等于循环嵌套深度时,截断后的矩阵也满足矩阵的秩小于循环嵌套深度的关系,此时也一定可以发生自空间复用。

考虑数组访问如下:

Z[1][i][2*i+j]

删除最后一行,得到矩阵如下:
( 0 0 1 0 ) \begin{pmatrix} 0&0\\ 1&0 \end{pmatrix} (0100)
这个矩阵的秩为1,但是循环嵌套的深度为2,所以可以进行自空间复用。

我们观察最后一行下标,事实也确实如此,因为遍历时,j是线性增长的,2i不属于该循环,所以[2*i+j]也是线性增长的,也就是说,它的迭代是在同一条cache线上。

对程序设计的要求

不考虑矩阵的最后一行,其实就是在找出独立的、线性改变数组访问的迭代,其实这对于程序设计有一个要求,那就是所有的数组下标都要与循环嵌套一一对应。

再考虑数组访问如下:

Z[2*i+j][i][1]

此时截断后的矩阵的秩为2,循环嵌套深度也为2,此时该技巧就不成立了。

对应线性代数的意义

假设程序设计合理,程序的每一列都对应不同的迭代变量,为了确保存在空间复用,我们必须要确保被我们截断后的变量的基本向量[0,1]位于截断矩阵的零空间中。

例如:

对于Z[1][i][2*i+j],迭代变量j的零向量是[0,1],刚好位于截断后的矩阵的零空间中

这是因为当该向量在截断矩阵的零空间中时,我们可以把除了最内层下标之外的所有下标都固定下来,确保最后一层迭代是线性变换的,这样就可以确保它对数组元素的访问是处于同一条cache线。

缺陷

考虑如下访问:

Z[1][i][2*i+50*j]

我们同样使用上面的方法截断矩阵,结果确实满足矩阵秩的要求,那么我们可以把这些元素都保存在cache中吗?

在这种情况下,访问确实是线性的,但是却跨越了50个元素,除非该cache线能保存元素的个数远远超过50个,否则该自空间复用的收益非常低,甚至是无法被自空间复用。

总结

以上属于自空间复用内容,主要重点是访问元素与cache线的线性关系。前面两篇已经写完了自复用内容,接下来写写组复用内容。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/65569.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

攻防世界web新手第五题supersqli

这是题目&#xff0c;题目看起来像是sql注入的题&#xff0c;先试一下最常规的&#xff0c;输入1&#xff0c;回显正常 输入1‘&#xff0c;显示错误 尝试加上注释符号#或者–或者%23&#xff08;注释掉后面语句&#xff0c;使1后面的单引号与前面的单引号成功匹配就不会报错…

SQL SERVER日常运维巡检系列之-日志

前言 做好日常巡检是数据库管理和维护的重要步骤&#xff0c;而且需要对每次巡检日期、结果进行登记&#xff0c;同时可能需要出一份巡检报告。 本系列旨在解决一些常见的困扰&#xff1a; 不知道巡检哪些东西不知道怎么样便捷体检机器太多体检麻烦生成报告困难&#xff0c;无…

小程序基础 —— 08 文件和目录结构

文件和目录结构 一个完整的小程序项目由两部分组成&#xff1a;主体文件、页面文件&#xff1a; 主体文件&#xff1a;全局文件&#xff0c;能够作用于整个小程序&#xff0c;影响小程序的每个页面&#xff0c;主体文件必须放到项目的根目录下&#xff1b; 主体文件由三部分组…

Vue 中el-table-column 进行循环,页面没渲染成功

文章目录 前言效果图代码示例可能出现的问题及原因解决思路 前言 实现效果&#xff1a;el-table-column 进行循环&#xff0c;使之代码简化 遇到的问题&#xff1a; data进行默认赋值&#xff0c;操作列的删除都可以出来&#xff0c;其他表格里面的数据没出来 效果图 示例&am…

不使用docker push ,使用docker save 打包成tar文件,scp到服务器上,应对离线环境

如果你不想使用 docker push&#xff0c;而是希望将本地 Docker 镜像打包成 tar 文件&#xff0c;并通过 scp 将其传输到目标服务器上&#xff0c;你可以按照以下步骤操作&#xff1a; 1. 在本地打包 Docker 镜像为 tar 文件 首先&#xff0c;在本地构建并打包你的 Docker 镜…

HarmonyOS NEXT应用开发实战:一分钟写一个网络接口,JsonFormat插件推荐

在开发鸿蒙操作系统应用时&#xff0c;网络接口的实现往往是一个繁琐且重复的过程。为了提高开发效率&#xff0c;坚果派(nutpi.net)特别推出了一个非常实用的插件——JsonFormat。这款插件的主要功能是将JSON格式的数据直接转换为arkts的结构定义&#xff0c;让我们在编写接口…

vue3中使用el-tag结合element-plus使用方法

vue3中使用el-tag结合element-plus在行内使用el-button按钮&#xff0c;带背景色&#xff0c;效果&#xff1a; 代码&#xff1a; <el-table-column label"状态" align"center" prop"states"><template #default"scope">…

快速排序算法的 Java 实现与性能调优

目录 一、快速排序的基本原理 二、快速排序的 Java 实现 三、时间复杂度与空间复杂度 四、总结 引言 排序是计算机科学中的基础问题之一&#xff0c;无论是在数据库查询、数据分析&#xff0c;还是在日常编程中&#xff0c;排序算法的选择都对性能有着重要的影响。快速排序…

如何利用无线路由器实现水泵房远程监测管理

水泵站广泛部署应用在工农业用水、防洪、排涝和抗旱减灾等方面&#xff0c;如果水泵站发生异常&#xff0c;往往会对生产生活造成诸多损失&#xff0c;甚至引发安全事故。因此&#xff0c;建立一套高效、可靠的泵站远程监测管理系统至关重要。 方案背景 目前&#xff0c;我国大…

解锁健康步姿密码:无标记点动作捕捉系统助力医疗康复

在医疗康复领域&#xff0c;精准的步态分析对于患者进行正常行走能力恢复检测起着举足轻重的作用。AI 无标记点动作捕捉系统基于先进的深度学习视觉算法&#xff0c;实现了对人体的全方位动作捕捉&#xff0c;为医疗康复步态分析提供了全新的解决方案。 无标记点动作捕捉系统在…

vue封装弹窗元素拖动指令

项目开发过程中我们通常会遇到需要到一些弹窗鼠标可以随意拖动位置去放置&#xff0c;vue里面直接通过封装对应的指令即可&#xff0c;于是封装了一个出来&#xff0c;希望可以用到。 Vue.directive(draggable-dom, draggableDom); 组件节点添加对应指令就可以 v-draggable-…

将广播发送和接收端实现一遍,完成一个发送端发送信息,对应多个接收端接收信息实验。

1、将广播发送和接收端实现一遍&#xff0c;完成一个发送端发送信息&#xff0c;对应多个接收端接收信息实验。 接受端 #include<myhead.h> #define handel_err(res,val) if(val-1){perror(res);return-1;} int main(int argc, const char *argv[]) {int rfdsocket(AF_…

基本算法——聚类

目录 创建工程 加载数据 聚类算法 评估 完整代码 结论 相比于有监督的分类器&#xff0c;聚类的目标是从一组未打标签的数据中识别相似对象组。它可 以用于识别同类群体的代表性样本&#xff0c;找到有用与合适的分组&#xff1b;或者找到不寻常的样本&#xff0c;比如 异…

uniapp中的条件编译

在script中 // #ifdef APP-PLUS console.log("11"); // #endif// #ifdef MP-WEIXIN console.log("22"); // #endif 在template中 <!-- #ifdef APP-PLUS --><view>哈哈哈</view> <!-- #endif --><!-- #ifdef MP-WEIXIN -->…

day21-ubuntu入门

小趣味docker 1.安装docker&#xff0c;从阿里云的yum yum install docker -y 2.需要提前准备好docker镜像&#xff0c;确保可用 docker -v 3.导入该游戏镜像&#xff08;先用systemctl start docker&#xff09; docker load < game_v2.tar 4.一条命令&#xff0c;在…

vue3 学习与实战

1. Vue3简介 2020年9月18日&#xff0c;Vue.js发布版3.0版本&#xff0c;代号&#xff1a;One Piece&#xff08;n 经历了&#xff1a;4800次提交、40个RFC、600次PR、300贡献者 官方发版地址&#xff1a;Release v3.0.0 One Piece vuejs/core 截止2023年10月&#xff0c;最…

Three.js滚动画案例精选

今天为大家带来 3 个基于滚动动画的网站 Demo&#xff0c;它们不仅视觉效果惊艳&#xff0c;而且每个案例的源码都已开源在 GitHub&#xff0c;方便大家学习和借鉴&#xff01; 3D照片墙滚动 通过滚动操作实现 3D 网格效果以及动态过渡动画。这个案例使用了 GSAP 的 SplitTex…

地理数据库Telepg面试内容整理-描述你如何在GIS应用中使用空间数据进行分析并生成可视化结果

在 GIS(地理信息系统)应用中,使用空间数据进行分析并生成可视化结果是一项关键功能。空间数据的分析和可视化帮助用户理解地理现象、发现模式,并做出数据驱动的决策。以下是一个关于如何在 GIS 应用中使用空间数据进行分析并生成可视化结果的详细描述。 准备空间数据 在进行…

若依(spring-cloud)修改登陆密码加密算法

文章目录 前言一、解决办法二、解决过程1 为啥要改加密算法2 找不到校验代码 总结 前言 若依是一套快速集成各种中间件的配套 Java 后端框架&#xff0c;本文旨在描述修改其登陆的加密算法。文章的大前提是后端框架是若依哈&#xff0c;不是的话可以跳过了~&#xff01; 文章…

Flutter富文本实现学习

Flutter 代码如何实现一个带有富文本显示和交互的页面。 前置知识点学习 RealRichText RealRichText 和 ImageSpan 不是 Flutter 框架中内置的组件&#xff0c;而是自定义的组件或来自第三方库。这些组件的实现可以提供比标准 RichText 更丰富的功能&#xff0c;比如在富文本…