将某些列重新调整为 R 中的特定均值和标准差

Rescaled certain columns to specific mean and standard deviation in R

给定如下数据框,我如何重新缩放 v5 以便 mean100 并且 standard deviation15

head(df, n=5)

输出:

v1  v2    v3   v4   v5 
65  1   121.12  4   27
98  1   89.36   4   25
85  1   115.44  4   27
83  1   99.45   3   25
115 1   92.75   4   27
98  0   107.90  1   18

我已经尝试使用 psych 包,但最后一列 df 不正确:

library(psych)
library(tidyverse)
v5.rescaled <- df %>% rescale(df$v5, mean = 100, sd = 15)
df$v5.rescaled

输出:

t.t.scale.x.....sd...mean.
121.11985               
89.35994                
115.43986               
99.44991                
92.74993                

但是 head(df, n=5) 对于重新缩放的 v5 不正确:

    v1  v2     v3   v4  v5        v5.rescaled
1   65  1   121.12  4   27  <data.frame [5 × 1]>
2   98  1   89.36   4   25  <data.frame [5 × 1]>
3   85  1   115.44  4   27  <data.frame [5 × 1]>
4   83  1   99.45   3   25  <data.frame [5 × 1]>
5   115 1   92.75   4   27  <data.frame [5 × 1]>
  1. 下次请尝试 post 一个有效的 reprex。这将为其他人省去必须手动复制您的输入数据的麻烦。此外,目前还不清楚您的第一个代码块如何引用具有列 v1 - v5 的 df 与引用 df$mother.iq 的后续代码块之间的关系。
  2. psych::rescale() 的帮助文件明确指出输入 x 应该是 矩阵或数据框 。我怀疑这就是为什么你得到的输出不是你所期望的。
  3. 虽然您可以使用 psych::rescale(),但提供更大灵活性的更好替代方案可能是完全放弃对 {psych} 包的额外依赖,而只是根据需要手动重新缩放列。下面的 reprex 中说明了这两种方法:
# load libraries
library(tidyverse)

# define data as per OP
df <- data.frame(
          v1 = c(65L, 98L, 85L, 83L, 115L, 98L),
          v2 = c(1L, 1L, 1L, 1L, 1L, 0L),
          v3 = c(121.12, 89.36, 115.44, 99.45, 92.75, 107.9),
          v4 = c(4L, 4L, 4L, 3L, 4L, 1L),
          v5 = c(27L, 25L, 27L, 25L, 27L, 18L)
)

# rescale via psych::rescale using entire data frame
df %>% psych::rescale(mean = 100, sd = 15)
#>          v1        v2        v3        v4        v5
#> 1  77.38682 106.12372 119.90143 108.25723 109.31746
#> 2 106.46091 106.12372  82.24089 108.25723 100.71673
#> 3  95.00748 106.12372 113.16617 108.25723 109.31746
#> 4  93.24541 106.12372  94.20546  95.87139 100.71673
#> 5 121.43847 106.12372  86.26070 108.25723 109.31746
#> 6 106.46091  69.38138 104.22535  71.09970  70.61416

# if you only want to do this for specific columns, do it manually by targeting
# columns using dplyr::mutate_at(), an anonymous function, and scale (from base
# R):
df %>% 
  mutate_at(vars(v4, v5), function(x) scale(x)*15 + 100)
#>    v1 v2     v3        v4        v5
#> 1  65  1 121.12 108.25723 109.31746
#> 2  98  1  89.36 108.25723 100.71673
#> 3  85  1 115.44 108.25723 109.31746
#> 4  83  1  99.45  95.87139 100.71673
#> 5 115  1  92.75 108.25723 109.31746
#> 6  98  0 107.90  71.09970  70.61416