基于Python的gdal库读取遥感影像TIFF,Python批量对NDVI植被指数计算(源代码)

目录

 一.单次针对波段分开的TIFF影像的NDVI植被指数的计算 

1.代码如下:(代码中已经将NDVI指数异常值进行了剔除,取值范围最终在[-1, 1]区间内)

2.运行结果(为了方便程序运行的进度查看,在函数内增添进度条显示):

二.针对波段合成后的TIFF影像计算NDVI处理影像

1.对于MODIS——MOD09A1影像(band1为红光波段,band2为近红外波段)

2.对于Landsat 4/5 TM波段影像(band3为红光波段,band4为近红外波段) 

三.针对波段合成后的批量TIFF影像计算NDVI处理


 一.单次针对波段分开的TIFF影像的NDVI植被指数的计算 

1.代码如下:(代码中已经将NDVI指数异常值进行了剔除,取值范围最终在[-1, 1]区间内)

(为了方便程序运行的进度查看,在函数内增添处理过程进度条显示)

from osgeo import gdal, gdalconst
import os
import numpy as np

def NDVI_calculte(Red_band_file, NIR_band_file, NDVI_output_file):
    """
    红光与近红外波段分别存储为tif文件的NDVI指数计算
    :param Red_band_file: 红光波段文件
    :param NIR_band_file: 近红外波段文件
    :param NDVI_output_file: 输出NDVI影像
    :return:
    """
    band_Red = gdal.Open(Red_band_file, gdalconst.GA_ReadOnly)
    band_NIR = gdal.Open(NIR_band_file, gdalconst.GA_ReadOnly)

    cols_Red = band_Red.RasterXSize  # 列数
    rows_Red = band_Red.RasterYSize  # 行数
    cols_NIR = band_NIR.RasterXSize  # 列数
    rows_NIR = band_NIR.RasterYSize  # 行数
    data_type_Red = band_Red.GetRasterBand(1).DataType
    data_type_NIR = band_NIR.GetRasterBand(1).DataType
    geotrans = list(band_Red.GetGeoTransform())
    if (cols_Red != cols_NIR or rows_Red != rows_NIR or data_type_Red != data_type_NIR):
        print("输入红光波段与近红外波段影像参数不对应")
        return


    if os.path.exists(NDVI_output_file) and os.path.isfile(NDVI_output_file):  # 如果已存在同名影像
        os.remove(NDVI_output_file)  # 则删除之

    NDVI = band_Red.GetDriver().Create(NDVI_output_file, xsize=cols_Red, ysize=rows_Red, bands=1,
                                       eType=data_type_Red)  # 创建空的与待处理的tif文件
    NDVI.SetProjection(band_Red.GetProjection())  # 设置投影坐标
    NDVI.SetGeoTransform(geotrans)  # 设置地理变换参数

    data_Red = band_Red.ReadAsArray(buf_xsize=cols_Red, buf_ysize=rows_Red)  #以numpy数组形式读取出图像
    data_NIR = band_NIR.ReadAsArray(buf_xsize=cols_NIR, buf_ysize=rows_NIR)
    data_NDVI = data_NIR
    count = 0              #记录异常值的个数
    list_x = []
    list_y = []            #记录异常值像素的X,Y坐标
    k = 1                  #记录进度
    print("完成进度:",end=" ")
    for i in range(0, rows_Red):
        for j in range(0, cols_Red):
            if (data_NIR[i][j]+data_Red[i][j] != 0 and data_Red[i][j]!=None and data_NIR[i][j]!=None):
                data_NDVI[i][j] = (data_NIR[i][j]-data_Red[i][j])/(data_NIR[i][j]+data_Red[i][j])
                if (data_NDVI[i][j]<-1 or data_NDVI[i][j]>1):    #剔除异常值,使最终NDVI范围在[-1, 1]内
                    data_NDVI[i][j] = None
                    count += 1              #记录异常值的个数,
                    list_x.append(i+1)
                    list_y.append(j+1)      #记录异常值像素的X,Y坐标
            else:
                data_NDVI[i][j] = None
        if i==int(k*(rows_Red/10))-1:       #以10%的进度单位设置进度条
            print(str(k)+"0% ",end="")      #记录进度
            k += 1
    NDVI.GetRasterBand(1).WriteArray(data_NDVI)  # 写入数据到新影像中
    NDVI.GetRasterBand(1).FlushCache()
    NDVI.GetRasterBand(1).ComputeBandStats(False)  # 计算统计信息
    print("\n已剔除异常值,异常值个数为"+str(count)+"个")
    print("正在写入完成")
    del band_Red
    del band_NIR


