Calculate list of raster from two different subfolder using ArcPy

2428
29
Jump to solution
08-17-2016 04:02 AM
ShouvikJha
Occasional Contributor III

I have two different folder (workspace1 and workspace2) with Rasters data with the two different parameters. Whatever raster in workspace1 (input raster name e.g 001_mean, 002_mean, 003_mean, 004_mean ….012_mean ), I would like to execute below equation

((Raster – Min Rater value) * (0.95 – 0.01)) / (Max raster value – Min Raster Value )‍

and save it into outputfolder 1 name of output (e.g. 001_FPAR, 002_FPAR, 003_FPAR, 004_FPAR ….012_FPAR)

After calculating workspace1, I want to take different raster file from workspace 2 (raster name , 001_SR, 002_SR, 003_SR, 004_SR……012_SR) and multiply it with each raster file with calculated raster from workspace 1 and save it into outputfolder 2 as name of 001_APAR, 002_APAR, 003_APAR, 004_APAR ……012_APAR.

I have attached below the list of input raster. 

I have written the code below but its giving error

import arcpy 
arcpy.CheckOutExtension("Spatial") 
from arcpy.sa import * 
 
workspace1 = glob.glob(r"D:\MODIS-NDVI-2012\MASKED-NDVI-2012A") 
workspace2 = glob.glob(r"D:\MODIS-NDVI-2012\MASKED")
outFolder1 = r"D:\MODIS-NDVI-2012\FPAR"
outFolder2 = r"D:\MODIS-NDVI-2012\APAR"
list = arcpy.ListRasters()
for inRaster in list:
 localRaster = Raster(inRaster) 
for r in workspace1 
NDVIMINResult = arcpy.GetRasterProperties_management(inRaster1, "MINIMUM") 
NDVIMAXResult = arcpy.GetRasterProperties_management(inRaster1, "MAXIMUM") 
 
NDVIMin = float(NDVIMINResult.getOutput(0)) 
NDVIMax = float(NDVIMAXResult.getOutput(0))
outminus = Minus(inRaster1, NDVIMin)
outminus1 = Minus(0.95-0.01)
outmultiply = Multiply(outminus,outminus1)
outminus2 = Minus(NDVIMax, NDVIMin)
outdevide = Devide(outmultiply,outminus2)
outdevide.save = (outdevide) 
for r in workspace2
outmultiply1 = Multiply (outdevide,Raster)
outmultiply1.save (outmultiply1)‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍
Tags (3)
0 Kudos
1 Solution

Accepted Solutions
XanderBakker
Esri Esteemed Contributor

Try something like this:

def main():
    import arcpy
    import os

    # Checkout extension
    arcpy.CheckOutExtension("Spatial")
    arcpy.env.overwriteOutput = True

    # avoid using - in folders in combination with raster calculations!
    ws_in_mean = r'D:\MODIS-NDVI-2012\MASKED-NDVI-2012A'
    ws_in_sr = r'D:\MODIS-NDVI-2012\MASKED'
    ws_out_fpar = r'D:\MODIS-NDVI-2012\FPAR'
    ws_out_apar = r'D:\MODIS-NDVI-2012\APAR'

    # list "mean" rasters
    arcpy.env.workspace = ws_in_mean
    lst_ras_mean = arcpy.ListRasters()
    print "lst_ras_mean", lst_ras_mean

    # list "sr" rasters
    arcpy.env.workspace = ws_in_sr
    lst_ras_sr = arcpy.ListRasters()
    print "lst_ras_sr", lst_ras_sr

    for ras_name in lst_ras_mean:
        ras_mean = arcpy.Raster(os.path.join(ws_in_mean, ras_name))
        print "ras_mean", ras_name

        # calculate ((Raster – Min Rater value) * (0.95 – 0.01)) / (Max raster value – Min Raster Value )
        ras_fpar = ((ras_mean - ras_mean.minimum) * (0.95 - 0.01)) / (ras_mean.maximum - ras_mean.minimum)

        # save raster
        ras_num = ras_name[:3]
        out_name_fpar = os.path.join(ws_out_fpar, 'r{0}_FPAR'.format(ras_num))
        ras_fpar.save(out_name_fpar)

        # calculate apar raster
        ras_name_sr = '{0}_SR'.format(ras_num)
        
        if ras_name_sr.upper() in [r.upper() for r in lst_ras_sr]:
            print "ras_name_sr", ras_name_sr
            ras_sr = arcpy.Raster(os.path.join(ws_in_sr, ras_name))
            ras_apar = ras_sr * ras_fpar

            # save raster
            out_name_apar = os.path.join(ws_out_apar, 'r{0}_APAR'.format(ras_num))
            ras_aparsave(out_name_apar)

        else:
            print "Error:", ras_name_sr, "not in lst_ras_sr"


