Read shape file with readOGR verses readShapePoly - r

I have read a shapefile using readShapePoly in the maptools package, but cannot read that same file with readOGR. I am hoping someone may be able to help me read the shapefile with readOGR.
I downloaded the file orcounty.shp from here: http://geography.uoregon.edu/geogr/topics/maps.htm
I also downloaded the associated files: orcounty.shx, orcounty.sbx, orcounty.sbn, and orcounty.dbf and put all five files in the folder: c:/users/mark w miller/gis_in_R/shapefile_example/
The following code reads the shapefile and displays some attributes:
library(maptools)
setwd('c:/users/mark w miller/gis_in_R/shapefile_example/')
# Oregon county census data (polygons)
orcounty.poly <- readShapePoly('orcounty.shp', proj4string=CRS("+proj=longlat"))
orcounty.line <- readShapeLines('orcounty.shp', proj4string=CRS("+proj=longlat"))
# see projection
summary(orcounty.poly)
Object of class SpatialPolygonsDataFrame
Coordinates:
min max
x -124.55840 -116.46944
y 41.98779 46.23626
Is projected: FALSE
proj4string : [+proj=longlat]
Data attributes:
However, when I try to read that same shapefile using the following code I receive an error:
library(rgdal)
# read shapefile
oregon.map <- readOGR(dsn="c:/users/mark w miller/gis_in_R/shapefile_example/", layer="orcounty")
# convert to dataframe
oregon.map_df <- fortify(oregon.map)
The error message says:
Error in ogrInfo(dsn = dsn, layer = layer, encoding = encoding, use_iconv = use_iconv) :
Cannot open file
I can read Natural Earth http://www.naturalearthdata.com/ shapefiles using:
library(rgdal)
setwd("c:/users/mark w miller/gis_in_R/")
# read shapefile
wmap <- readOGR(dsn="ne_110m_physical", layer="ne_110m_land")
So, apparently there is a difference between the Natural Earth shapefiles and the Oregon shapefile orcounty.shp.
Thank you for any advice on how to read orcounty.shp with readOGR. My question is similar to the question here: rgdal / readOGR - unable to read shapefile from .zip

Try to remove your last '/' from file path.
readOGR(dsn = 'c:/users/mark w miller/gis_in_R/shapefile_example',
layer = 'orcounty')

For anyone ending up here with this error on a Linux box, I found the problem was using a home path shortcut. i.e.
# Works
readOGR(dsn="/home/user/dir", layer="file")
# Doesn't work
readOGR(dsn="~/dir", layer="file")
I have no idea why.

I used the file ne_110m_land
Try with this:
setwd('D:/JMSR/codes.R/mapas')
unzip("ne_110m_land.zip")
ogrInfo(".", "ne_110m_land")
wmap <- readOGR(".", "ne_110m_land")