if __name__ == "__main__":
    print("**********正在开始读取**********")
    print("正在读取第"+str(month)+"月份的NDVI")
    band_Red = "D:/MOD09A1_06_09/Result_Link/mean_Bo_1000/Bo1_mean_2019_0"+str(month)+"_1000.tif"    #红光波段文件
    band_NIR = "D:/MOD09A1_06_09/Result_Link/mean_Bo_1000/Bo2_mean_2019_0"+str(month)+"_1000.tif"    #近红外波段文件
    NDVI_output_file = "D:/MOD09A1_06_09/Result_Link/NDVI_6789/NDVI_2019_06.tif "       #输出NDVI指数文件
    NDVI_calculte(band_Red, band_NIR, NDVI_output_file)
    print("**********读取计算完成**********")

2.运行结果(为了方便程序运行的进度查看,在函数内增添进度条显示):

基于Python的gdal库读取遥感影像TIFF,Python批量对NDVI植被指数计算(源代码)_第1张图片  

展示计算后ArcGIS内的影像截图:

注:该图为Sin投影数据框属性切换为WGS_84后的影像

查看其NDVI直方图如下:

基于Python的gdal库读取遥感影像TIFF,Python批量对NDVI植被指数计算(源代码)_第2张图片

可以看出计算后效果很好。

二.针对波段合成后的TIFF影像计算NDVI处理影像

只需要修改主函数内代码即可

1.对于MODIS——MOD09A1影像(band1为红光波段,band2为近红外波段)

if __name__ == "__main__":
    print("**********正在开始读取**********")
    band_All = "D:/MOD09A1_06_09/Result_Link/mean_Bo_1000/Bo1_mean_2019_06_1000.tif"    #输入合成多波段后文件
    NDVI_output_file = "D:/MOD09A1_06_09/Result_Link/NDVI_6789/NDVI_2019_06.tif "       #输出NDVI指数文件
    NDVI_calculte(band_All.GetRasterBand(1), band_All.GetRasterBand(2), NDVI_output_file)
    print("**********读取计算完成**********")

2.对于Landsat 4/5 TM波段影像(band3为红光波段,band4为近红外波段) 

if __name__ == "__main__":
    print("**********正在开始读取**********")
    band_All = "D:/MOD09A1_06_09/Result_Link/mean_Bo_1000/Bo1_mean_2019_06_1000.tif"    #输入合成多波段后文件
    NDVI_output_file = "D:/MOD09A1_06_09/Result_Link/NDVI_6789/NDVI_2019_06.tif "       #输出NDVI指数文件
    NDVI_calculte(band_All.GetRasterBand(3), band_All.GetRasterBand(4), NDVI_output_file)
    print("**********读取计算完成**********")

三.针对波段合成后的批量TIFF影像计算NDVI处理

 (以MODIS——MOD09A1影像为例)

if __name__ == "__main__":
    print("**********正在开始读取**********")
    file_dir = "D:/MOD09A1_06_09/Result_Link/mean_Bo_1000"    #输入合成多波段后文件路径
    list_dir = os.listdir(file_dir)     #以列表形式返回存储tif文件的文件夹内所有文件
    number_tif = len(list_dir)          #待处理影像数目
    for i in range(0, number_tif):
        band_All = list_dir[i]
        NDVI_output_file = "D:/MOD09A1_06_09/Result_Link/NDVI_6789/NDVI_2019_0"+str(i+1)+".tif "       #输出NDVI指数文件
        NDVI_calculte(band_All.GetRasterBand(1), band_All.GetRasterBand(2), NDVI_output_file)
    print("**********读取计算完成**********")

以上就是关于tif影像的分开波段和多波段植被指数(NDVI)计算方法!

你可能感兴趣的:(Python处理遥感影像,python)