From be2ebfeb3f80e2966223cea7dfa8b7aab69f5e77 Mon Sep 17 00:00:00 2001
From: kgao <kenny.gao@ssec.wisc.edu>
Date: Thu, 25 Aug 2016 15:58:41 +0000
Subject: [PATCH] Fixed --daily bug and missing dewpoint bugs If dewpoint is
 missing from netcdf files, the script uses rel_hum and air_temp data to
 recreate dewpoint data

--daily was calculating min and max of temperature and dewpoint
plot wrong by not considering dewpoint at all - that has now
been fixed
---
 .../tower_quicklooks/create_quicklook.py      | 92 ++++++++++++++++++-
 1 file changed, 91 insertions(+), 1 deletion(-)

diff --git a/aosstower/tower_quicklooks/create_quicklook.py b/aosstower/tower_quicklooks/create_quicklook.py
index fce1b0d..7873f03 100644
--- a/aosstower/tower_quicklooks/create_quicklook.py
+++ b/aosstower/tower_quicklooks/create_quicklook.py
@@ -452,7 +452,84 @@ def create_full_plot(frame, ymin, ymax, create_air_dew_plot, output):
     axes.get_xaxis().get_major_ticks()[-1].set_visible(True)            
     axes.get_xaxis().get_major_ticks()[0].set_visible(True)            
     
-    plt.savefig(output + '.png')         
+    plt.savefig(output + '.png')
+
+# the purpose of this method is to use TW's algo to convert
+# tempC and relhum to dewpoint
+# @param tempC - temperature value in deg C
+# @param relhum - relative humidity value in %
+
+def calcDewpoint(tempC, relhum):
+    """
+    Algorithm from Tom Whittaker tempC is the temperature in degrees Celsius,
+    relhum is the relative humidity as a percentage.
+
+    :param tempC: temperature in celsius
+    :param relhum: relative humidity as a percentage
+    """
+    if tempC is None or relhum is None:
+        return np.NaN
+
+    gasconst = 461.5
+    latheat = 2500800.0
+
+    dp = 1.0 / (1.0 / (273.15 + tempC) - gasconst * np.log((0.0 + relhum) / 100) /
+                (latheat - tempC * 2397.5))
+
+    return min(dp - 273.15, tempC)    
+
+# The purpose of this method is to check to see if we have dewpoint data
+# if we do not, fill in dewpoint data
+# @param frame - pandas frame of nc data
+# @return frame with dewpoint data and qc_dewpoint with only good data flagged
+
+def check_dewpoint(frame):
+    dewpoint = frame['dewpoint']
+    qc_dewpoint = frame['qc_dewpoint']
+
+    good_list = get_good_data(qc_dewpoint.tolist(), list(frame.index), dewpoint.tolist())
+
+    # no dewpoint data that is viable
+    if len(good_list[0]) == 0:
+        temp = frame['air_temp'].tolist()
+        rel_hum = frame['rh'].tolist()
+        qc_temp = frame['qc_air_temp'].tolist()
+        qc_rel_hum = frame['qc_rh'].tolist()
+        stamps = list(frame.index)
+
+        newDewpoint = {}
+
+        qc_dew = {}
+
+        for idx, rh_quality in enumerate(qc_rel_hum):
+            rh = rel_hum[idx]
+            temp_quality = qc_temp[idx]
+            air_temp = temp[idx]
+            stamp = stamps[idx]
+
+            if not math.isnan(temp_quality):
+                air_temp = None
+
+            elif not math.isnan(rh_quality):
+                rh = None
+
+            dew = calcDewpoint(air_temp, rh)    
+
+            newDewpoint[stamp] = dew
+
+            if math.isnan(dew):
+                qc_dew[stamp] = 1
+
+            else:
+                qc_dew[stamp] = np.NaN    
+        
+        newDewpoint = pd.Series(newDewpoint)
+        qc_dew = pd.Series(qc_dew)
+
+        frame['dewpoint'] = newDewpoint
+        frame['qc_dewpoint'] = qc_dew
+    
+    return frame                 
 
 def main():
     import argparse
@@ -515,6 +592,8 @@ def main():
 
     #get data
     frame = get_data(args.input_files)
+
+    frame = check_dewpoint(frame)
     
     #only have the data we need
     for name in CHOICES:
@@ -570,6 +649,17 @@ def main():
                 ymin[name] = frame[name].min()
                 ymax[name] = frame[name].max()
 
+            elif name == 'air_temp' and create_air_dew_plot:
+                ymin[name] = math.floor(frame[name].min())
+                ymax[name] = math.ceil(frame[name].max())
+
+                dew_min = math.floor(frame['dewpoint'].min())
+                dew_max = math.ceil(frame['dewpoint'].max())
+
+                ymin[name] = min(dew_min, ymin[name])
+                ymax[name] = max(dew_max, ymax[name])
+
+
             else:
                 ymin[name] = math.floor(frame[name].min())
                 ymax[name] = math.ceil(frame[name].max())    
-- 
GitLab