当前位置: 首页 > 知识库问答 >
问题:

使用数据进行矩阵运算和组件加法。桌子

乐正焕
2023-03-14

如果要求和的矩阵数事先未知,那么进行分量矩阵加法的最佳方法是什么?一般来说,是否有一种在数据上下文中执行矩阵(或多维数组)操作的好方法。桌子我使用数据。表,用于通过几个固定变量或类别对数据进行排序和分组的效率,每个变量或类别包含不同数量的观察值。

例如:

  1. 在数据的每个观察(行)中查找给定向量分量的外积,为每行返回矩阵。
  2. 对每个数据类别分组的所有行按组件方式求和所得矩阵。

这里用2x2矩阵和一个类别来说明:

library(data.table)

# example data, number of rows differs by category t
N <- 5
dt <- data.table(t = rep(c("a", "b"), each = 3, len = N), 
                 x1 = rep(1:2, len = N), x2 = rep(3:5, len = N),
                 y1 = rep(1:3, len = N), y2 = rep(2:5, len = N))
setkey(dt, t)
> dt
   t x1 x2 y1 y2
1: a  1  3  1  2
2: a  2  4  2  3
3: a  1  5  3  4
4: b  2  3  1  5
5: b  1  4  2  2

我尝试了一个函数来计算外积上的矩阵和,%o%

mat_sum <- function(x1, x2, y1, y2){
  x <- c(x1, x2) # x vector
  y <- c(y1, y2) # y vector
  xy <- x %o% y # outer product (i.e. 2x2 matrix)
  sum(xy)  # <<< THIS RETURNS A SINGLE VALUE, NOT WHAT I WANT.
  }

当然,这是行不通的,因为sum将数组中的所有元素相加。

我使用Reduce(“”,.list)看到了这个答案,但这似乎需要已经有一个list来添加所有矩阵。我还没有弄明白如何在数据中做到这一点。表,因此我有一个麻烦的解决方法:

# extract each outer product component first...
mat_comps <- function(x1, x2, y1, y2){
  x <- c(x1, x2) # x vector
  y <- c(y1, y2) # y vector
  xy <- x %o% y # outer product (i.e. 2x2 matrix)
  xy11 <- xy[1,1]
  xy21 <- xy[2,1]
  xy12 <- xy[1,2]
  xy22 <- xy[2,2]
  return(c(xy11, xy21, xy12, xy22))
}

# ...then running this function on dt, 
# taking extra step (making column 'n') to apply it row-by-row...
dt[, n := 1:nrow(dt)]
dt[, c("xy11", "xy21", "xy12", "xy22") := as.list(mat_comps(x1, x2, y1, y2)), 
   by = n]

# ...then sum them individually, now grouping by t
s <- dt[, list(s11 = sum(xy11),
               s21 = sum(xy21),
               s12 = sum(xy12),
               s22 = sum(xy22)),
        by = key(dt)]
> s
   t s11 s21 s12 s22
1: a   8  26  12  38
2: b   4  11  12  23

这就给出了求和的分量,这些分量最终可以转换回矩阵。

共有2个答案

曹高轩
2023-03-14

编辑:对于“x”和“y”中的两个元素,修改后的函数可以是:

ff2 = function(x_ls, y_ls)
{
   combs_ls = lapply(seq_along(x_ls[[1]]), 
                     function(i) list(sapply(x_ls, "[[", i), 
                                      sapply(y_ls, "[[", i)))
   rowSums(sapply(combs_ls, function(x) as.vector(do.call(outer, x))))
}

其中,"x_ls"和"y_ls"是各个向量的列表。

使用它:

dt[, as.list(ff2(list(x1, x2), list(y1, y2))), by = t]
#   t V1 V2 V3 V4
#1: a  8 26 12 38
#2: b  4 11 12 23

以及其他“数据帧/表格”:

set.seed(101)
DF = data.frame(group = rep(letters[1:3], c(4, 2, 3)), 
                x1 = sample(1:20, 9, T), x2 = sample(1:20, 9, T), 
                x3 = sample(1:20, 9, T), x4 = sample(1:20, 9, T),
                y1 = sample(1:20, 9, T), y2 = sample(1:20, 9, T), 
                y3 = sample(1:20, 9, T), y4 = sample(1:20, 9, T))               
DT = as.data.table(DF)

DT[, as.list(ff2(list(x1, x2, x3, x4), 
                 list(y1, y2, y3, y4))), by = group]
#   group  V1  V2  V3  V4  V5  V6  V7  V8  V9 V10 V11 V12 V13 V14 V15 V16
#1:     a 338 661 457 378 551 616 652 468 460 773 536 519 416 766 442 532
#2:     b 108 261 171  99  29  77  43  29 154 386 238 146 161 313 287 121
#3:     c 345 351 432 293 401 421 425 475 492 558 621 502 510 408 479 492

不过,我不知道“data.table”中的一个函数如何不明确说明在函数中使用哪些列;i、 e.你如何做与以下工作相当的工作:

do.call(rbind, lapply(split(DF[-1], DF$group), 
                      function(x) 
                          do.call(ff2, c(list(x[grep("^x", names(x))]), 
                                         list(x[grep("^y", names(x))])))))
