【问题标题】:A lengths() sugar function in Rcpp?Rcpp 中的 lengths() 糖函数?
【发布时间】:2019-12-17 16:56:29
【问题描述】:

在基数 R 中,lengths() 函数计算列表中每个元素的长度。例如,

> mylist = list(v1 = c(1,2,3), v2 = c(1,2), v3 = c(1,2,3,4))
> mylist
$`v1`
[1] 1 2 3

$v2
[1] 1 2

$v3
[1] 1 2 3 4

> lengths(mylist)
v1 v2 v3 
 3  2  4 

在 Rcpp(或来自 Armadillo)中是否有类似的功能?我知道可以编写一个基于 Rcpp 的 apply() 函数,但我想在这一步优化我的速度。谢谢!

【问题讨论】:

    标签: r rcpp armadillo


    【解决方案1】:

    我不知道等效的糖功能,所以很想知道是否也存在。我知道你说你可以自己写,但我会用我使用的这两个函数把我的帽子扔进戒指。一种是递归的,所以它决定了每个子列表元素的大小,另一种相当于lengths()(非递归)。

    library(Rcpp)
    
    cppFunction(
    
      code = 'Rcpp::List rcpp_lengths_recursive( const Rcpp::List& lst ) {
      std::size_t n = lst.size();
      Rcpp::List res( n ); 
      std::size_t i;
    
      for( i = 0; i < n; i++ ) {
        switch( TYPEOF( lst[i] ) ) {
          case VECSXP: {
            // might need an `Rf_inherits( lst[i], "data.frame" )` check, 
            // depending on your use-case
            res[ i ] = rcpp_lengths_recursive( lst[i] );
            break;
          }
          default: {
            int n_elements = Rf_length( lst[i] );
            res[i] = n_elements;
          }
        }
      }
      return res;
    }'
    
    )
    
    cppFunction(
    
      code = 'Rcpp::IntegerVector rcpp_lengths( const Rcpp::List& lst ) {
        std::size_t n = lst.size();
        Rcpp::IntegerVector res( n );
        std::size_t i;
    
        for( i = 0; i < n; i++ ) {
          res[i] = Rf_length( lst[i] );
        }
        return res;
      }'
    
    )
    
    mylist <- list(v1 = c(1,2,3), v2 = c(1,2), v3 = list(list(c(1,2,3,4)), 1:2))
    
    rcpp_lengths( mylist )
    # [1] 3 2 2
    
    rcpp_lengths_recursive( mylist )
    # [[1]]
    # [1] 3
    # 
    # [[2]]
    # [1] 2
    # 
    # [[3]]
    # [[3]][[1]]
    # [[3]][[1]][[1]]
    # [1] 4
    # 
    # 
    # [[3]][[2]]
    # [1] 2
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-06-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-21
      • 1970-01-01
      • 2013-11-13
      相关资源
      最近更新 更多