Apakah ada cara untuk mendapatkan koordinat sudut (dalam derajat lat / panjang) dari file raster menggunakan binding Python gdal?
Beberapa pencarian online telah meyakinkan saya bahwa tidak ada, jadi saya telah mengembangkan pekerjaan dengan mem-parsing keluaran gdalinfo, ini agak mendasar tapi saya pikir mungkin menghemat waktu bagi orang yang mungkin kurang nyaman dengan python. Ini juga hanya berfungsi jika gdalinfo berisi koordinat geografis bersama dengan koordinat sudut, yang saya tidak percaya selalu demikian.
Ini solusi saya, apakah ada yang punya solusi yang lebih baik?
gdalinfo pada raster yang sesuai menghasilkan sesuatu seperti ini di tengah-tengah output:
Corner Coordinates:
Upper Left ( -18449.521, -256913.934) (137d 7'21.93"E, 4d20'3.46"S)
Lower Left ( -18449.521, -345509.683) (137d 7'19.32"E, 5d49'44.25"S)
Upper Right ( 18407.241, -256913.934) (137d44'46.82"E, 4d20'3.46"S)
Lower Right ( 18407.241, -345509.683) (137d44'49.42"E, 5d49'44.25"S)
Center ( -21.140, -301211.809) (137d26'4.37"E, 5d 4'53.85"S)
Kode ini akan berfungsi pada file yang terlihat seperti gdalinfo. Saya percaya kadang-kadang koordinat akan dalam derajat dan desimal, bukan derajat, menit dan detik; itu seharusnya sepele untuk menyesuaikan kode untuk situasi itu.
import numpy as np
import subprocess
def GetCornerCoordinates(FileName):
GdalInfo = subprocess.check_output('gdalinfo {}'.format(FileName), shell=True)
GdalInfo = GdalInfo.split('/n') # Creates a line by line list.
CornerLats, CornerLons = np.zeros(5), np.zeros(5)
GotUL, GotUR, GotLL, GotLR, GotC = False, False, False, False, False
for line in GdalInfo:
if line[:10] == 'Upper Left':
CornerLats[0], CornerLons[0] = GetLatLon(line)
GotUL = True
if line[:10] == 'Lower Left':
CornerLats[1], CornerLons[1] = GetLatLon(line)
GotLL = True
if line[:11] == 'Upper Right':
CornerLats[2], CornerLons[2] = GetLatLon(line)
GotUR = True
if line[:11] == 'Lower Right':
CornerLats[3], CornerLons[3] = GetLatLon(line)
GotLR = True
if line[:6] == 'Center':
CornerLats[4], CornerLons[4] = GetLatLon(line)
GotC = True
if GotUL and GotUR and GotLL and GotLR and GotC:
break
return CornerLats, CornerLons
def GetLatLon(line):
coords = line.split(') (')[1]
coords = coords[:-1]
LonStr, LatStr = coords.split(',')
# Longitude
LonStr = LonStr.split('d') # Get the degrees, and the rest
LonD = int(LonStr[0])
LonStr = LonStr[1].split('\'')# Get the arc-m, and the rest
LonM = int(LonStr[0])
LonStr = LonStr[1].split('"') # Get the arc-s, and the rest
LonS = float(LonStr[0])
Lon = LonD + LonM/60. + LonS/3600.
if LonStr[1] in ['W', 'w']:
Lon = -1*Lon
# Same for Latitude
LatStr = LatStr.split('d')
LatD = int(LatStr[0])
LatStr = LatStr[1].split('\'')
LatM = int(LatStr[0])
LatStr = LatStr[1].split('"')
LatS = float(LatStr[0])
Lat = LatD + LatM/60. + LatS/3600.
if LatStr[1] in ['S', 's']:
Lat = -1*Lat
return Lat, Lon
FileName = Image.cub
# Mine's an ISIS3 cube file.
CornerLats, CornerLons = GetCornerCoordinates(FileName)
# UpperLeft, LowerLeft, UpperRight, LowerRight, Centre
print CornerLats
print CornerLons
Dan itu memberi saya:
[-4.33429444 -5.82895833 -4.33429444 -5.82895833 -5.081625 ]
[ 137.12275833 137.12203333 137.74633889 137.74706111 137.43454722]
Jawaban:
Berikut cara lain untuk melakukannya tanpa memanggil program eksternal.
Apa yang dilakukan adalah mendapatkan koordinat keempat sudut dari geotransform dan memproyeksikannya kembali ke lon / lat menggunakan osr.CoordinateTransformation.
Beberapa kode dari metageta proyek, osr.CoordinateTransformation ide dari jawaban ini
sumber
Ini dapat dilakukan dalam baris kode yang jauh lebih sedikit
ulx
,uly
adalah sudut kiri ataslrx
,,lry
adalah sudut kanan bawahPustaka osr (bagian dari gdal) dapat digunakan untuk mengubah titik ke sistem koordinat apa pun. Untuk satu titik:
Untuk reproject citra raster seluruh akan menjadi masalah yang jauh lebih rumit, tapi GDAL> = 2.0 menawarkan solusi mudah untuk ini juga:
gdal.Warp
.sumber
ST_Transform(ST_SetSRID(ST_MakeBox2D(
[hasilnya]),28355),4283)
itu. (Satu berdalih - 'T' disrc.GetGeoTransform()
harus dikapitalisasi).Saya telah melakukan ini ... ini sedikit sulit dikodekan tetapi jika tidak ada perubahan dengan gdalinfo, ini akan berfungsi untuk gambar yang diproyeksikan UTM!
sumber
gdalinfo
tersedia di jalur pengguna (tidak selalu halnya, terutama pada windows) dan parsing output yang dicetak yang tidak memiliki antarmuka yang ketat - yaitu mengandalkan 'angka ajaib' untuk jarak yang benar. Tidak perlu ketika gdal menyediakan binding python komprehensif yang dapat melakukan ini dengan cara yang lebih eksplisit dan kuatJika raster Anda diputar, maka matematika menjadi sedikit lebih rumit, karena Anda perlu mempertimbangkan masing-masing dari enam koefisien transformasi affine. Pertimbangkan menggunakan affine untuk mengubah transformasi affine / geotransform yang diputar:
Sekarang Anda dapat menghasilkan empat pasangan koordinat sudut:
Dan jika Anda juga membutuhkan batasan berbasis grid (xmin, ymin, xmax, ymax):
sumber
Saya percaya pada versi yang lebih baru dari modul OSGEO / GDAL untuk python seseorang dapat langsung memanggil utilitas GDAL dari kode tanpa melibatkan panggilan sistem. misalnya alih-alih menggunakan subproses untuk menelepon:
gdalinfo orang dapat memanggil gdal.Info (the_name_of_the_file) untuk memiliki eksposur metadata file / anotasi
atau alih-alih menggunakan subproses untuk memanggil: gdalwarp seseorang dapat memanggil gdal. Lewati untuk melakukan warping pada raster.
Daftar utilitas GDAL saat ini tersedia sebagai fungsi internal: http://erouault.blogspot.com/2015/10/gdal-and-ogr-utilities-as-library.html
sumber