[GIS] Handling MOD13Q1 NDVI Product Quality Assessment (QA) flags

modisremote sensing

I am working on MOD13Q1 NDVI Product and i want to apply Savitzky Golay filter for smoothing Ndvi time series using Quality Assessment(QA) flags.

I studied MOD13Q1 NDVI help file and found that possible range of values for quality layer is (0-65534) .

For applying SG filter in TIMESAT software i need 3 ranges of QA values for assigning weight of relative importance (1, 0.5, and 0.1) to corresponding ndvi values.

Which ranges of QA values will be useful, moderate useful and useless?

Best Answer

If you just want three ranges - 1, 0.5 and 0, I'd use MOD13Q1 Pixel Reliability instead of VI Quality. From the MOD13Q1 page:

TABLE 1: MOD13Q1 Pixel Reliability
Rank Key Summary QA     Description                                            
      -1 Fill/No Data   Not Processed                                          
       0 Good Data      Use with confidence                                    
       1 Marginal data  Useful, but look at other QA information               
       2 Snow/Ice       Target covered with snow/ice                           
       3 Cloudy         Target not visible, covered with cloud                 

Read the 250m 16 days pixel reliability summary QA layer into an array and assign 1 to your relative importance where QA is 0, 0.5 where QA is 1 and 0 where QA is any other value.

I don't know r but in python it would be something like:

# Assuming the 250m 16 days pixel reliability summary QA layer has been read into "qa" array
importance = numpy.zeros(qa.shape)
importance[qa == 0] = 1
importance[qa == 1] = 0.5

If you want to use the usefulness flags, they are stored as 4 bits in a two dimensional unsigned 16 bit integer array:

TABLE 2: MOD13Q1 VI Quality
Bit 0 is the least significant (read bit words right to left)

bit Long Name    Value Key                                                                               
0–1 MODLAND_QA      00 VI produced, good quality                                                         
                    01 VI produced, but check other QA                                                   
                    10 Pixel produced, but most probably cloudy                                          
                    11 Pixel not produced due to other reasons than clouds                               
2–5 VI usefulness 0000 Highest quality                                                                   
                  0001 Lower quality                                                                     
                  0010 Decreasing quality                                                                
                  0100 Decreasing quality                                                                
                  1000 Decreasing quality                                                                
                  1001 Decreasing quality                                                                
                  1010 Decreasing quality                                                                
                  1100 Lowest quality                                                                    
                  1101 Quality so low that it is not useful                                              
                  1110 L1B data faulty                                                                   
                  1111 Not useful for any other reason/not processed                                     
<SNIP>...

In python you can use the bitwise right shift (>>) and 'and' (&) operators to extract VI usefulness:

# Assuming the 250m 16 days VI Quality detailed QA layer has been read into a UInt16 array "qa"
usefulness = (qa >> 2) & 15 # Right shift 2 bits and extract 1st 4 bits (values of 0-15)
importance = numpy.zeros(qa.shape)
importance[usefulness <= 7] = 0.5
importance[usefulness == 0] = 1

Note the TimeSAT documentation states:

In previous work weights w = 0; 0.5 and 1. have been used for values in the time-series associated with, respectively, cloudy, mixed and clear conditions. There are, of course, no general rules for converting ancillary data to weights associated with the values in the time-series, and the user of the Timesat program is encouraged to take an experimental approach and test different settings.

So you don't have to confine yourself to three weights and can use the VI Quality to define a range of weights. Again a python example:

# Assuming the 250m 16 days VI Quality detailed QA layer has been read into a UInt16 array "qa"
usefulness = (qa >> 2) & 15 # Right shift 2 bits and extract 1st 4 bits (values of 0-15)
importance = numpy.zeros(qa.shape)
importance[usefulness == 0] = 1
importance[usefulness == 1] = 0.8
importance[usefulness == 2] = 0.6
importance[usefulness == 3] = 0.5
importance[usefulness == 4] = 0.4
importance[usefulness == 5] = 0.3
importance[usefulness == 6] = 0.2
importance[usefulness == 7] = 0.1
Related Question