尝试循环遍历数据框并引用多个字段

4
我有一个包含地址、城市、州和邮编的数据框。我想使用Yahoo API对每个地址进行地理编码。
我基于O'Reilly的“使用R进行数据混搭”教程中的代码进行开发。原始示例使用硬编码的城市向量。我正在尝试创建一个支持多个城市的动态示例。
以下是代码的简化版本:
    geocodeAddresses<-function(myStreets)
    }
  appid<-'<put your appid here>'
          baseURL<-"http://local.yahooapis.com/MapsService/V1/geocode?appid="
          myGeoTable<-data.frame(address=character(),lat=numeric(),long=numeric(),EID=numeric())
          for (myStreet in myStreets){  
            requestUrl<-paste(baseURL, appid, "&street=", URLencode(myStreet$address),"&city=",URLencode(myStreet$city),"&state=",URLencode(myStreet$state),sep="")
            xmlResult<-xmlTreeParse(requestUrl,isURL=TRUE,addAttributeNamespaces=TRUE)
            geoResult<-xmlResult$doc$children$ResultSet$children$Result
            lat<-xmlValue(geoResult[['Latitude']])
            long<-xmlValue(geoResult[['Longitude']])
            myGeoTable<-rbind(myGeoTable,data.frame(address=myStreet,Y=lat,X=long,EID=NA))
          }
    }

当我尝试引用myStreet$City和myStreet$Address时,出现错误。
$ operator is invalid for atomic vectors

除了循环遍历数据框myStreets,我不知道如何为每一行只调用一次Yahoo API并存储每个成员的经纬度。

2个回答

6
如果myStreets是数据框,则for循环会遍历它的每一列。因此,第一步取出Addres并且Addres$City没有意义。
您可以将for条件更改为遍历行:
for (i in 1:nrow(myStreets))  {
   myStreet <- myStreets[i,]
   # rest is the same
}

为了优化您的代码,您还可以采取以下措施:
myGeoTable <- data.frame( address=myStreet$address, lat=NA_real_, long=NA_real_, EID=NA_real_)
for (i in 1:nrow(myStreets))  {
  myStreet <- myStreets[i,] 
  requestUrl <- ...
  ...
  myGeoTable[i,2:4] <- c(lat,long,NA)
}

小心使用 1:nrow 语法。如果 myStreet 中没有行,则会生成序列 1 0。更安全的做法是使用 seq_len(nrow(myStreets)) - Head

4
如果你要这样做,我建议不要在公共场合谈论它。这违反了他们的服务条款。我建议使用USC webgis。几个月前,我地理编码了大约50万条记录,没有遇到太多问题。

我需要更好地检查服务条款。我原以为由于 O'Reilly 在教程中使用了此 API,并且我们每 24 小时仅能获取 5k 次请求,因此这是公平竞争的。谢谢你提醒我。我会确保查看 USC WebGIS。 - Neil Kodner

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接