R:从一系列值中筛选值

pbossiut  于 2023-03-27  发布在  其他
关注(0)|答案(2)|浏览(172)

我有这样的数据框

situations <- c("{17: '', 80: '', 55: '693', 29: '', 103: '19', 233: '872', 6: '', 20: '', 230: '99.3', 215: '', 102: '47.7', 56: 'Center', 146: '85.1', 147: '40.6', 23: '', 231: '47.8'}", "{103: '1.9', 18: '', 154: '', 147: '48.6', 22: '', 233: '879', 76: '', 459: '', 55: '719', 29: '', 102: '54.2', 56: 'Center', 328: '', 146: '94.7', 20: ''}", "{215: '', 22: '', 56: 'Center', 233: '731', 103: '19', 78: '', 230: '97.7', 146: '78.2', 20: '', 102: '50.4', 29: '', 18: '', 55: '899', 147: '43.3', 82: '', 231: '48.7'}")

events <- c("A", "B", "C")

df <- data.frame(situations, events)

并且我想过滤掉包含6(或6:你能帮我一下吗?
我尝试过用grepl来选择行,但是不需要输出。
df$filter <- as.integer(grepl('6:', df$situations))
它保留所有包含6的值。例如76、146、56等
在Python中,我使用这样简单的代码来完成这个任务,但在R中找不到类似的东西。
df['is_ok'] = df['situations'].apply(lambda x: True if 6 in x else False)

解决方案

感谢@MrFlick,我找到了想要的输出

as.integer(grepl('\\b6:', df$situations))

谢谢大家

jogvjijk

jogvjijk1#

它不是真正的JSON,但我们可以用一个小正则表达式强制它。

situations |>
  gsub("'", '"', x = _) |>
  gsub("([^ {,]+):", '"\\1":', x = _) |>
  lapply(jsonlite::fromJSON) |>
  Filter(function(z) !"6" %in% names(z), x = _) |>
  str()
# List of 2
#  $ :List of 15
#   ..$ 103: chr "1.9"
#   ..$ 18 : chr ""
#   ..$ 154: chr ""
#   ..$ 147: chr "48.6"
#   ..$ 22 : chr ""
#   ..$ 233: chr "879"
#   ..$ 76 : chr ""
#   ..$ 459: chr ""
#   ..$ 55 : chr "719"
#   ..$ 29 : chr ""
#   ..$ 102: chr "54.2"
#   ..$ 56 : chr "Center"
#   ..$ 328: chr ""
#   ..$ 146: chr "94.7"
#   ..$ 20 : chr ""
#  $ :List of 16
#   ..$ 215: chr ""
#   ..$ 22 : chr ""
#   ..$ 56 : chr "Center"
#   ..$ 233: chr "731"
#   ..$ 103: chr "19"
#   ..$ 78 : chr ""
#   ..$ 230: chr "97.7"
#   ..$ 146: chr "78.2"
#   ..$ 20 : chr ""
#   ..$ 102: chr "50.4"
#   ..$ 29 : chr ""
#   ..$ 18 : chr ""
#   ..$ 55 : chr "899"
#   ..$ 147: chr "43.3"
#   ..$ 82 : chr ""
#   ..$ 231: chr "48.7"

_特殊参数需要R〉= 4.2。)
如果你需要数字是数字,我们可以使用type.convert

situations |>
  gsub("'", '"', x = _) |>
  gsub("([^ {,]+):", '"\\1":', x = _) |>
  lapply(function(z) type.convert(jsonlite::fromJSON(z), as.is=TRUE)) |>
  Filter(function(z) !"6" %in% names(z), x = _) |>
  str()
# List of 2
#  $ :List of 15
#   ..$ 103: num 1.9
#   ..$ 18 : logi NA
#   ..$ 154: logi NA
#   ..$ 147: num 48.6
#   ..$ 22 : logi NA
#   ..$ 233: int 879
#   ..$ 76 : logi NA
#   ..$ 459: logi NA
#   ..$ 55 : int 719
#   ..$ 29 : logi NA
#   ..$ 102: num 54.2
#   ..$ 56 : chr "Center"
#   ..$ 328: logi NA
#   ..$ 146: num 94.7
#   ..$ 20 : logi NA
#  $ :List of 16
#   ..$ 215: logi NA
#   ..$ 22 : logi NA
#   ..$ 56 : chr "Center"
#   ..$ 233: int 731
#   ..$ 103: int 19
#   ..$ 78 : logi NA
#   ..$ 230: num 97.7
#   ..$ 146: num 78.2
#   ..$ 20 : logi NA
#   ..$ 102: num 50.4
#   ..$ 29 : logi NA
#   ..$ 18 : logi NA
#   ..$ 55 : int 899
#   ..$ 147: num 43.3
#   ..$ 82 : logi NA
#   ..$ 231: num 48.7
kq0g1dla

kq0g1dla2#

也许你可以尝试从reticulate中提取py_eval来解析字符串向量situations,例如,

library(reticulate)
lapply(
  situations,
  function(x) {
    d <- py_eval(x)
    d[endsWith(names(d), "6")]
  }
)

你将获得

[[1]]
[[1]]$`6`
[1] ""

[[1]]$`56`
[1] "Center"

[[1]]$`146`
[1] "85.1"

[[2]]
[[2]]$`76`
[1] ""

[[2]]$`56`
[1] "Center"

[[2]]$`146`
[1] "94.7"

[[3]]
[[3]]$`56`
[1] "Center"

[[3]]$`146`
[1] "78.2"

相关问题