首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >为什么MATLAB在创建随机数方面比C++更快?

为什么MATLAB在创建随机数方面比C++更快?
EN

Stack Overflow用户
提问于 2015-07-29 06:31:59
回答 4查看 853关注 0票数 3

我在我的项目中使用MATLAB已经有一段时间了,我几乎从来没有在C++方面有过经验。

我需要速度,我听说C++比MATLAB更高效和更快。所以我试了一下:

我在MATLAB上使用rand(5000,5000)创建了一个随机数矩阵。

在C++中,我初始化了一个2D向量,创建了2个循环,每个循环5000次,每次循环。MATLAB的速度快了4-5倍,所以我想是因为matlab并行执行矢量化代码,然后我用parallel_for编写了parallel_for代码。以下是代码:

代码语言:javascript
运行
复制
#include "stdafx.h"
#include <iostream>
#include <vector>
#include <fstream>
#include <ppl.h>
using namespace std;
using namespace concurrency;
int main();
{
    int a = 5000, b = 5000, j, k;
    vector< vector<int> > vec(a, vector<imt>(b));
    parallel_for(int(0), a, [&](int i) {
        for (j = 0; j <b; j++)
        {
            vec[i][j] = rand();
        }
    });
}

所以上面的代码比MATLAB的rand(5000,5000)快25%,但是C++使用的CPU是100%,而MATLAB是使用30%的CPU。

因此,我强迫MATLAB使用rand(5000,5000)运行3个实例,并将所需的时间除以3,使MATLAB的运行速度是C++的两倍。

我想知道我错过了什么?我知道这是一个很小的例子,但我需要一个答案来确保将我的代码移植到C++。

现状:

当我编写没有C++的parallel_for代码时,在相同的CPU使用情况下,我的速度只有MATLAB的一半。然而,给出答案的人说,他们几乎是一样的。我不明白我错过了什么

下面是优化菜单的快照

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2018-09-07 16:22:04

在Matlab中调用rand(5000,5000)时,Matlab通过调用Intel库来执行命令,这是一个用C/C++编写的高度优化的库,包含大量手工编码的程序集。

MKL应该比任何简单的C++实现都快,但是Matlab调用外部库的开销很大。最终的结果是,对于较小规模的随机数生成(例如小于1K ),普通C/C++实现将更快,但对于较大的大小,Matlab将受益于超级优化的MKL。

票数 1
EN

Stack Overflow用户

发布于 2015-07-29 07:49:30

这也许是没有答案,但一小部分暗示。由于vectors的使用,这种比较可能有点不公平。

这是我写过的一个比较。这两个线程都占了四个可用线程中的一个线程的100%左右。在这两种情况下,我都创建了5000x5000随机数,并为计时做了100次

Matlab

代码语言:javascript
运行
复制
function stackoverflow

tic
for i=1:100
    A =rand(5000);
end
toc

运行时:~27.9秒

C++

代码语言:javascript
运行
复制
#include <iostream>
#include <stdlib.h>
#include <time.h>
#include <ctime>

using namespace std;


int main(){

    int N = 5000;
    double ** A = new double*[N];
    for (int i=0;i<N;i++)
        A[i] = new double[N];


    srand(time(NULL));

    clock_t start = clock();
    for (int k=0;k<100;k++){
        for (int i=0;i<N;i++){
            for (int j=0;j<N;j++){
                A[i][j] = rand();
            }
        }
    }

    cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;

}

运行时:~28.7秒

因此,这两个例子的运行速度几乎一样快。

票数 2
EN

Stack Overflow用户

发布于 2015-07-29 08:31:33

在查看了@sonystarmap的答案之后,我添加了几种类型的容器:double*vector<double>vector<vector<double> >。我还添加了“指针容器”是memset的测试,因为vector初始化了所有内存。

C++代码是用以下优化标志编译的:-O3 -march=native

结果:

经过的时间是28.457788秒。

C++:

T=23844.2ms

T=25161.5ms

T=25154ms

T=24197.3ms

T=24235.2ms

T=24166.1ms

我根本找不到你提到的大收益。

代码语言:javascript
运行
复制
#include <iostream>
#include <stdlib.h>
#include <time.h>
#include <ctime>
#include <vector>
#include <cstring>

using namespace std;


int main(){

    const int N = 5000;

    {
        vector<double> A(N*N);

        srand(0);

        clock_t start = clock();
        for (int k=0;k<100;k++){
            for (int i=0;i<N;i++){
                for (int j=0;j<N;j++){
                    A[i*N+j] = rand();
                }
            }
        }

        cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;
    }

    {
        vector<vector<double> > A(N);
        for (int i=0;i<N;i++)
            A[i] = vector<double>(N);

        srand(0);

        clock_t start = clock();
        for (int k=0;k<100;k++){
            for (int i=0;i<N;i++){
                for (int j=0;j<N;j++){
                    A[i][j] = rand();
                }
            }
        }

        cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;
    }

    {
        double ** A = new double*[N];
        for (int i=0;i<N;i++)
            A[i] = new double[N];

        srand(0);

        clock_t start = clock();
        for (int k=0;k<100;k++){
            for (int i=0;i<N;i++){
                for (int j=0;j<N;j++){
                    A[i][j] = rand();
                }
            }
        }

        cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;
    }

    {
        double ** A = new double*[N];
        for (int i=0;i<N;i++) {
            A[i] = new double[N];
            memset(A[i], 0, sizeof(double) * N);
        }

        srand(0);

        clock_t start = clock();
        for (int k=0;k<100;k++){
            for (int i=0;i<N;i++){
                for (int j=0;j<N;j++){
                    A[i][j] = rand();
                }
            }
        }

        cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;
    }

    {
        double * A = new double[N * N];

        srand(0);

        clock_t start = clock();
        for (int k=0;k<100;k++){
            for (int i=0;i<N;i++){
                for (int j=0;j<N;j++){
                    A[i*N + j] = rand();
                }
            }
        }

        cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;
    }

    {
        double * A = new double[N * N];
        memset(A, 0, sizeof(double) * N * N);

        srand(0);

        clock_t start = clock();
        for (int k=0;k<100;k++){
            for (int i=0;i<N;i++){
                for (int j=0;j<N;j++){
                    A[i*N + j] = rand();
                }
            }
        }

        cout << "T="<< (clock()-start)/(double)(CLOCKS_PER_SEC/1000)<< "ms " << endl;
    }
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/31692856

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档