Почему при извлечении моего списка во фрейм данных получается меньше значений, чем содержится в списке? - PullRequest
0 голосов
/ 29 июня 2018

У меня есть список из примерно 200 000 элементов.

Каждый элемент хранит два значения и представляет координаты карты (широта и долгота).

Я хочу извлечь значения в переменные lat и lon и до сих пор придумал следующее:

for(i in nrow(users)) {
  lat[i] <- users$location[[i]][1]
  lon[i] <- users$location[[i]][2]
}

coords <- as.data.frame(cbind(lat, lon))

Насколько я вижу, он, кажется, извлек первый элемент, а затем 19 элементов в конце, и между ними ничего нет (всего 20 при проверке с complete.cases).

В идеале я бы хотел исключить значения NA и 0, 0.

Глядя на список напрямую, я вижу, что это неправильно, поскольку в нем содержится несколько значений.

Если я сравниваю окончательный фрейм данных с элементами списка, цифры не совпадают. Например, значение -73.9924 существует в списке, но отсутствует в моем фрейме данных.

Куда я иду не так?

Мой окончательный фрейм данных:

> coords[complete.cases(coords), ]
            lat       lon
1       37.4590 -122.1781
96960   40.8152  -73.3624
96961   40.0409  -75.6374
96962   42.5153  -70.9075
96963   33.7773  -84.3366
96964   39.9831  -86.2876
96965   40.7588  -73.9680
96966   36.7646  -76.1990
96967   44.7415  -91.3012
96968   42.6179  -70.7154
96969   40.5953  -74.6173
96970   50.8000   -0.3667
96971   34.0523 -118.3852
96972   41.4468  -74.0689
96973   26.9467  -80.2170
96974   40.7139  -74.0079
96975   34.2313 -118.1486
96976   43.6655  -79.4378
96977   39.0972  -84.1225
96978 -122.1781   37.4590

Пример содержимого списка:

[[734]]
[1] 0 0

[[735]]
[1] 0 0

[[736]]
[1] 0 0

[[737]]
[1] 0 0

[[738]]
[1] -73.9924  40.7553

[[739]]
[1] 0 0

[[740]]
[1] -76.7818  39.4370

[[741]]
[1] -97.822  37.751

[[742]]
NULL

[[743]]
[1] 0 0

[[744]]
[1] 0 0

Ответы [ 2 ]

0 голосов
/ 29 июня 2018

Нет необходимости в for петле. Используйте sapply с [ в качестве функции:

lat<-sapply(users$location,"[",1)
lon<-sapply(users$location,"[",2)

Не уверен, что является причиной пропуска строк, но если это все еще не работает, мы можем оттуда выяснить основную причину.

Если вы хотите избежать NULL s, используйте это с двумя векторами, которые вы создали:

lat<-unlist(lat[!sapply(lat,is.null)])

и аналогично для lon. Кроме того, вы можете применить ту же логику к пользователям $ location перед созданием lat и lon - может быть быстрее с длинными списками.

Если вы хотите все в одной (несколько) элегантной команде, я бы предложил пройти через промежуточный процесс преобразования списка в матрицу с использованием sapply, а затем изменить его на data.frame:

coords<-as.data.frame(t(sapply(users$location[!sapply(users$location,is.null)],"[",c(1,2)))) %>% 
dplyr::rename(lat=V1,lon=V2) %>% 
dplyr::filter(!lat==0,!lon==0)
0 голосов
/ 29 июня 2018

Предположим, у вас есть список, как в моем примере, вы можете использовать dplyr, например:

require(dplyr)
lista <- list(as.data.frame(matrix(c(0,0), nrow = 1)), 
          as.data.frame(matrix(c(37.4590,-122.1781), nrow = 1)), 
          as.data.frame(matrix(c(NA,NA), nrow = 1)), 
          as.data.frame(matrix(c(42.5153,-70.9075), nrow = 1))) # toy example
names(lista) <- 1:4 # each element in the list has a name

lista %>% 
  bind_rows() %>% 
  filter(!is.na(V1), !is.na(V2)) %>%  # here you remove NAs
  filter(V1 != 0, V2 != 0) # here you remove zeros
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...