raster::shapefile wraps around readOGR to take care of paths and tildes; just pass the full file name.
library(raster)
x <- shapefile("c:/users/orcounty.shp')
or
y <- shapefile("~/users/orcounty.shp")

Related

Extract bands as individual layers from a multilayered tiff file

I have a tiff file which contains 6 bands Data link, I used all methods to extract [See here][2] [see here 2][3] all 6 bands as individual layers but unable to extract them as individual files.
library(raster)
library(ncdf4)
library(rgdal)
r <- raster("E:/TRY/bands.tif")
writeRaster(r, paste0(names(r),".tif"), bylayer=TRUE, format="GTiff")
I get just one tif file and the file doesn't have any information whatsoever like what it is.
Appreciate any help
thanks
Try the function raster::stack. This will read all the layers.
library(raster)
library(ncdf4)
library(rgdal)
s1 <- stack("~/Downloads/bands.tif")
writeRaster(s1, paste0(names(s1),".tif"), bylayer=TRUE, format="GTiff")

Why does cropping a raster stack changes the names of layers?

I'm processing yearly multilayer netCDF files with daily precipitation data from CHIRPS. I have the files for the whole world, each file about 1.2gb large. I need to calculate indices from the precipitation data for each cell in the raster for a specific region. In order to do that I'm trying to crop the files to get a rectangular shape above my area of interest using the raster R package.
This is the code I'm using, exemplary for the first file.
library(ncdf4)
library(raster)
library(rgdal)
# Crop extent
crop_extent <- as(raster::extent(79, 89, 25, 31), "SpatialPolygons")
proj4string(crop_extent) <- "+proj=longlat +ellps=WGS84 +datum=WGS84 +no_defs"
# Set directory with original files
setwd("~/data")
# Read file
chirps81 <- stack("chirps-v2.0.1981.days_p05.nc")
chirps81crop <-crop(chirps1981, crop_extent)
# Write cropped file back to different folder
setwd("~/croppeddata")
writeRaster(chirps81crop, "chirps81crop.nc", overwrite=TRUE)
For some reason however while writing the file the layers lose their name. In the original files and after cropping the names have layer names of the format "X1981.01.01". But after writing and reading the netCDF file with new file <- stack("chirps81crop.nc") the layer names are changed to the format 'X1' up to 'X365'. I think it should be fine working with it, assuming that the order of the layers didn't get mixed up but I don't understand what is happening to the layer names and if this happens because there is something wrong with the code.
It's the writeRaster() function that is losing the layer names, not the crop operation. It is possible to use lower level ncdf functions to assign a numeric value (not a string unfortunately) to each layer which will then show up in the name of the layers after reading. Taking inspiration from the example here, I created some code that shows this.
library(ncdf4)
library(raster)
library(rgdal)
# Crop extent
crop_extent <- as(raster::extent(5.74, 5.75, 50.96, 50.97), "SpatialPolygons")
proj4string(crop_extent) <- "+proj=longlat +ellps=WGS84 +datum=WGS84 +no_defs"
# make a sample file
r <- raster(system.file("external/test.grd", package="raster"))
r.latlon <- projectRaster(r, crs = proj4string(crop_extent))
writeRaster(x=r.latlon, filename = 'test.nc', format = 'CDF', overwrite=TRUE)
# read the sample as a 2 layer stack and crop it
test <- stack('test.nc', 'test.nc')
writeRaster(test, 'teststack.nc', overwrite=TRUE, format='CDF')
testcrop <- crop(test, crop_extent)
names(testcrop)
# [1] "test.1" "test.2"
# write the cropped file and make the zname equal to Layer
writeRaster(testcrop, 'testcrop.nc', overwrite=TRUE, format='CDF', zname='Layer')
# open the cdf file directly
nc <- nc_open('testcrop.nc', write = T)
# give the layers numbers starting from 10 so
# we can see them easily
layers = 1:nlayers(testcrop) + 10
layers
# [1] 11 12
ncvar_put(nc, 'Layer', layers)
nc_close(nc)
newtestcrop <- stack('testcrop.nc')
names(newtestcrop)
# [1] "X11" "X12"
nc <- nc_open('testcrop.nc', write = F)
layers = ncvar_get(nc, 'Layer')
layers
# [1] 11 12
nc_close(nc)
So it is possible to get names with numbers under your control when writing the raster, but I don't know enough about your environment to determine if this will help since it might be tricky to map the names you need to a single unambiguous number.
I hope you don't mind me offering a non-R solution, but this task is much easier from the command line using CDO:
cdo sellonlatbox,79,89,25,31 chirps-v2.0.1981.days_p05.nc cropped_file.nc
Which indices did you want to calculate? I suspect it is possible to calculate those quickly and easily with CDO functions too...

Error in reading shapefile in R

When I try to read shapefiles in a loop in R, it always reports
"Error in .local(x, ...) : file.exists(extension(x, ".shp")) is not
TRUE " .
The code that I use to read the shapefile is
"city.i=shapefile(citynames1[i]) "
where citynames1 is a vector of shapefile names with the extension of .shp.
Thanks very much for your help.
The problem is connected with locale setting on your PC. In my case sf package were able to write files with Chinese characters, please see the code below:
# simulation
library(sf)
file_name <- system.file("shape/nc.shp", package="sf")
nc <- st_read(file_name)
# write shape
st_write(nc, "你好.shp")
# clear & read
rm(list = ls())
nc <- st_read("你好.shp")
plot(nc)
Output:

R: Match Polygons from Shapefile 1 to Area Codes in shapefile 2

I was asked whether R can work with shapefiles - I never worked with shapefiles myself before, but I am sure, others must have come across this kind of question!
I have two shapefiles:
a) shapefile 1 (PolygonSamples.shp) contains a list of polygons which are distributed all over Germany (attached is a sample). The polygons might be smaller, equal or larger than the polygon of one postal codes polygon.
b) shapefile 2 lists the german postal codes and can be downloaded from
https://blog.oraylis.de/2010/05/german-map-spatial-data-for-plz-postal-code-regions/
The question is now:
How to 'match' the two shapefiles to get a dataframe that lists which polygon in shapefile 1 matches which postal codes(s) of shapefile 2. The result ideally looks like
Polygon ID (shapefile 1) Postal Code (shapefile 2)
1 80995
2 80997
2 80999
3 81247
Nothing of what I found matches really my question.
For example From a shapefile with polygons/areas, and points (lat,lon), figure out which polygon/area each point belongs to? In R
seems close, but I don't manage to get the desired dataframe (or datatable) output.
library(maps)
library(maptools)
# Polygons
tmp_dir <- "C:/Users/.../"
polygons <- readShapeSpatial(sprintf('%s/polygons.shp', tmp_dir)
plot(polygons)
# Postal codes
dir <- "C:/Users/..../"
postcode <- readShapeSpatial(sprintf('%s/post_pl.shp', dir)
plot(postcode)
The missing codes snipplet would read something like
result_table <- match(polygons_ID, postcode,
data1= polygon, data2 = postcode,
by = "coordinates in the shapefile"
Sample of polygons in a shapefile (.shp) incl. other spatial files (.dbf,.prj, .qpj,.shx) can be send.
Any help is really VERY much appreciated!
PS: R version 3.2.3, 64 bit, RStudio on Windows 7
Unfortunately I did not find an answer in R, but I could figure out how to match the two independent shapefiles in QGIS.
The main problem: The custom shapefile uses in the .prj file the geocoding Google Mercator (EPSG = 900913), while the downloaded postal code shapefile uses EPSG 4326.
QGIS does not automatically recognize these .prj files as projection files. One has to set them by hand.
Most importantly: Google Mercator (EPSG = 900913) was changed to EPSG= 3857. So for the custom shapefile I had to set – by hand! – the CRS to WGS 84/Pseudo-Mercator EPSG = 3857.
Now I could right click on the custom shape layer -> save as …. And Change the CRS to EPSG 4326. Thus the new custom shapefile now has the same projection like the downloaded postal code shapefile, and they can be joined by location.
(PS: Although I have a solution to do the conversion by hand, I would love to do this in R, because I need the resulting file for analysis.)
Check out: https://gis.stackexchange.com/questions/140504/extracting-intersection-areas-in-r?newreg=033544fa0f5349bcb8167d78867c8073
It gives you which shapefiles in dataset B overlap with a shapefile in dataset A as well as how much area in each of B's shapefiles is present in the target shapefile.

Read Netcdf sub categories and convert to grid

I also posted this question on stack gis 1. From the netcdf4 data that have sub categories, I want to be able to read "Retrieval/fs" variable. I also want to read them and convert to raster girds, but it seems that raster doesn't support netcdf4. I appreciate any suggestions.
library(ncdf4)
library(raster)
file <- "http://140906_B7101Ar_150909171225s.nc4"
names(file$var)
"latitude" ... "longitude"... "Retrieval/fs"
lat <- raster(file, varname="latitude")
lon <- raster(file, varname="longitude")
Error in (function (classes, fdef, mtable) :
unable to find an inherited method for function ‘raster’ for signature ‘"ncdf4"’
raster does work with ncdf4 You are now showing actual code. file is a character vector. You cannot do names(file$var) with that (at least you won't get "latitude" ... "longitude"... "Retrieval/fs". So file is probably ncdf4 object (see the error message), while the raster function expects a filename (but not a url).
If you download the file and then do
library(raster)
x <- brick(filename, var="Retrieval/fs")
Things should work if the ncdf file had regular raster data.
However, it does not so you cannot directly import this as a raster. Instead you can get the lat and lon and values from the files, treat these as points and then rasterize (interpolate) these to get a regular raster.
Here is the answer to the question I asked. Since the data is not gridded, I retrieve the lon and lat information along with the variables to create a dataframe.
fs <- ncvar_get(ncfile, "Retrieval/fs")
xlon <- ncvar_get(ncfile, "longitude")
xlat <- ncvar_get(ncfile, "latitude")
d <- data.frame( as.vector(xlon),as.vector(xlat), as.vector(fs))# create a dataframe
coordinates(d) <- c("xlon","xlat")
proj4string(d) <- CRS("+proj=longlat")
spoint <- SpatialPoints(coords = d) #create a spatial point object

Resources