-
《并行算法设计与性能优化》——简单理解
2020-04-06 20:00:25对未来的憧憬,都是假象;前期的技术累计,也不一定用的上。现在年纪大了,没有年轻的时候,有那么多的试错机会,评估所有的成分。 当然,这个开篇,其实就是打算写一个系列出来,重点还是刘工的并行计算加速,也是...前言,下周开始将会开启新一段旅程,并行计算的领域。对未来的憧憬,都是假象;前期的技术累计,也不一定用的上。
当然,其实就是打算写一个系列出来,学习的内容还是刘工的并行计算加速,也是浅尝辄止,希望从宏观的角度去了解并行计算的领域。
1,为什么存在并行计算的概念?运算单元当然是越快越好,无论是CPU,GPU。并行计算的热起来,也差不多以下三个原因。1)CPU加速差不多到头了,接下去继续加速,成本和难度也会增加;2)多核技术普及;3)ANN应该也有点功劳。
2,什么是并行计算。我的理解,以前是一个人搬砖,现在是多个人一起搬砖。并行计算的目标是什么。并行或者向量化技术的首要任务是尽可能发挥硬件提供的全部算力,以减少延迟(更快地完成计算任务)或者提高吞吐量(在相同的时间内完成跟多的任务)。说白了,就是尽可能减少模块等待,谁也别闲着。
3,如何选择合适的算法。标准就是复杂度计算,常用的方法就是时间负责度,空间复杂度和实现复杂度。实现复杂度有计算复杂度,仿存负责度,指令复杂度。4,分析模块之间的相互关系计算机内部组成差不多就是类似上述描述的。其实就是多个多级别的流水线在数据搬运和数据计算的事情。现在就是遇到很核心的问题,哪些模块必须串行,哪些模块并行之类的问题。作者定义为依赖性分析,分为指令依赖和循环依赖,我到时觉得可以分为指令先后顺序依赖,和数据前后顺序的依赖。

