随机化对称矩阵的非对角元素

Ajm*_*mal 8 random r shuffle matrix

我有一个对称矩阵,我想随机洗牌,同时保持对角线元素不变。所有行的总和均为 1,并且在洗牌后总和仍应为 1。

玩具示例如下:

A <- rbind(c(0.6,0.1,0.3),c(0.1,0.6,0.3),c(0.1,0.3,0.6))
A
#      [,1] [,2] [,3]
# [1,]  0.6  0.1  0.3
# [2,]  0.1  0.6  0.3
# [3,]  0.1  0.3  0.6
Run Code Online (Sandbox Code Playgroud)

我想要一个矩阵 B ,其对角线元素与 A 相同并且仍然对称,但元素随机洗牌以生成类似的内容

B <- rbind(c(0.6,0.3,0.1), c(0.3,0.6,0.1), c(0.3,0.1,0.6))
B
#      [,1] [,2] [,3]
# [1,]  0.6  0.3  0.1
# [2,]  0.3  0.6  0.1
# [3,]  0.3  0.1  0.6
Run Code Online (Sandbox Code Playgroud)

我的目标是在 24 *24 矩阵上执行此操作,因此代码可能会很混乱,并且不需要计算成本较低的东西。到目前为止,我已经尝试过循环,但代码很快就变得过于复杂,我想知道是否有更简单的方法来做到这一点。

Hen*_*rik 3

获取非对角元素的索引。子值和行索引。在每一行中,打乱值并分配回来。

i = row(A) != col(A)
A[i] = ave(A[i], row(A)[i], FUN = sample)
A
#      [,1] [,2] [,3]
# [1,]  0.6  0.1  0.3
# [2,]  0.3  0.6  0.1
# [3,]  0.3  0.1  0.6
Run Code Online (Sandbox Code Playgroud)

如果您不想覆盖原始矩阵,请改为分配给副本。

A = rbind(c(0.6,0.1,0.3), c(0.1,0.6,0.3), c(0.1,0.3,0.6))
i = row(A) != col(A)
A2 = A

set.seed(1)
A2[i] = ave(A[i], row(A)[i], FUN = sample)
A2
#      [,1] [,2] [,3]
# [1,]  0.6  0.1  0.3
# [2,]  0.1  0.6  0.3
# [3,]  0.3  0.1  0.6

set.seed(12)
A2[i] = ave(A[i], row(A)[i], FUN = sample)
A2
#      [,1] [,2] [,3]
# [1,]  0.6  0.3  0.1
# [2,]  0.3  0.6  0.1
# [3,]  0.1  0.3  0.6
Run Code Online (Sandbox Code Playgroud)