Я делаю обнаружение объектов деревьев на растровом изображении в формате TIFF. Результатом моей модели является серия ограничивающих рамок, которые предоставляют xmin, xmax, ymin, ymax для каждой ограничивающей рамки для каждого дерева на моем изображении. Эти значения предоставляются в системе координат ИЗОБРАЖЕНИЯ, которая предполагает, что верхний левый угол равен (0,0). Однако мой растр находится в зоне NAD83(CSRS)/UTM 18N (EPSG:2959).
Как преобразовать эти значения в правильную проекцию, чтобы можно было наложить их на растр?
Вот растр .
Вот код для получения данных CSV:
library(deepforestr)
library(terra)
library(sf)
model = df_model()
model$use_release()
raster_path = get_data("sample2.tif") # Gets a path to an example raster tile
bounding_boxes = model$predict_tile(raster_path, return_plot=TRUE)
Данные CSV выглядят следующим образом:
Растр выглядит так:
Я обновил ссылку. И да, я видел вариант Python, но я ищу решение на основе R. Как для этого можно использовать сетчатый пакет?
deepforestr
— это сетчатая реализация (обертка r, обращающаяся к API Python Deepforest). Неясно (пока, т.е. требуется дополнительное чтение), что оболочка ожидает (повторное)-проецирование (из r) или предполагает, что это уже выполнено в deepforest(python) до доступа к r.
Сначала я создаю несколько примеров данных. SpatRaster x
и data.frame с номерами ячеек d
(вместо файлов и снимков экрана используйте данные, сгенерированные кодом, подобные этим, когда задаете вопросы).
library(terra)
x <- rast(ncols=1999, nrows=1249, nlyrs=3, xmin=331567.84, xmax=331887.68,
ymin=5078301.12, ymax=5078500.96, crs='EPSG:2959')
d <- data.frame(xmin=c(1521, 799), ymin=c(910, 1121),
xmax=c(1550, 832), ymax=c(876, 1087))
Вы можете применить простую математику:
fun <- function(r, e) {
cbind(
xmin(r) + e[, c("xmin", "xmax")] * xres(r) + 0.5 * xres(r),
ymax(r) - e[, c("ymin", "ymax")] * yres(r) - 0.5 * yres(r)
)
}
crds <- fun(x, d)
crds
# xmin xmax ymin ymax
#1 331811.3 331815.9 5078355 5078361
#2 331695.8 331701.0 5078322 5078327
Чтобы создать многоугольники, теперь вы можете сделать
p <- apply(crds, 1, \(x) as.polygons(ext(x))) |> vect(crs=crs(x))
p
# class : SpatVector
# geometry : polygons
# dimensions : 2, 0 (geometries, attributes)
# extent : 331695.8, 331815.9, 5078322, 5078361 (xmin, xmax, ymin, ymax)
# coord. ref. : NAD83(CSRS) / UTM zone 18N (EPSG:2959)
Учитывая эту цель, вот альтернативный, более короткий маршрут, который сначала вычисляет номера ячеек.
cmn <- cellFromRowCol(x, d$ymax+1, d$xmin+1)
cmx <- cellFromRowCol(x, d$ymin+1, d$xmax+1)
v <- apply(cbind(cmn,cmx), 1, \(i) as.polygons(ext(x, i))) |> vect(crs=crs(x))
v
# class : SpatVector
# geometry : polygons
# dimensions : 2, 0 (geometries, attributes)
# extent : 331695.7, 331816, 5078321, 5078361 (xmin, xmax, ymin, ymax)
# coord. ref. : NAD83(CSRS) / UTM zone 18N (EPSG:2959)
Я не должен ничего говорить, так как нашел эту «простую математику» весьма полезной, но я подозреваю, что ОП ищет vect
полигонов, полученных из fun(x,d)
результата, что сделало бы это промежуточным решением (это просто просмотр графиков из глубокого леса Python).
Спасибо. Я добавил создание полигона.
В глухом лесу, начинающем проектировать предсказания, по сути, говорится, что это выполняется
rasterio
утилитами на Python (возможно, черезreticulate
из R). Вы это смотрели? Ваша растровая ссылка недоступна.