5,如何理解并行计算以及加速。从我目前的认知来说,可以从两个角度,一个是从指令集和数据调度方面来理解,一个是从算法和应用逻辑角度。6,指令集角度。Enmmm.这个问题,先建模。无论是并行计算还是串行计算,都是存储和运算单元之间相爱相杀。CPU负责的指令搬运,指令解析,指令执行,结果回写。硬件单元就是内存,运算逻辑单元。在冯诺依曼架构里面,L1,L2,内存这些都是存储单元,为了CPU的指令快速获取数据设计的。并行计算也是如此,系统内部存在指令集的流水线,数据搬运的问题。1)运算单元入手,把指令流水线拉长,把一个模块切分多个,这样一个小块在干活的时候,其他小模块也不用闲着。指令多发射,说白了,就是不停的下发任务,让硬件单元不闲着。2)减少指令等待。乱序执行,分支预测。3)缓存技术,文中主要还是阐述了CPU的缓存技术。估计不同的架构不一样吧4)SIMD
6,从算法层面讲优化,从算法层面对应用程序抽象,数据流经过控制流之后,输出结果。划分策略:主要还是数据划分或者是任务划分两类,原则是数据流和任务不相关,减少数据流的内部通信。通信,因为通信是并行算法引入的额外开销消耗 ,如果能够减少这种消耗就能提高并行效率。各种方法各有千秋,具体可以看我之前写的关于锁的内容。结果归并 ,任务切分之后,最后执行的结果归一化,这个部分是额外的开销。应用场景实际应用中,我们需要考虑单核 多核,GPU等各个因素。
-
深入理解并行编程-分割和同步设计(三)
2017-05-22 15:13:33设计准则 上面的章节中给出了三个并行编程的目标:性能、生产率和通用性。...这些准则可以被认为是设计中的阻力,对这些阻力进行恰当权衡,这就称为“设计模式”[Ale79],[GHJV95]。 基于三个并行编程目...设计准则
上面的章节中给出了三个并行编程的目标:性能、生产率和通用性。但是还需要更详细的设计准则来真正的指导真实世界中的设计,这就是本节将解决的任务。在真实世界中,这些准则经常在某种程度上冲突,这需要设计者小心的权衡得失。
这些准则可以被认为是设计中的阻力,对这些阻力进行恰当权衡,这就称为“设计模式”[Ale79],[GHJV95]。
基于三个并行编程目标的设计准则是加速、竞争、开销、读写比率和复杂性。
加速:性能增加是花费如此多时间和精力进行并行化的主要原因。加速的定义是运行程序的顺序执行版本所需要的时间,比上执行并行版本所需时间的比例。
竞争:如果对于一个并行程序来说,增加更多的CPU并不能让程序忙起来,那么多出来的CPU是因为竞争的关系而无法有效工作。可能是锁竞争、内存竞争或者其他什么性能杀手的原因。
工作-同步比率:单处理器、单线程、不可抢占、不可中断版本的并行程序完全不需要任何同步原语。因此,任何消耗 在这些原语上(通信中的cache miss、消息延迟、加解锁原语、原子指令和内存屏障等)的时间都是对程序意图完成的工作没有直接帮助的开销。重要的衡量准则是同步开销与临界区中代码的 开销之间的关系,更大的临界区能容忍更大的同步开销。工作-同步开销比率与同步效率的概念有关。
读-写比率:极少更新的数据结构更多是复制而不是分割,并且用非对称的同步原语来保护,以提高写者同步开销的代价来降低读者的同步开销。对频繁更新的数据结构的优化也是可以的,详见第4章的讨论。
复杂性:并行程序比相同的顺序执行程序复杂,这是因为并行程序要比顺序执行程序维护更多状态,虽然这些状态在某些情况下(有规律并且结构化的)理解起来很容易。并行程序员必须考虑同步原语、消息传递、锁的设计、临界区识别以及死锁等诸多问题。
更大的复杂性通常转换成了更高的开发和维护代价。因此,代码预算可以有效限制对现有程序修改的数目和类型,因为原有程序在一定程度的加速只值这么多 的时间和精力。进一步说,还有可能对顺序执行程序进行一定程度的优化,这比并行化更廉价、更有效。并行化只是众多优化中的一种,并且只是一种主要应用于 CPU是瓶颈的优化。
这些准则合在一起,让程序达到了最大程度的加速。前三个准则相互交织在一起,所以本节剩下的部分将分析这三个准则的交互关系。
请注意,这些准则也是需求说明的一部份。必须,加速既是愿望(“越快越好”),又是工作负荷的绝对需求,或者说是“运行环境”(“系统必须至少支持每秒1百万次的web点击”)。
理解这些设计准则之间的关系,对于权衡并行程序的各个设计目标十分有用。
1. 程序在临界区上所花的时间越少,潜在的加速就越大。这是Amdahl定律的结果,这也是因为在一个时刻只能只有一个CPU进入临界区的原因。
2. 程序在某个互斥的临界区上所耗费的时间必须大大小于CPU数的倒数,因为这样增加CPU数目才能达到事实上的加速。比如在10个CPU上运行的程序只能在关键的临界区上花费小于1/10的时间,这样扩展性才好。
3. 竞争效应所浪费的多余CPU和/或者本来该是加速的墙上时间,应该少于可用CPU的数目。CPU数和实际的加速之间的差距越大,CPU使用的效率越低。同样,需要的效率越高,可以做到的加速就越小。
4. 如果可用的同步原语相较它们保护的临界区来说开销太大,那么加速程序运行的最佳办法是减少调用这些原语的次数(比如分批进入临界区、数据所有权、RCU或者使用粒度更粗的设计——比如代码锁)。
5. 如果临界区相较守护这块临界区的原语来说开销太大,那么加速程序运行的最佳办法是增加程序的并行化程度,比如使用读写锁、数据锁、RCU或者数据所有权。
6. 如果临界区相较守护这块临界区的原语来说开销太大,并且被守护的数据结构读多于写,那么加速程序运行的最佳办法是增加程序的并行化程度,比如读写锁或者RCU。
7. 各种增加SMP性能的改动,比如减少锁竞争程度,能改善响应时间。
文章转自 并发编程网-ifeve.com
-
【计算机组成原理】Verilog语言编写32位并行加法器的理解
2020-12-19 14:21:18考虑到verilog语言和硬件设计的关联性,我们需要从结构上完成对并行加法器的理解。 32位加法器注重逻辑结构的顺序,本文主要简单介绍了加法器的逻辑顺序并附上代码说明,较为简单。 加法器结构 首先,并行加法器的...【计算机组成原理】 Verilog语言编写32位并行加法器的理解
近日,为了完成本学期的计算机组成原理课程大作业的要求,我开始学习利用verilog语言编写的一套32位并行加法器以完成在整个项目中提高运算速度的基本要求。考虑到verilog语言和硬件设计的关联性,我们需要从结构上完成对并行加法器的理解。
32位加法器注重逻辑结构的顺序,本文主要简单介绍了加法器的逻辑顺序并附上代码说明,较为简单。加法器结构
首先,并行加法器的特点基本决定了其组成结构,每一位均由对应的一位全加器确定输出结果,且每一位的对应进位输入将由超前进位加法器(CLA)在本位的运算开始前计算得到。
CLA基本功能:输入各位级的值,在全加器计算之前先行计算出各位级对应的进位输入,便于全加器计算并得到输出的值。整个代码的流程框架为:
基础-1位全加器模块add;4位CLA模块cla
进阶1-使用1位全加器和4位CLA构成4位全加器
进阶2-使用4位CLA模块构成16位CLA模块
应用-使用16位CLA模块构成32位并行加法器代码展示与理解
下文附上整理为逻辑顺序架构的32位超前进位加法器的整体代码,语句的基本注释已经附在代码块中。
//基础-设置一位全加器模块 module add(X,Y,Cin,F,Cout); input X,Y,Cin; output F,Cout; assign F = X ^ Y ^ Cin; assign Cout = (X ^ Y) & Cin | X & Y; endmodule //一位全加器输入x,y,Cin;输出F,Cout; //基础-设置4位超前进位加法器CLA module CLA(c0,c1,c2,c3,c4,p1,p2,p3,p4,g1,g2,g3,g4); input c0,g1,g2,g3,g4,p1,p2,p3,p4; output c1,c2,c3,c4; //直接采取超前进位方式,完成相应的进位的计算 assign c1 = g1 ^ (p1 & c0), c2 = g2 ^ (p2 & g1) ^ (p2 & p1 & c0), c3 = g3 ^ (p3 & g2) ^ (p3 & p2 & g1) ^ (p3 & p2 & p1 & c0), c4 = g4 ^ (p4 & g3) ^ (p4 & p3 & g2) ^ (p4 & p3 & p2 & g1) ^(p4 & p3 & p2 & p1 & c0); endmodule //4位CLA输入本级的基本参数,输出对应的各位级上的进位输入值 //进阶1-在一位全加器基础上设置四位并行进位加法器 module add_4(x,y,c0,c4,F,Gm,Pm); //定义4位加法器模块 input [4:1] x; // 设置4位二进制输入x,y input [4:1] y; input c0; //设置二进制输入进位c0 output c4,Gm,Pm; //设置二进制输出进位c4 output [4:1] F; //设置二进制输出4位数F wire p1,p2,p3,p4,g1,g2,g3,g4; //设置wire类型线变量用于过程中计算 wire c1,c2,c3; //分四级完成单位上的一位全加器输出 add add1( .X(x[1]), .Y(y[1]), .Cin(c0), .F(F[1]), .Cout() ); add add2( .X(x[2]), .Y(y[2]), .Cin(c1), .F(F[2]), .Cout() ); add add3( .X(x[3]), .Y(y[3]), .Cin(c2), .F(F[3]), .Cout() ); add add4( .X(x[4]), .Y(y[4]), .Cin(c3), .F(F[4]), .Cout() ); CLA CLA( .c0(c0), .c1(c1), .c2(c2), .c3(c3), .c4(c4), .p1(p1), .p2(p2), .p3(p3), .p4(p4), .g1(g1), .g2(g2), .g3(g3), .g4(g4) ); assign p1 = x[1] ^ y[1], p2 = x[2] ^ y[2], p3 = x[3] ^ y[3], p4 = x[4] ^ y[4]; assign g1 = x[1] & y[1], g2 = x[2] & y[2], g3 = x[3] & y[3], g4 = x[4] & y[4]; assign Pm = p1 & p2 & p3 & p4, //Pm和Gm分别为进位传递输出和进位产生输出 Gm = g4 ^ (p4 & g3) ^ (p4 & p3 & g2) ^ (p4 & p3 & p2 & g1); endmodule //进阶2-在4位CLA的基础上设置16位CLA模块 module CLA_16(A,B,c0,S,px,gx); input [16:1] A; input [16:1] B; input c0; output gx,px; output [16:1] S; wire c4,c8,c12; wire Pm1,Gm1,Pm2,Gm2,Pm3,Gm3,Pm4,Gm4; //同理分四级完成对应位数上的累加和超前进位计算 add_4 add1( .x(A[4:1]), .y(B[4:1]), .c0(c0), .c4(), .F(S[4:1]), .Gm(Gm1), .Pm(Pm1) ); add_4 add2( .x(A[8:5]), .y(B[8:5]), .c0(c4), .c4(), .F(S[8:5]), .Gm(Gm2), .Pm(Pm2) ); add_4 add3( .x(A[12:9]), .y(B[12:9]), .c0(c8), .c4(), .F(S[12:9]), .Gm(Gm3), .Pm(Pm3) ); add_4 add4( .x(A[16:13]), .y(B[16:13]), .c0(c12), .c4(), .F(S[16:13]), .Gm(Gm4), .Pm(Pm4) ); assign c4 = Gm1 ^ (Pm1 & c0),//计算各个分级位进位输出取值 c8 = Gm2 ^ (Pm2 & Gm1) ^ (Pm2 & Pm1 & c0), c12 = Gm3 ^ (Pm3 & Gm2) ^ (Pm3 & Pm2 & Gm1) ^ (Pm3 & Pm2 & Pm1 & c0); assign px = Pm1 & Pm2 & Pm3 & Pm4,//Pm和Gm分别为16进位传递输出和进位产生输出 gx = Gm4 ^ (Pm4 & Gm3) ^ (Pm4 & Pm3 & Gm2) ^ (Pm4 & Pm3 & Pm2 & Gm1); endmodule //进阶3-由16位CLA直接设置32位CLA module add32(A,B,S,C32); input [32:1] A; input [32:1] B; output [33:1] S; output C32; wire px1,gx1,px2,gx2; //设置中间操作变量 wire c16; //将32位数分为两个16位操作数带入16位CLA模块完成并行计算过程 CLA_16 CLA1( .A(A[16:1]), .B(B[16:1]), .c0(0), .S(S[16:1]), .px(px1), .gx(gx1) ); CLA_16 CLA2( .A(A[32:17]), .B(B[32:17]), .c0(c16), .S(S[32:17]), .px(px2), .gx(gx2) ); assign c16 = gx1 ^ (px1 && 0), //默认AB相加时c0 = 0 C32 = gx2 ^ (px2 && c16); //确定32位输出进位为c32 S[33]=C32 endmodule //32位并行加法器输入为32位二进制数A,B;最终的输出为33位二进制数S(将整体进位整合到二进制数当中成为第33位);
-
并行粒子群优化算法的设计与实现
2018-08-23 09:53:03粒子群算法的并行实现算法,有利于加深对粒子群算法的理解 -
ASIC设计中一种通用型并行设计方法
2015-04-26 23:20:48ASIC设计中一种通用型并行设计方法: 1)流水网的概念提出 IC设计中的控制有串行和并行两种思想。状态机方法反应了串行控制思想,有软件的思路,比较好理解,新手比较喜欢用。流水线方法是并行处理的思想,...我是个“低调”的人,总不喜欢表达出来,对异性如此,对工作也是如此。在翔哥的鼓励下,决定把自己工作的一些经验和思考写下来,和同道们一起分享。
ASIC设计中一种通用型并行设计方法:
1)流水网的概念提出
IC设计中的控制有串行和并行两种思想。状态机方法反应了串行控制思想,有软件的思路,比较好理解,新手比较喜欢用。流水线方法是并行处理的思想,比较抽象,因为其效率高,老手喜欢用。从“流水线“的名字就容易知道,它只是一维的一条线,一个设计中可以有很多条。小设计中可能很容易设计,但对于大设计,流水线会很多条,条与条之间还有交叉,给同步带来很大的麻烦。显然还用流水线的思想去考虑并行的硬件设计显然就力不从心了。因而我们提出二维的流水网的概念,以完善并行设计思想。
2)流水级的概念提出及实现
一条流水线就像一个产品代理线。例如我是一件产品中间的一级代理,我有我的上级代理,我也有我的下级代理。对于很大的一个代理系统中,我只需要和我的上级和下级打交道就可以了,而不会跨级(例如我的上上级或者下下级)。只有我仓库有货,我就可以往下出货,出货成功的条件是刚好下级也要货。一方面只要仓库没有满,我就可以向上级要货,另一方面,即使我的仓库满了,但现在刚好会出货,我也可以向上级要货,入货成功的条件是刚好上级也有货。入货和出货同时进行,正是并行系统的体现。这是典型的互联网分布式设计思想。因而我们可以提出流水级的概念。在流水级中,我们用upen表示上级可以出货,uprdy本级可以入货,dnen表示本级可以出货,dnrdy表示下级可以入货。本级入货成功的条件是上级可以出货并且本级可以入货(upen&uprdy),本级出货成功的条件是本级可以出货,下级可以入货(dnen&dnrdy)。
3)流水节点的概念的提出及实现
一条流水线里面的流水级的上下级都只有一个,但在两端的流水级则可能有多个在其他流水线上的上下级。流水节点实现他们之间的同步,从而形成流水网络。需要同步的每个流水级都有一组输入和输出信号(可能是upen和uprdy的一组信号,也可以dnen和dnrdy的一组信号),本组输出信号就是除本组输入信号外的所有输入信号求与。
4)流水级,流水线,流水节点流水网的关系
流水级是一个点,多个流水级首尾相连可以形成流水线,多条流水线通过流水节点同步形成流水网。流水网可以实现任何的并行任务。
-
实战matlab之并行程序设计
2019-01-06 22:54:45第一个分太高了要50,过分,通过阅读和学习,读者可以掌握基于多种平台(多核、多处理器、集群和GPU等),利用多项技术(Matlab并行计算工具箱、多线程MEX文件、OpenMP和GPU等),学习理解Matlab并行程序设计的原理、... -
《实战Matlab之并行程序设计》
2016-12-10 15:20:14通过阅读和学习本书的内容,读者可以掌握基于多种平台(多核、多处理器、集群和GPU 等),利用多项技术(Matlab 并行计算工具箱、多线程MEX 文件、OpenMP 和GPU 等),学习理解Matlab 并行程序设计的原理、方法和技巧。... -
基于OpenMP矩阵相乘并行算法的设计
2014-05-07 15:39:41通过一个实例去理解OpenMP,看完后,就能完成初步OpenMP编程!十分适合入门!通过实例再回头学习原理,更清晰!希望对大家有帮助!谢谢! -
实战Matlab之并行程序设计_刘维
2016-06-19 09:56:08《实战Matlab之并行程序设计》通过阅读和学习,读者可以掌握基于多种平台(多核、多处理器、集群和GPU等),利用多项技术(Matlab并行计算工具箱、多线程MEX文件、OpenMP和GPU等),学习理解Matlab并行程序设计的原理、... -
翻新并行程序设计的认知整理版(state of the art parallel)
2019-03-17 21:12:00近几年,业内对并行和并发积累了丰富的经验。有了较深刻的理解。但之前积累的大量教材,在当今的软硬件体系下。反而都成了负面教材。所以,有必要加强宣传,翻新大家的认知。 首先。天地倒悬,结论先行:当你须要... -
论文研究 - 并行计算环境对CFD仿真解决方案一致性的影响-以IC引擎为重点
2020-06-01 16:45:39需要仔细研究和理解并行环境对仿真结果的影响。 在本文中,研究了并行CFD仿真的解决方案不一致问题。 首先,回顾了并行计算中解决方案不一致的概念,然后是针对IC引擎应用的系统CFD仿真。 使用商用CFD代码CONVERGE... -
设计系列-No1:将串行的功能拆分为并行的一个实践案例
2018-07-15 19:29:46为什么一开始就没想到呢?我们设计程序逻辑时候,往往会按照顺序...往往由于进度时间压迫我们没有做深入的理解,从思考层次来说仅仅是达到解决问题的水平,并没有进一步做优化。如果你坚持程序是一件艺术品,不是一... -
并行计算课程设计(代码+执行文件+文档)
2016-01-11 16:35:33这次的大作业虽然是对以前实验的整合,但它加深了我对并行计算的印象,也使我对并行计算知识的理解更加深刻,也使我认识到了自己很多不足之处。学习并行计算的历程不会因为完成本次大作业而停止,我们是为了用知识... -
对shell的理解
2019-01-30 18:24:181. 什么是shell: ... 它通过建立文件的形式并行的运行多个程序,帮助用户完成很多工作; Shell即是一种命令语言,也是一种程序设计语言。 作为命令语言的时候,shell的工作形式是交互式的... -
并行计算课程设计(报告+代码+可执行文件)
2016-01-11 16:31:59这次的大作业虽然是对以前实验的整合,但它加深了我对并行计算的印象,也使我对并行计算知识的理解更加深刻,也使我认识到了自己很多不足之处。学习并行计算的历程不会因为完成本次大作业而停止,我们是为了用知识... -
对Java中的Pipeline的理解
2020-08-06 20:54:03Pipe对处理阶段的抽象,负责对输入进行处理,并将输出作为下一个阶段的输入; process()用于接收前一个处理阶段的处理结果,作为该处理阶段的输入,init()初始化当前处理阶段对外提供的服务,shutdown()关闭当前... -
YMCache:YMCache是针对iOS和Mac OS X的轻量级对象缓存解决方案,专为高度并行访问方案设计-源码
2021-02-02 20:43:12YMCache是针对iOS和Mac OS X的轻量级对象缓存解决方案,专为高度并行访问方案而设计。 YMCache提供了一个熟悉的界面,可模拟NSMutableDictionary ,同时在内部利用Apple的技术在性能和一致性之间取得平衡。 ... -
对UART接口的理解
2012-10-11 16:33:53UART首先将接收到的并行数据转换成串行数据来传输。消息帧从一个低位起始位开始,后面是7个或8个数据位,一个可用的奇偶位和一个或几个高位停止位。接收器发现开始位时它就知道数据准备发送,并尝试与发 -
多核时代:并行程序设计探讨(9)——数据分解模式Data Decomposition
2009-09-20 20:34:00并行算法的设计者必须首先详细了解待解决的问题,除此之外,还必须识别如下几个关键因素: 1)计算强相关的部分:待解决问题中的哪部分需要进行大量运算; 2)关键数据结构:主要是对什么数据进行运算;如何进行... -
四 GPU 并行编程的存储系统架构
2014-08-11 21:07:00在用 CUDA 对 GPU 进行并行编程的过程中,除了需要对线程架构要有深刻的认识外,也需要对存储系统架构有深入的了解。 这两个部分是 GPU 编程中最为基础,也是最为重要的部分,需要花时间去理解吸收,加深内功。... -
谈谈对线程与进程的理解
2016-03-19 16:14:00概念: 线程 线程(threading)是操作系统能够进行运算调度的最小单位。它被包含在进程之中,是进程中的实际运作单位。一条线程指的是进程中一个单一顺序的控制流,一个...在早期面向进程设计的计算机结构中,进... -
多核平台的并行开发
2006-08-01 11:46:00计算机的核心任务就是执行各种应用的计算,双核作为一种突破主频限制、在功耗不变的情况下,实现性能提高的技术,简单理解,就是将两个计算内核集成在一个处理器之中,而多核的出现成为解决计算效率和应用对资源... -
第四篇:GPU 并行编程的存储系统架构
2017-01-18 16:21:00在用 CUDA 对 GPU 进行并行编程的过程中,除了需要对线程架构要有深刻的认识外,也需要对存储系统架构有深入的了解。 这两个部分是 GPU 编程中最为基础,也是最为重要的部分,需要花时间去理解吸收,加深内功。 ... -
并行计算-mpi编程手册(完整版)
2014-04-08 18:01:30首先介绍了并行程序设计的基础提供给读者进行并行程序设计所需要的基本知识然 后介绍了MPI的基本功能从简单的例子入手告诉读者MPI程序设计的基本过程和框架 这一部分是具有C或/FORTRAN串行程序设计经验的人员很容易... -
并行计算机体系结构-硬件-软件方法.pdf
2019-07-23 18:24:06本书遵循了一系列对所有并行架构都至关重要的问题——通信延迟、通信带宽以及跨整个现代设计的协作工作的协调。 它描述了用于解决每个问题的硬件和软件中可用的一组技术,并探讨了各种技术如何交互。 案例研究...
-
零基础极简以太坊智能合约开发环境搭建并开发部署
-
MySQL 事务和锁
-
一天学完MySQL数据库
-
3-5 常量
-
【布道者】Linux极速入门
-
物联网基础篇:快速玩转MQTT
-
每日算法:用递归算法求n的阶乘
-
江西财经大学《会计学》3套期末考试试卷(含答案).pdf
-
Spring注解驱动开发第46讲——Spring容器创建源码解析(六)之初始化所有剩下的单实例bean(上)
-
东南大学计算机技术935专业考研经验分享
-
朱老师鸿蒙系列课程第1期-3.鸿蒙系统Harmonyos源码配置和管理
-
PAT甲级-排序类型-1028 List Sorting解题思路
-
python2102 3.2总结
-
江西财经大学《货币银行学》期末知识点重点整理.pdf
-
湖南大学马哲期末复习资料(精华版).pdf
-
江西财经大学《大学语文》期末复习知识点总结(含答案).pdf
-
2021年 系统架构设计师 系列课
-
江西财经大学《微机分I》各单项训练汇总(含答案).pdf
-
记录十字链表打印矩阵
-
江西财经大学《微机操作》历年期末考试试卷.pdf