Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/r/70.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
为Rcpp';使用循环是否是一个理想的选择;C++;? 我想使用 RCPP::MultMexMatcs/Cuff>作为C++函数的参数类型,将通过它循环。我现在应该将Rcpp::numerimatrix的全部内容复制到一个C样式的数组中以获得良好的性能,还是在C++循环中多次使用Rcpp::numerimatrix的[]-操作符也很快?有没有比使用随机访问更快的方法来循环通过Rcpp::numerimatrix实例_C++_R_Rcpp - Fatal编程技术网

为Rcpp';使用循环是否是一个理想的选择;C++;? 我想使用 RCPP::MultMexMatcs/Cuff>作为C++函数的参数类型,将通过它循环。我现在应该将Rcpp::numerimatrix的全部内容复制到一个C样式的数组中以获得良好的性能,还是在C++循环中多次使用Rcpp::numerimatrix的[]-操作符也很快?有没有比使用随机访问更快的方法来循环通过Rcpp::numerimatrix实例

为Rcpp';使用循环是否是一个理想的选择;C++;? 我想使用 RCPP::MultMexMatcs/Cuff>作为C++函数的参数类型,将通过它循环。我现在应该将Rcpp::numerimatrix的全部内容复制到一个C样式的数组中以获得良好的性能,还是在C++循环中多次使用Rcpp::numerimatrix的[]-操作符也很快?有没有比使用随机访问更快的方法来循环通过Rcpp::numerimatrix实例,c++,r,rcpp,C++,R,Rcpp,因为这是一个相当悠闲的日子,我无法很快找到这方面的基准(第4节待定,第6节待定)。。。还有我的好奇心。。。让我们试一试吧 首先,要访问numerimatrix的c样式数组,我们首先需要将numerimatrix转换为std::vector。从std::vector,我们可以提取由指针控制的c样式数组。在这种结构下,我们完全复制了数据。不过,我们可以调查所提出的问题,然后再进行一些调查 下面是一个功能的快速测试套件,重点放在四个不同的组件上: c型阵列 std::累加 循环一个std::vecto

因为这是一个相当悠闲的日子,我无法很快找到这方面的基准(第4节待定,第6节待定)。。。还有我的好奇心。。。让我们试一试吧

首先,要访问
numerimatrix
的c样式数组,我们首先需要将
numerimatrix
转换为
std::vector
。从
std::vector
,我们可以提取由指针控制的c样式数组。在这种结构下,我们完全复制了数据。不过,我们可以调查所提出的问题,然后再进行一些调查