if __name__ == '__main__':
    main()

View solution in original post

29 Replies
XanderBakker
Esri Esteemed Contributor

I would probably do something like this:

def main():
    import arcpy
    import os

    # Checkout extension
    arcpy.CheckOutExtension("Spatial")

    # avoid using - in folders in combination with raster calculations!
    ws_in_mean = r'D:\MODIS-NDVI-2012\MASKED-NDVI-2012A'
    ws_in_sr = r'D:\MODIS-NDVI-2012\MASKED'
    ws_out_fpar = r'D:\MODIS-NDVI-2012\FPAR'
    ws_out_apar = r'D:\MODIS-NDVI-2012\APAR'

    # list "mean" rasters
    arcpy.env.workspace = ws_in_mean
    lst_ras_mean = arcpy.ListRasters()
##    lst_ras_mean = ['001_mean','002_mean','003_mean','004_mean',
##                   '005_mean','006_mean','007_mean','008_mean',
##                   '009_mean','010_mean','011_mean','012_mean']

    # list "sr" rasters
    arcpy.env.workspace = ws_in_sr
    lst_ras_sr = arcpy.ListRasters()
##    lst_ras_sr =  ['001_sr','002_sr','003_sr','004_sr',
##                    '005_sr','006_sr','007_sr','008_sr',
##                    '009_sr','010_sr','011_sr','012_sr']

    for ras_name in lst_ras_mean:
        ras_mean = arcpy.Raster(os.path.join(ws_in_mean, ras_name))

        # calculate ((Raster – Min Rater value) * (0.95 – 0.01)) / (Max raster value – Min Raster Value )
        ras_fpar = ((ras_mean - ras_mean.minimum) * (0.95 - 0.01)) / (ras_mean.maximum - ras_mean.minimum)

        # save raster
        ras_num = ras_name[:3]
        out_name_fpar = os.path.join(ws_out_fpar, 'r{0}_fpar'.format(ras_num))
        ras_fpar.save(out_name_fpar)

        # calculate apar raster
        ras_name_sr = '{0}_sr'.format(ras_num)
        if ras_name_sr in lst_ras_sr:
            ras_sr = arcpy.Raster(os.path.join(ws_in_sr, ras_name))
            ras_apar = ras_sr * ras_fpar

            # save raster
            out_name_apar = os.path.join(ws_out_apar, 'r{0}_apar'.format(ras_num))
            ras_aparsave(out_name_apar)


if __name__ == '__main__':
    main()

Some points to understand:

  • Avoid using "-" in your paths with raster data if you want to perform calculations on them. This may cause errors
  • Avoid starting the names of raster with a number
  • You can use the list rasters in a folder if you set the workspace previously (see lines 15 + 16 and 22 + 23)
  • Use raster objects (see line 29) so you can access the properties minimum and maximum directly from the raster (see line 32) and perform raster algebra (see line 32 and 43)
XanderBakker
Esri Esteemed Contributor

BTW, the code has not been tested, since I do not have access to sample data...

0 Kudos
ShouvikJha
Occasional Contributor III

Xander Bakker‌ , Thank you. I have run the updated code given by you, upto FPAR program run correctly but after FPAR program not working (APAR folder is empty) while its successfully execute. There is no output file for APAR. Even there is no error massage showing after finished the program.

0 Kudos
XanderBakker
Esri Esteemed Contributor

Glad to hear to some part works... The probleable reason for the APAR folder to be empty is the validation performed on line 41. It checks literally if the name exists in the folder with the SR rasters. I notice that I used lowercase. That will probably be the reason for not creating the APAR rasters. Will get back shortly with some code that provides more info and a better way for checking the existence of the required rasters.

0 Kudos
XanderBakker
Esri Esteemed Contributor

Try something like this:

