Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/r/72.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
对R中字符串的dplyr友好位操作_R_Dplyr - Fatal编程技术网

对R中字符串的dplyr友好位操作

对R中字符串的dplyr友好位操作,r,dplyr,R,Dplyr,我需要对包含位字符串的tible列执行逐位操作。例如,我希望能够做一些像 ds <- tibble(Id=1:2, X1=c("001", "011"), X2=c("101", "110")) mutate(ds, X1andX2 = magic.AND(X1,X2)) mutate(ds, X1Int = bitStrToInt(X1), X2Int = bitStrToInt(X2)) %>% mutate(X1andX2 = intToBitStr(bitwAnd(X1In

我需要对包含位字符串的tible列执行逐位操作。例如,我希望能够做一些像

ds <- tibble(Id=1:2, X1=c("001", "011"), X2=c("101", "110"))
mutate(ds, X1andX2 = magic.AND(X1,X2))
mutate(ds, X1Int = bitStrToInt(X1), X2Int = bitStrToInt(X2)) %>%
mutate(X1andX2 = intToBitStr(bitwAnd(X1Int, X2Int), bitN=4)) %>%
select(-X1Int, -X2Int)

dsPackage
bitops
使这些操作变得简单

library(bitops)
ds$X1_X2 <- sprintf('%03d', bitAnd(ds$X1, ds$X2))
ds
# A tibble: 2 x 4
#     Id    X1    X2 X1_X2
#  <int> <chr> <chr> <chr>
#1     1   001   101   001
#2     2   011   110   010
库(位操作)

我放弃了一个简单的解决方案。根据康拉德·鲁道夫的建议,我编写了两个转换函数。第一个灵感来自于


它可能不是很有效,我还没有测试过它。如果结果太慢,我将用Perl编写所有内容。

如何
001
101
给出
001
?元素方面,即0&1=>0,0&0=>0,1&1=>1如果您追求性能,第一个明显的问题是为什么要将位存储在字符串中。而是将它们存储在位向量(=整数)中,并执行真正的位运算。@Sotos…根据传统的位运算规则。@Konrad Rudolph,我想到了这一点,但我必须保持它的用户友好性。如果其他人打开数据文件进行快速查看,他们需要能够轻松区分“0101000”(多个0)和“1110111”(多个1)。级别2:使此dplyr友好。抱歉,我提供了一个不好的示例。这种方法适用于三位字符串,但对较长的字符串无效。此外,我可能需要对很长的字符串进行操作,而位运算将所有内容转换为32位整数。我把问题扩大到更清楚。
# A tibble: 2 x 4
      Id    X1    X2   X1andX2
    <int> <chr> <chr>   <chr>
1     1    0101  1110    0100
2     2    1110  0110    0110
library(bitops)
ds$X1_X2 <- sprintf('%03d', bitAnd(ds$X1, ds$X2))
ds
# A tibble: 2 x 4
#     Id    X1    X2 X1_X2
#  <int> <chr> <chr> <chr>
#1     1   001   101   001
#2     2   011   110   010
intToBitStr <- Vectorize(function(x, bitN) {
    i <- 0
    v <- integer(bitN)
    while(x > 0) {
        v[bitN - i] <- x %% 2
        x <- x %/% 2
        i <- i + 1 
    }
    return(paste0(v, collapse=""))
}, c("x"), USE.NAMES = F)

bitStrToInt <- Vectorize(function(x) {
    v <- rev(as.integer(strsplit(x, "")[[1]]))
    acc <- 0
    for (i in 1:length(v)) {
        acc <- acc + v[i] * 2^(i - 1)
    }
    return(acc)
}, USE.NAMES = F)
mutate(ds, X1Int = bitStrToInt(X1), X2Int = bitStrToInt(X2)) %>%
mutate(X1andX2 = intToBitStr(bitwAnd(X1Int, X2Int), bitN=4)) %>%
select(-X1Int, -X2Int)