下面是一个功能的快速测试套件,重点放在四个不同的组件上:

  • c型阵列
  • std::累加
  • 循环一个
    std::vector
  • 使用
    numerimatrix
  • 现在,我在纯c风格函数中进行了“欺骗”,因为我没有尝试通过
    sizeof()
    calculations从数组本身计算数组的大小。(这可能会导致一些问题,因为指针的大小是给定的…)

    让我们检查一下函数的测试套件

    #include <Rcpp.h>
    
    // [[Rcpp::export]]
    double c_for_access(const Rcpp::NumericMatrix& x){
    
      // Cast to std vector
      std::vector<double> v = Rcpp::as<std::vector<double> >(x);
    
      // Convert to c-style pointer
      double* pv = &v[0];
    
      // Sum using a pointer
      double sum = 0;
      for(unsigned int i = 0; i < v.size(); i++){
        sum += *(pv+i);  
      }
    
      return sum;
    }
    
    // [[Rcpp::export]]
    double stl_for_access(const Rcpp::NumericMatrix& x){
    
      // Cast to std vector
      std::vector<double> v = Rcpp::as<std::vector<double> >(x);
    
      // Summing Operation
      double sum = 0;
      for(unsigned int i = 0; i < v.size(); i++){
        sum +=  v[i];
      }
    
      return sum;
    }
    
    // [[Rcpp::export]]
    double stl_access(const Rcpp::NumericMatrix& x){
      // Cast to STL Vector
      std::vector<double> v = Rcpp::as<std::vector<double> >(x);
    
      // Use STL to return sum
      return std::accumulate(v.begin(), v.end(), 0.0); // Important to specify 0.0 instead of 0. 
    }
    
    
    // [[Rcpp::export]]
    double matrix_access(const Rcpp::NumericMatrix& x) {
      // Define matrix information and looping variables.
      unsigned int r = x.nrow(), c = x.ncol(), i, j;
    
      // Sum elements
      double sum = 0;
      for(i = 0; i < r; i++){
        for(j = 0; j < c; j++){
          sum += x(i,j);
        }
      }
    
      return sum;
    }
    
    接下来,我们计算并检查每个对象的总和,以确保它们都相等:

    # Calculate each object
    oracle = sum(x)     # Oracle is the correct answer given by R
    
    c.out = c_for_access(x)
    
    stl.loop = stl_for_access(x)
    
    stl.lib = stl_access(x)
    
    rcpp.pure = matrix_access(x)
    
    # Check all equal
    all.equal(oracle, c.out)
    
    all.equal(oracle, stl.loop)
    
    all.equal(oracle, stl.lib)
    
    all.equal(oracle, rcpp.pure)
    
    最后,我们在每个函数上运行一个微基准:

    # install.packages("microbenchmark")
    
    microbenchmark::microbenchmark(oracle = sum(x),
    
                   c.out = c_for_access(x),
    
                   stl.loop = stl_for_access(x),
    
                   stl.lib = stl_access(x),
    
                   rcpp.pure = matrix_access(x)
    )
    
    从microbenchmark,我们有:

    Unit: microseconds
          expr    min     lq     mean  median      uq    max neval
        oracle  8.105  8.705  9.11406  8.7060  9.0060 24.016   100
         c.out 30.319 31.220 31.75767 31.2210 31.5210 54.636   100
      stl.loop 30.320 30.921 32.56819 31.2210 31.5210 55.836   100
       stl.lib 30.319 30.920 31.64063 31.2205 31.6705 50.133   100
     rcpp.pure  9.907 10.807 10.95122 10.8070 11.1070 12.909   100
    
    因此,通过
    Rcpp
    的矩阵求和比R慢约2微秒,但比
    std::vector
    和c型数组设置快得多


    Q.E.D?

    因为这是一个相当悠闲的一天,我无法很快找到这方面的基准(第4节待定,第6节待定)。。。还有我的好奇心。。。让我们试一试吧

    首先,要访问
    numerimatrix
    的c样式数组,我们首先需要将
    numerimatrix
    转换为
    std::vector
    。从
    std::vector
    ,我们可以提取由指针控制的c样式数组。在这种结构下,我们完全复制了数据。不过,我们可以调查所提出的问题,然后再进行一些调查

    下面是一个功能的快速测试套件,重点放在四个不同的组件上:

  • c型阵列
  • std::累加
  • 循环一个
    std::vector
  • 使用
    numerimatrix
  • 现在,我在纯c风格函数中进行了“欺骗”,因为我没有尝试通过
    sizeof()
    calculations从数组本身计算数组的大小。(这可能会导致一些问题,因为指针的大小是给定的…)

    让我们检查一下函数的测试套件

    #include <Rcpp.h>
    
    // [[Rcpp::export]]
    double c_for_access(const Rcpp::NumericMatrix& x){
    
      // Cast to std vector
      std::vector<double> v = Rcpp::as<std::vector<double> >(x);
    
      // Convert to c-style pointer
      double* pv = &v[0];
    
      // Sum using a pointer
      double sum = 0;
      for(unsigned int i = 0; i < v.size(); i++){
        sum += *(pv+i);  
      }
    
      return sum;
    }
    
    // [[Rcpp::export]]
    double stl_for_access(const Rcpp::NumericMatrix& x){
    
      // Cast to std vector
      std::vector<double> v = Rcpp::as<std::vector<double> >(x);
    
      // Summing Operation
      double sum = 0;
      for(unsigned int i = 0; i < v.size(); i++){
        sum +=  v[i];
      }
    
      return sum;
    }
    
    // [[Rcpp::export]]
    double stl_access(const Rcpp::NumericMatrix& x){
      // Cast to STL Vector
      std::vector<double> v = Rcpp::as<std::vector<double> >(x);
    
      // Use STL to return sum
      return std::accumulate(v.begin(), v.end(), 0.0); // Important to specify 0.0 instead of 0. 
    }
    
    
    // [[Rcpp::export]]
    double matrix_access(const Rcpp::NumericMatrix& x) {
      // Define matrix information and looping variables.
      unsigned int r = x.nrow(), c = x.ncol(), i, j;
    
      // Sum elements
      double sum = 0;
      for(i = 0; i < r; i++){
        for(j = 0; j < c; j++){
          sum += x(i,j);
        }
      }
    
      return sum;
    }
    
    接下来,我们计算并检查每个对象的总和,以确保它们都相等:

    # Calculate each object
    oracle = sum(x)     # Oracle is the correct answer given by R
    
    c.out = c_for_access(x)
    
    stl.loop = stl_for_access(x)
    
    stl.lib = stl_access(x)
    
    rcpp.pure = matrix_access(x)
    
    # Check all equal
    all.equal(oracle, c.out)
    
    all.equal(oracle, stl.loop)
    
    all.equal(oracle, stl.lib)
    
    all.equal(oracle, rcpp.pure)
    
    最后,我们在每个函数上运行一个微基准:

    # install.packages("microbenchmark")
    
    microbenchmark::microbenchmark(oracle = sum(x),
    
                   c.out = c_for_access(x),
    
                   stl.loop = stl_for_access(x),
    
                   stl.lib = stl_access(x),
    
                   rcpp.pure = matrix_access(x)
    )
    
    从microbenchmark,我们有:

    Unit: microseconds
          expr    min     lq     mean  median      uq    max neval
        oracle  8.105  8.705  9.11406  8.7060  9.0060 24.016   100
         c.out 30.319 31.220 31.75767 31.2210 31.5210 54.636   100
      stl.loop 30.320 30.921 32.56819 31.2210 31.5210 55.836   100
       stl.lib 30.319 30.920 31.64063 31.2205 31.6705 50.133   100
     rcpp.pure  9.907 10.807 10.95122 10.8070 11.1070 12.909   100
    
    因此,通过
    Rcpp
    的矩阵求和比R慢约2微秒,但比
    std::vector
    和c型数组设置快得多


    Q.E.D?

    尝试两者并进行比较?所有这些都在Rcpp文档和软件包中讨论过。我们甚至还有基准测试。@Dirkedelbuettel谢谢!我今天从Rcpp开始。尝试两者并进行比较?Rcpp文档和软件包中都有讨论。我们甚至还有基准测试。@Dirkedelbuettel谢谢!我今天从Rcpp开始。太棒了!所以转换是一个相当大的开销,这正是我想知道的。太棒了!所以转换是相当大的开销,这正是我想知道的。