def main():
    import arcpy
    import os

    # Checkout extension
    arcpy.CheckOutExtension("Spatial")
    arcpy.env.overwriteOutput = True

    # avoid using - in folders in combination with raster calculations!
    ws_in_mean = r'D:\MODIS-NDVI-2012\MASKED-NDVI-2012A'
    ws_in_sr = r'D:\MODIS-NDVI-2012\MASKED'
    ws_out_fpar = r'D:\MODIS-NDVI-2012\FPAR'
    ws_out_apar = r'D:\MODIS-NDVI-2012\APAR'

    # list "mean" rasters
    arcpy.env.workspace = ws_in_mean
    lst_ras_mean = arcpy.ListRasters()
    print "lst_ras_mean", lst_ras_mean

    # list "sr" rasters
    arcpy.env.workspace = ws_in_sr
    lst_ras_sr = arcpy.ListRasters()
    print "lst_ras_sr", lst_ras_sr

    for ras_name in lst_ras_mean:
        ras_mean = arcpy.Raster(os.path.join(ws_in_mean, ras_name))
        print "ras_mean", ras_name

        # calculate ((Raster – Min Rater value) * (0.95 – 0.01)) / (Max raster value – Min Raster Value )
        ras_fpar = ((ras_mean - ras_mean.minimum) * (0.95 - 0.01)) / (ras_mean.maximum - ras_mean.minimum)

        # save raster
        ras_num = ras_name[:3]
        out_name_fpar = os.path.join(ws_out_fpar, 'r{0}_FPAR'.format(ras_num))
        ras_fpar.save(out_name_fpar)

        # calculate apar raster
        ras_name_sr = '{0}_SR'.format(ras_num)
        
        if ras_name_sr.upper() in [r.upper() for r in lst_ras_sr]:
            print "ras_name_sr", ras_name_sr
            ras_sr = arcpy.Raster(os.path.join(ws_in_sr, ras_name))
            ras_apar = ras_sr * ras_fpar

            # save raster
            out_name_apar = os.path.join(ws_out_apar, 'r{0}_APAR'.format(ras_num))
            ras_aparsave(out_name_apar)

        else:
            print "Error:", ras_name_sr, "not in lst_ras_sr"


if __name__ == '__main__':
    main()
ShouvikJha
Occasional Contributor III

Following error massage appearing. 001_SR to 012_SR. This program also calculate upto FPAR and when its execute APAR function that time might be error occurring. Below i have attached two images from two workspace . Kindly find it for reference purpose. Thank you 

lst_ras_mean [u'001_mean.tif', u'002_mean.tif', u'003_mean.tif', u'004_mean.tif', u'005_mean.tif', u'006_mean.tif', u'007_mean.tif', u'008_mean.tif', u'009_mean.tif', u'010_mean.tif', u'011_mean.tif', u'012_mean.tif']
lst_ras_sr [u'001_sr.tif', u'002_sr.tif', u'003_sr.tif', u'004_sr.tif', u'005_sr.tif', u'006_sr.tif', u'007_sr.tif', u'008_sr.tif', u'009_sr.tif', u'010_sr.tif', u'011_sr.tif', u'012_sr.tif']‍‍‍‍‍‍
ras_mean 001_mean.tif
Error: 001_SR not in lst_ras_sr ‍‍‍‍‍‍‍‍‍‍‍‍
XanderBakker
Esri Esteemed Contributor

I did not include the .tif extension in the name on line 38. Change this line to:

        ras_name_sr = '{0}_SR.TIF'.format(ras_num)

Then you will probably want to have tif files for all the outputs. In that case change line 34 to:

        out_name_fpar = os.path.join(ws_out_fpar, 'r{0}_FPAR.TIF'.format(ras_num))

... and line 46 to:

            out_name_apar = os.path.join(ws_out_apar, 'r{0}_APAR.TIF'.format(ras_num))
ShouvikJha
Occasional Contributor III

I have rerun the updated code, following error massage appearing. And into mask folder raster name like 001_sr, but program reading different file in that folder   

Runtime error 
Traceback (most recent call last):
 File "<string>", line 53, in <module>
 File "<string>", line 41, in main
RuntimeError: ERROR 000732: Input Raster: Dataset D:\MODIS-NDVI-2012\MASKED\001_mean.tif does not exist or is not supported‍‍‍‍‍


  

0 Kudos
DanPatterson_Retired
MVP Esteemed Contributor

paths with dashes are flakey and filenames beginning with a number can be suspect as well.  create a simple folder and filename to rule out file reading issues

r"c:\test\test.tif"