#  [,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10] [,11] [,12] [,13] [,14] [,15] [,16]
#a  338  661  457  378  551  616  652  468  460   773   536   519   416   766   442   532
#b  108  261  171   99   29   77   43   29  154   386   238   146   161   313   287   121
#c  345  351  432  293  401  421  425  475  492   558   621   502   510   408   479   492

旧答案:

也许你可以这样定义你的函数

ff1 = function(x1, x2, y1, y2)
     rowSums(sapply(seq_along(x1), 
                    function(i) as.vector(c(x1[i], x2[i]) %o% c(y1[i], y2[i]))))

dt[, as.list(ff1(x1, x2, y1, y2)), by = list(t)]
#   t V1 V2 V3 V4
#1: a  8 26 12 38
#2: b  4 11 12 23
华峰
2023-03-14

通常,数据。表设计用于处理列。你越是将问题转化为同列操作,你就越能从数据中获得更多信息。表

这是一个完成这项行动的尝试。也许有更好的办法。这更多的是作为一个模板,提供一个解决问题的想法(尽管我知道这在所有情况下都不可能)。

xcols <- grep("^x", names(dt))
ycols <- grep("^y", names(dt))
combs <- CJ(ycols, xcols)
len <- seq_len(nrow(combs))
cols = paste("V", len, sep="")
for (i in len) {
    c1 = combs$V2[i]
    c2 = combs$V1[i]
    set(dt, i=NULL, j=cols[i], value = dt[[c1]] * dt[[c2]])
}

#    t x1 x2 y1 y2 V1 V2 V3 V4
# 1: a  1  3  1  2  1  3  2  6
# 2: a  2  4  2  3  4  8  6 12
# 3: a  1  5  3  4  3 15  4 20
# 4: b  2  3  1  5  2  3 10 15
# 5: b  1  4  2  2  2  8  2  8

这基本上适用于外部产品。现在,这只是一个聚合它的问题。

dt[, lapply(.SD, sum), by=t, .SDcols=cols]

#    t V1 V2 V3 V4
# 1: a  8 26 12 38
# 2: b  4 11 12 23

编辑:修改一个位,以获得输出的正确顺序为V2V3

 类似资料:
  • 使用JCUDA对复数进行运算的最佳方法是什么?我应该使用cuComplex格式还是有其他的解决方案(像一个数组,实部和虚部一个接着一个走)?我非常感谢使用这种类型的计算的java代码示例。 由于我的目的是用GPU求解复杂的线性方程组,所以我不想只附上jCuda。用GPU进行这样的计算有哪些可供选择的方式?

  • 本文向大家介绍python如何进行矩阵运算,包括了python如何进行矩阵运算的使用技巧和注意事项,需要的朋友参考一下 python进行矩阵运算的方法: 1、矩阵相乘 2、矩阵对应元素相乘 multiply()函数:数组和矩阵对应位置相乘,输出与相乘数组/矩阵的大小一致 3、矩阵点乘 4、矩阵求逆 5、矩阵转置 6、计算每一列、行的和 内容扩展: numpy矩阵运算 (1) 矩阵点乘:m=mult

  • 本文向大家介绍Python中矩阵创建和矩阵运算方法,包括了Python中矩阵创建和矩阵运算方法的使用技巧和注意事项,需要的朋友参考一下 矩阵创建 1、from numpyimport *; a1=array([1,2,3]) a2=mat(a1) 矩阵与方块列表的区别如下: 2、data2=mat(ones((2,4))) 创建一个2*4的1矩阵,默认是浮点型的数据,如果需要时int类型,可以使用

  • 本文向大家介绍Python常用库Numpy进行矩阵运算详解,包括了Python常用库Numpy进行矩阵运算详解的使用技巧和注意事项,需要的朋友参考一下 Numpy支持大量的维度数组和矩阵运算,对数组运算提供了大量的数学函数库! Numpy比Python列表更具优势,其中一个优势便是速度。在对大型数组执行操作时,Numpy的速度比Python列表的速度快了好几百。因为Numpy数组本身能节省内存,并

  • 本文向大家介绍纯python进行矩阵的相乘运算的方法示例,包括了纯python进行矩阵的相乘运算的方法示例的使用技巧和注意事项,需要的朋友参考一下 本文介绍了纯python进行矩阵的相乘运算的方法示例,分享给大家,具体如下: 说明: A矩阵与B矩阵的乘法运算,最终得到新的矩阵X , 思路 首先判断是否可以相乘:前提条件是A的列与B的行要相同 我们可以画图理解:假如A是3行5列,B是5行2列,相乘结

  • 我发现了这个先前的职位,它让我接近。如何将数据帧的列和行的子集转换成数字数组 但是,我需要迭代数据帧,并为“a”中每个正确匹配的值创建一个从列“b”到列“j”的3x3数组(或矩阵),而不是根据第三列中的值创建两列的单个数组(或数组)。 我想要的是两个独立的数组,每个一个 我尝试了以下操作,但收到了一个非常难看的错误。该代码是基于原始帖子的尝试。 这是错误- () ----中的IndexingErr