按组迭代的不同 类 个因子的欧氏距离
Euclidean distant for distinct classes of factors iterated by groups
*更新:Rui 建议的答案很好,可以正常工作。然而,当我 运行 它进行了大约 700 万次观察(我的实际数据集)时,R 卡在了一个计算块中(我使用的是具有 64gb RAM 的机器)。非常感谢任何其他解决方案!
我有一个专利数据框,包括公司、申请年份、专利号和专利 classes。我想根据以下公式计算每个公司基于专利 classes 的连续年份之间的欧氏距离:
其中Xi表示t年属于特定class的专利数,Yi表示上一年(t-1)属于特定class的专利数.
为了进一步说明这一点,请考虑以下数据集:
df <- data.table(Firm = rep(c(LETTERS[1:2]),each=6), Year = rep(c(1990,1990,1991,1992,1992,1993),2),
Patent_Number = sample(184785:194785,12,replace = FALSE),
Patent_Class = c(12,5,31,12,31,6,15,15,15,3,3,1))
> df
Firm Year Patent_Number Patent_Class
1: A 1990 192473 12
2: A 1990 193702 5
3: A 1991 191889 31
4: A 1992 193341 12
5: A 1992 189512 31
6: A 1993 185582 6
7: B 1990 190838 15
8: B 1990 189322 15
9: B 1991 190620 15
10: B 1992 193443 3
11: B 1992 189937 3
12: B 1993 194146 1
由于 1990 年是公司 A 的开始年份,因此该年没有欧几里得距离(应生成 NA。前进到 1991 年,今年 (1991) 的不同 classses和前一年 (1990) 分别是 31、5 和 12。因此,上面的公式对这三个不同的 classes 求和(有三个不同的 'i's)。所以公式的输出将是:
经过相同的计算并重复公司,最终输出应为:
> df
Firm Year Patent_Number Patent_Class El_Dist
1: A 1990 192473 12 NA
2: A 1990 193702 5 NA
3: A 1991 191889 31 1.2247450
4: A 1992 193341 12 0.7071068
5: A 1992 189512 31 0.7071068
6: A 1993 185582 6 1.2247450
7: B 1990 190838 15 NA
8: B 1990 189322 15 NA
9: B 1991 190620 15 0.5000000
10: B 1992 193443 3 1.1180340
11: B 1992 189937 3 1.1180340
12: B 1993 194146 1 1.1180340
为了提高速度,我最好寻找 data.table 解决方案。
非常感谢您的帮助。
我相信下面的函数可以满足问题的要求,但是 Firm == "B"
的结果不等于问题的结果。
fEl_Dist <- function(X){
Year <- X[["Year"]]
PatentClass <- X[["Patent_Class"]]
sapply(seq_along(Year), function(i){
j <- which(Year %in% (Year[i] - 1:0))
tbl <- table(Year[j], PatentClass[j])
if(NROW(tbl) == 1){
NA_real_
} else {
numer <- sum((tbl[2, ] - tbl[1, ])^2)
denom <- sum(tbl[2, ]^2)*sum(tbl[1, ]^2)
sqrt(numer/denom)
}
})
}
setDT(df)[, El_Dist := fEl_Dist(.SD),
by = .(Firm),
.SDcols = c("Year", "Patent_Class")]
head(df)
# Firm Year Patent_Number Patent_Class El_Dist
#1: A 1990 190948 12 NA
#2: A 1990 186156 5 NA
#3: A 1991 190801 31 1.2247449
#4: A 1992 185226 12 0.7071068
#5: A 1992 185900 31 0.7071068
#6: A 1993 186928 6 1.2247449
*更新:Rui 建议的答案很好,可以正常工作。然而,当我 运行 它进行了大约 700 万次观察(我的实际数据集)时,R 卡在了一个计算块中(我使用的是具有 64gb RAM 的机器)。非常感谢任何其他解决方案!
我有一个专利数据框,包括公司、申请年份、专利号和专利 classes。我想根据以下公式计算每个公司基于专利 classes 的连续年份之间的欧氏距离:
其中Xi表示t年属于特定class的专利数,Yi表示上一年(t-1)属于特定class的专利数.
为了进一步说明这一点,请考虑以下数据集:
df <- data.table(Firm = rep(c(LETTERS[1:2]),each=6), Year = rep(c(1990,1990,1991,1992,1992,1993),2),
Patent_Number = sample(184785:194785,12,replace = FALSE),
Patent_Class = c(12,5,31,12,31,6,15,15,15,3,3,1))
> df
Firm Year Patent_Number Patent_Class
1: A 1990 192473 12
2: A 1990 193702 5
3: A 1991 191889 31
4: A 1992 193341 12
5: A 1992 189512 31
6: A 1993 185582 6
7: B 1990 190838 15
8: B 1990 189322 15
9: B 1991 190620 15
10: B 1992 193443 3
11: B 1992 189937 3
12: B 1993 194146 1
由于 1990 年是公司 A 的开始年份,因此该年没有欧几里得距离(应生成 NA。前进到 1991 年,今年 (1991) 的不同 classses和前一年 (1990) 分别是 31、5 和 12。因此,上面的公式对这三个不同的 classes 求和(有三个不同的 'i's)。所以公式的输出将是:
经过相同的计算并重复公司,最终输出应为:
> df
Firm Year Patent_Number Patent_Class El_Dist
1: A 1990 192473 12 NA
2: A 1990 193702 5 NA
3: A 1991 191889 31 1.2247450
4: A 1992 193341 12 0.7071068
5: A 1992 189512 31 0.7071068
6: A 1993 185582 6 1.2247450
7: B 1990 190838 15 NA
8: B 1990 189322 15 NA
9: B 1991 190620 15 0.5000000
10: B 1992 193443 3 1.1180340
11: B 1992 189937 3 1.1180340
12: B 1993 194146 1 1.1180340
为了提高速度,我最好寻找 data.table 解决方案。
非常感谢您的帮助。
我相信下面的函数可以满足问题的要求,但是 Firm == "B"
的结果不等于问题的结果。
fEl_Dist <- function(X){
Year <- X[["Year"]]
PatentClass <- X[["Patent_Class"]]
sapply(seq_along(Year), function(i){
j <- which(Year %in% (Year[i] - 1:0))
tbl <- table(Year[j], PatentClass[j])
if(NROW(tbl) == 1){
NA_real_
} else {
numer <- sum((tbl[2, ] - tbl[1, ])^2)
denom <- sum(tbl[2, ]^2)*sum(tbl[1, ]^2)
sqrt(numer/denom)
}
})
}
setDT(df)[, El_Dist := fEl_Dist(.SD),
by = .(Firm),
.SDcols = c("Year", "Patent_Class")]
head(df)
# Firm Year Patent_Number Patent_Class El_Dist
#1: A 1990 190948 12 NA
#2: A 1990 186156 5 NA
#3: A 1991 190801 31 1.2247449
#4: A 1992 185226 12 0.7071068
#5: A 1992 185900 31 0.7071068
#6: A 1993 186928 6 1.2247449