matlab矩阵作分钟平均,性能折衷-什么时候MATLAB比C / C ++更好/更慢

我已经使用Matlab和C ++大约10年了。 对于为我的研究实现的每个数值算法,我总是从使用Matlab进行原型设计开始,然后将项目转换为C ++,以获得10倍至100倍的性能提升(我不是在开玩笑)。 当然,我正在将优化的C ++代码与完全矢量化的Matlab代码进行比较。 平均而言,改善幅度约为50倍。

两种编程语言背后都有许多细微的差别,以下是一些误解:

Matlab是一种脚本语言,但已编译C ++

Matlab使用JIT编译器将脚本转换为机器代码,通过使用Matlab提供的编译器,您最多可以将速度提高1.5到2倍。

Matlab代码也许可以完全矢量化,但是您必须在C ++中手动优化代码

完全矢量化的Matlab代码可以调用以C ++ / C / Assembly编写的库(例如Intel MKL)。 但是普通的C ++代码可以由现代编译器合理地向量化。

Matlab提供的工具箱和例程应进行很好的调整,并具有合理的性能

否。除了线性代数例程外,性能通常很差。

与矢量Matlab代码相比,您在C ++中可以获得10x〜100x性能的原因:

在Matlab中调用外部库(MKL)需要花费时间。

Matlab中的内存是动态分配和释放的。 例如,小矩阵乘法:

A = B*C + D*E + F*G

需要Matlab创建2个临时矩阵。 在C ++中,如果事先分配内存,则将创建NONE。 现在,假设您将该语句循环了1000次。 C ++ 11 Rvalue参考提供了C ++中的另一种解决方案。 这是C ++的最大改进之一,现在C ++代码可以和普通C代码一样快。

如果要进行并行处理,则Matlab模型是多进程的,而C ++方式是多线程的。 如果您有许多需要并行化的小任务,C ++可以提供多达许多线程的线性增益,但是在Matlab中可能会有负性能增益。

C ++中的矢量化涉及使用内部函数/汇编,有时SIMD矢量化仅在C ++中才可能。

在C ++中,有经验的程序员可以完全避免L2高速缓存未命中甚至L1高速缓存未命中,从而使CPU达到其理论吞吐量极限。 仅由于这个原因,Matlab的性能就会比C ++落后10倍。

在C ++中,有时可以将计算密集型指令按其延迟(在汇编或内部函数中仔细编码)和相关性(大多数时间由编译器或CPU硬件自动完成)进行分组,从而可以将理论IPC(每个时钟周期的指令) 到达并且CPU管道已满。

但是,与Matlab相比,C ++的开发时间也是原来的10倍!

为什么要使用Matlab而不是C ++的原因:

数据可视化。 我认为如果没有C ++,我的职业生涯就可以继续,但是如果没有Matlab,我将无法生存,因为它会产生漂亮的情节!

低效率,但数学上强大的内置例程和工具箱。 首先获得正确答案,然后再谈效率。 人们可以在C ++中犯一些细微的错误(例如,将double隐式转换为int)并获得正确的结果。

表达您的想法并向同事展示您的代码。 与C ++相比,Matlab代码更易于阅读,而且更短,并且无需编译器即可正确执行Matlab代码。 我只是拒绝阅读别人的C ++代码。 我什至不使用C ++ GNU科学库,因为不能保证代码质量。 对于研究人员/工程师来说,将C ++库用作黑匣子并获得认可的准确性是危险的。 即使对于商用C / C ++库,我也记得英特尔编译器去年在sin()函数中出现符号错误,并且MKL中也出现了数字精度问题。

最后但是同样重要的:

因为一旦Matlab代码向量化,程序员就没有太多要优化的东西了,与C ++代码相比,Matlab代码的性能对代码质量的敏感度要低得多。 因此,最好在Matlab中优化计算算法,而略微更好的算法通常在Matlab中具有略微更好的性能。 另一方面,C ++中的算法测试要求体面的程序员以相同的方式或多或少地编写经过优化的算法,并确保编译器不会以不同的方式优化算法。

我最近在C ++和Matlab中的经验:

在过去的一年中,我制作了几种大型的Matlab数据分析工具,但由于Matlab的速度较慢而遭受了困扰。 但是我可以通过以下技术将Matlab程序速度提高10倍:

运行/分析Matlab脚本,在C / C ++中重新实现关键例程,并使用MEX进行编译。 关键例程在逻辑上很可能很简单,但在数字上却很繁琐。 这样可以将速度提高5倍。

通过注释所有不必要的安全检查和输出参数计算,简化Matlab工具箱附带的“ .m”文件。 请注意,修改后的代码无法与其余用户脚本一起分发。 这样可以将速度再提高2倍(在C / C ++和MEX之后)。

改进的代码在Matlab中约为98%,在C ++中约为2%。

我相信,如果整个工具都用C ++编码,则速度可以再提高2倍(总计20倍),这是计算例程速度的约100倍提高。 然后,硬盘驱动器I / O将主导程序运行时间。

给Mathworks工程师的问题:

当Matlab代码完全矢量化后,性能限制因素之一就是矩阵索引操作。 例如,需要对尺寸为5000x5000的矩阵A执行有限差分运算:

B = A(:,2:end)-A(:,1:end-1)

矩阵索引操作使Matlab代码比C ++代码慢许多倍。 可以提高矩阵索引性能吗?

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值