jupyterpidaq.Boards.Simulated.ADCsim_line

  1# Noisy line substitute for actual analog to digital converter.
  2# Used to allow a 'demo' mode for JupyterPiDAQ.
  3# J. Gutow <jgutow@new.rr.com> June 11, 2020
  4# license GPL V3 or greater
  5
  6import time
  7
  8from numpy import around
  9from numpy import float64
 10from numpy import floor
 11from numpy import log10
 12from numpy import random
 13from numpy import sqrt
 14from numpy import std
 15
 16from jupyterpidaq.Boards import Board
 17
 18# mimicking an installed ADS1115 ADC PiHAT.
 19RATE = 475
 20# 475 Hz with oversampling best S/N on Pi 3B+ per unit time interval.
 21
 22
 23# other rates 8, 16, 32, 64, 128, 250, 475, 860 in Hz.
 24def find_boards():
 25    return Board_ADCsim_line('placeholder')
 26
 27
 28class Board_ADCsim_line(Board):
 29    """
 30    This class simulates an Analog-to-Digital board that returns a linearly
 31    increasing signal with a small amount of noise on the signal. The
 32    intercept and slope depend upon which hour of the day the simulation is
 33    run.
 34    """
 35    def __init__(self, adc):
 36        super().__init__()
 37        self.name = 'ADCsym Line'
 38        self.vendor = 'JupyterPiDAQ'
 39        self.channels = (0, 1, 2, 3)
 40        self.gains = [1]
 41        self.Vdd = 3.3
 42        self.adc = adc
 43
 44    def getsensors(self):
 45        """
 46        Return a list of valid sensor object names for this board.
 47        :return: list of classnames
 48        """
 49        sensorlist = ['RawAtoD',
 50                      'VernierSSTemp',
 51                      'VernierGasP',
 52                      'VernierpH',
 53                      'VernierFlatpH'
 54                      ]
 55        # TODO: extend this list as appropriate. You can get a full list
 56        #  using the `Sensors.sensors.listSensors()` call.
 57        # The main program will use this list to access the actual sensor
 58        # objects when converting the raw board voltage and for producing
 59        # a menu of valid options for this particular board.
 60        return sensorlist
 61
 62    def V_oversampchan(self, chan, gain, avg_sec, data_rate=RATE):
 63        """
 64        This routine returns the average voltage for the channel
 65        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
 66        number of seconds. The 0.0012 is the required loop time
 67        on a RPI 3B+ in python3. The voltage is rounded to the number
 68        of decimals indicated by the standard deviation. The standard
 69        deviation and the estimated deviation of the mean are also
 70        returned.
 71        Parameters
 72            chan    the channel number 0, 1, 2, 3
 73            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
 74                    8 (+/-0.512V), 16 (+/-0.256V)
 75            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
 76             or 860 Hz)
 77            avg_sec seconds to average for, actual averaging interval will be
 78             as close as possible for an integer number of samples.
 79        Returns a tuple (V_avg, V_min, V_max, time_stamp)
 80            V_avg   the averaged voltage
 81            stdev   estimated standard deviation of the measurements
 82            stdev_avg   estimated standard deviation of the mean
 83            time_stamp the time at halfway through the averaging interval in
 84             seconds since the beginning of the epoch (OS dependent begin
 85             time).
 86
 87        """
 88        time_tuple = time.localtime()
 89        nearesthr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
 90                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
 91                                 time_tuple.tm_wday, time_tuple.tm_yday,
 92                                 time_tuple.tm_isdst))
 93        n_samp = int(round(avg_sec / (0.0017 + 1 / data_rate)))
 94        if n_samp < 1:
 95            n_samp = 1
 96        value = []
 97        start = time.time()
 98        intercept = (time.time() - nearesthr) / 1800
 99        slope = (time.time() - nearesthr) / 692000
100        for k in range(n_samp):
101            tempval = intercept + slope * (time.time() - nearesthr) + (
102                    random.random() - 0.5) * slope
103            value.append(tempval)
104        end = time.time()
105        time_stamp = (start + end) / 2.0
106        V_avg = sum(value) / len(value) / gain
107        V_max = max(value)
108        V_min = min(value)
109        return V_avg, V_min, V_max, time_stamp, self.Vdd
110
111    def V_oversampchan_stats(self, chan, gain, avg_sec, data_rate=RATE):
112        """
113        This routine returns the average voltage for the channel
114        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
115        number of seconds. The 0.0012 is the required loop time
116        on a RPI 3B+ in python3. The voltage is rounded to the number
117        of decimals indicated by the standard deviation. The standard
118        deviation and the estimated deviation of the mean are also
119        returned.
120        Parameters
121            chan    the channel number 0, 1, 2, 3
122            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
123                    8 (+/-0.512V), 16 (+/-0.256V)
124            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
125             or 860 Hz)
126            avg_sec seconds to average for, actual averaging interval will be
127             as close as possible for an integer number of samples.
128        Returns a tuple (V_avg, V_min, V_max, time_stamp)
129            V_avg   the averaged voltage
130            stdev   estimated standard deviation of the measurements
131            stdev_avg   estimated standard deviation of the mean
132            time_stamp the time at halfway through the averaging interval in
133              seconds since the beginning of the epoch (OS dependent begin
134              time).
135
136        """
137        time_tuple = time.localtime()
138        currhr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
139                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
140                                 time_tuple.tm_wday, time_tuple.tm_yday,
141                                 time_tuple.tm_isdst))
142        currdy = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
143                                 time_tuple.tm_mday, 0, 0, 0,
144                                 time_tuple.tm_wday, time_tuple.tm_yday,
145                                 time_tuple.tm_isdst))
146        n_samp = int(round(avg_sec / (0.0017 + 1 / data_rate)))
147        if n_samp < 1:
148            n_samp = 1
149        value = []
150        start = time.time()
151        intercept = (currhr - currdy) / 24 / 3600 - 0.5
152        slope = (currhr - currdy) / 24 / 3600 / 300
153        for k in range(n_samp):
154            tempval = intercept + slope * (time.time() - currhr) + (
155                    random.random() - 0.5) * slope
156            value.append(tempval)
157        end = time.time()
158        time_stamp = (start + end) / 2
159        V_avg = sum(value) / len(value) / gain
160        stdev = std(value, ddof=1, dtype=float64) / gain
161        stdev_avg = stdev / sqrt(float(len(value)))
162        decimals = 0
163        if stdev_avg == 0:
164            decimals = 6
165        else:
166            if (stdev_avg != float('inf')) and (stdev_avg > 0):
167                decimals = -int(floor(log10(stdev_avg)))
168        # print('decimals = '+str(decimals))
169        V_avg = around(V_avg, decimals=decimals)
170        stdev = around(stdev, decimals=decimals)
171        stdev_avg = around(stdev_avg, decimals=decimals)
172        return V_avg, stdev, stdev_avg, time_stamp, self.Vdd
173
174    def V_sampchan(self, chan, gain, data_rate=RATE):
175        """
176        This routine returns the average voltage for the channel
177        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
178        number of seconds. The 0.0012 is the required loop time
179        on a RPI 3B+ in python3. The voltage is rounded to the number
180        of decimals indicated by the standard deviation. The standard
181        deviation and the estimated deviation of the mean are also
182        returned.
183        Parameters
184            chan    the channel number 0, 1, 2, 3
185            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
186                    8 (+/-0.512V), 16 (+/-0.256V)
187            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
188             or 860 Hz) avg_sec seconds to average for, actual averaging
189             interval will be as close as possible for an integer number of
190             samples.
191        Returns a tuple (V_avg, V_min, V_max, time_stamp)
192            V_avg   the averaged voltage
193            stdev   estimated standard deviation of the measurements
194            stdev_avg   estimated standard deviation of the mean
195            time_stamp the time at halfway through the averaging interval in
196             seconds since the beginning of the epoch (OS dependent begin
197             time).
198
199        """
200        time_tuple = time.localtime()
201        nearesthr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
202                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
203                                 time_tuple.tm_wday, time_tuple.tm_yday,
204                                 time_tuple.tm_isdst))
205        start = time.time()
206        intercept = (time.time() - nearesthr) / 1800
207        slope = (time.time() - nearesthr) / 692000
208        V = intercept + slope * (time.time() - nearesthr) + (random.random()
209                                                             - 0.5) * slope
210        end = time.time()
211        time_stamp = (start + end) / 2.0
212        return V, time_stamp, self.Vdd
def find_boards():
25def find_boards():
26    return Board_ADCsim_line('placeholder')
class Board_ADCsim_line(jupyterpidaq.Boards.boards.Board):
 29class Board_ADCsim_line(Board):
 30    """
 31    This class simulates an Analog-to-Digital board that returns a linearly
 32    increasing signal with a small amount of noise on the signal. The
 33    intercept and slope depend upon which hour of the day the simulation is
 34    run.
 35    """
 36    def __init__(self, adc):
 37        super().__init__()
 38        self.name = 'ADCsym Line'
 39        self.vendor = 'JupyterPiDAQ'
 40        self.channels = (0, 1, 2, 3)
 41        self.gains = [1]
 42        self.Vdd = 3.3
 43        self.adc = adc
 44
 45    def getsensors(self):
 46        """
 47        Return a list of valid sensor object names for this board.
 48        :return: list of classnames
 49        """
 50        sensorlist = ['RawAtoD',
 51                      'VernierSSTemp',
 52                      'VernierGasP',
 53                      'VernierpH',
 54                      'VernierFlatpH'
 55                      ]
 56        # TODO: extend this list as appropriate. You can get a full list
 57        #  using the `Sensors.sensors.listSensors()` call.
 58        # The main program will use this list to access the actual sensor
 59        # objects when converting the raw board voltage and for producing
 60        # a menu of valid options for this particular board.
 61        return sensorlist
 62
 63    def V_oversampchan(self, chan, gain, avg_sec, data_rate=RATE):
 64        """
 65        This routine returns the average voltage for the channel
 66        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
 67        number of seconds. The 0.0012 is the required loop time
 68        on a RPI 3B+ in python3. The voltage is rounded to the number
 69        of decimals indicated by the standard deviation. The standard
 70        deviation and the estimated deviation of the mean are also
 71        returned.
 72        Parameters
 73            chan    the channel number 0, 1, 2, 3
 74            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
 75                    8 (+/-0.512V), 16 (+/-0.256V)
 76            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
 77             or 860 Hz)
 78            avg_sec seconds to average for, actual averaging interval will be
 79             as close as possible for an integer number of samples.
 80        Returns a tuple (V_avg, V_min, V_max, time_stamp)
 81            V_avg   the averaged voltage
 82            stdev   estimated standard deviation of the measurements
 83            stdev_avg   estimated standard deviation of the mean
 84            time_stamp the time at halfway through the averaging interval in
 85             seconds since the beginning of the epoch (OS dependent begin
 86             time).
 87
 88        """
 89        time_tuple = time.localtime()
 90        nearesthr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
 91                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
 92                                 time_tuple.tm_wday, time_tuple.tm_yday,
 93                                 time_tuple.tm_isdst))
 94        n_samp = int(round(avg_sec / (0.0017 + 1 / data_rate)))
 95        if n_samp < 1:
 96            n_samp = 1
 97        value = []
 98        start = time.time()
 99        intercept = (time.time() - nearesthr) / 1800
100        slope = (time.time() - nearesthr) / 692000
101        for k in range(n_samp):
102            tempval = intercept + slope * (time.time() - nearesthr) + (
103                    random.random() - 0.5) * slope
104            value.append(tempval)
105        end = time.time()
106        time_stamp = (start + end) / 2.0
107        V_avg = sum(value) / len(value) / gain
108        V_max = max(value)
109        V_min = min(value)
110        return V_avg, V_min, V_max, time_stamp, self.Vdd
111
112    def V_oversampchan_stats(self, chan, gain, avg_sec, data_rate=RATE):
113        """
114        This routine returns the average voltage for the channel
115        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
116        number of seconds. The 0.0012 is the required loop time
117        on a RPI 3B+ in python3. The voltage is rounded to the number
118        of decimals indicated by the standard deviation. The standard
119        deviation and the estimated deviation of the mean are also
120        returned.
121        Parameters
122            chan    the channel number 0, 1, 2, 3
123            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
124                    8 (+/-0.512V), 16 (+/-0.256V)
125            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
126             or 860 Hz)
127            avg_sec seconds to average for, actual averaging interval will be
128             as close as possible for an integer number of samples.
129        Returns a tuple (V_avg, V_min, V_max, time_stamp)
130            V_avg   the averaged voltage
131            stdev   estimated standard deviation of the measurements
132            stdev_avg   estimated standard deviation of the mean
133            time_stamp the time at halfway through the averaging interval in
134              seconds since the beginning of the epoch (OS dependent begin
135              time).
136
137        """
138        time_tuple = time.localtime()
139        currhr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
140                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
141                                 time_tuple.tm_wday, time_tuple.tm_yday,
142                                 time_tuple.tm_isdst))
143        currdy = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
144                                 time_tuple.tm_mday, 0, 0, 0,
145                                 time_tuple.tm_wday, time_tuple.tm_yday,
146                                 time_tuple.tm_isdst))
147        n_samp = int(round(avg_sec / (0.0017 + 1 / data_rate)))
148        if n_samp < 1:
149            n_samp = 1
150        value = []
151        start = time.time()
152        intercept = (currhr - currdy) / 24 / 3600 - 0.5
153        slope = (currhr - currdy) / 24 / 3600 / 300
154        for k in range(n_samp):
155            tempval = intercept + slope * (time.time() - currhr) + (
156                    random.random() - 0.5) * slope
157            value.append(tempval)
158        end = time.time()
159        time_stamp = (start + end) / 2
160        V_avg = sum(value) / len(value) / gain
161        stdev = std(value, ddof=1, dtype=float64) / gain
162        stdev_avg = stdev / sqrt(float(len(value)))
163        decimals = 0
164        if stdev_avg == 0:
165            decimals = 6
166        else:
167            if (stdev_avg != float('inf')) and (stdev_avg > 0):
168                decimals = -int(floor(log10(stdev_avg)))
169        # print('decimals = '+str(decimals))
170        V_avg = around(V_avg, decimals=decimals)
171        stdev = around(stdev, decimals=decimals)
172        stdev_avg = around(stdev_avg, decimals=decimals)
173        return V_avg, stdev, stdev_avg, time_stamp, self.Vdd
174
175    def V_sampchan(self, chan, gain, data_rate=RATE):
176        """
177        This routine returns the average voltage for the channel
178        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
179        number of seconds. The 0.0012 is the required loop time
180        on a RPI 3B+ in python3. The voltage is rounded to the number
181        of decimals indicated by the standard deviation. The standard
182        deviation and the estimated deviation of the mean are also
183        returned.
184        Parameters
185            chan    the channel number 0, 1, 2, 3
186            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
187                    8 (+/-0.512V), 16 (+/-0.256V)
188            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
189             or 860 Hz) avg_sec seconds to average for, actual averaging
190             interval will be as close as possible for an integer number of
191             samples.
192        Returns a tuple (V_avg, V_min, V_max, time_stamp)
193            V_avg   the averaged voltage
194            stdev   estimated standard deviation of the measurements
195            stdev_avg   estimated standard deviation of the mean
196            time_stamp the time at halfway through the averaging interval in
197             seconds since the beginning of the epoch (OS dependent begin
198             time).
199
200        """
201        time_tuple = time.localtime()
202        nearesthr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
203                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
204                                 time_tuple.tm_wday, time_tuple.tm_yday,
205                                 time_tuple.tm_isdst))
206        start = time.time()
207        intercept = (time.time() - nearesthr) / 1800
208        slope = (time.time() - nearesthr) / 692000
209        V = intercept + slope * (time.time() - nearesthr) + (random.random()
210                                                             - 0.5) * slope
211        end = time.time()
212        time_stamp = (start + end) / 2.0
213        return V, time_stamp, self.Vdd

This class simulates an Analog-to-Digital board that returns a linearly increasing signal with a small amount of noise on the signal. The intercept and slope depend upon which hour of the day the simulation is run.

Board_ADCsim_line(adc)
36    def __init__(self, adc):
37        super().__init__()
38        self.name = 'ADCsym Line'
39        self.vendor = 'JupyterPiDAQ'
40        self.channels = (0, 1, 2, 3)
41        self.gains = [1]
42        self.Vdd = 3.3
43        self.adc = adc

Should be overridden by each board and define at minimum: self.name = 'board name/adc name/type' Short an useful to end user self.vendor = 'Vendor/Manufacturer name` self.channels = tuple of available channel IDs self.gains = list of gains self.Vdd = voltage provided by board to sensors

def getsensors(self):
45    def getsensors(self):
46        """
47        Return a list of valid sensor object names for this board.
48        :return: list of classnames
49        """
50        sensorlist = ['RawAtoD',
51                      'VernierSSTemp',
52                      'VernierGasP',
53                      'VernierpH',
54                      'VernierFlatpH'
55                      ]
56        # TODO: extend this list as appropriate. You can get a full list
57        #  using the `Sensors.sensors.listSensors()` call.
58        # The main program will use this list to access the actual sensor
59        # objects when converting the raw board voltage and for producing
60        # a menu of valid options for this particular board.
61        return sensorlist

Return a list of valid sensor object names for this board.

Returns

list of classnames

def V_oversampchan(self, chan, gain, avg_sec, data_rate=475):
 63    def V_oversampchan(self, chan, gain, avg_sec, data_rate=RATE):
 64        """
 65        This routine returns the average voltage for the channel
 66        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
 67        number of seconds. The 0.0012 is the required loop time
 68        on a RPI 3B+ in python3. The voltage is rounded to the number
 69        of decimals indicated by the standard deviation. The standard
 70        deviation and the estimated deviation of the mean are also
 71        returned.
 72        Parameters
 73            chan    the channel number 0, 1, 2, 3
 74            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
 75                    8 (+/-0.512V), 16 (+/-0.256V)
 76            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
 77             or 860 Hz)
 78            avg_sec seconds to average for, actual averaging interval will be
 79             as close as possible for an integer number of samples.
 80        Returns a tuple (V_avg, V_min, V_max, time_stamp)
 81            V_avg   the averaged voltage
 82            stdev   estimated standard deviation of the measurements
 83            stdev_avg   estimated standard deviation of the mean
 84            time_stamp the time at halfway through the averaging interval in
 85             seconds since the beginning of the epoch (OS dependent begin
 86             time).
 87
 88        """
 89        time_tuple = time.localtime()
 90        nearesthr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
 91                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
 92                                 time_tuple.tm_wday, time_tuple.tm_yday,
 93                                 time_tuple.tm_isdst))
 94        n_samp = int(round(avg_sec / (0.0017 + 1 / data_rate)))
 95        if n_samp < 1:
 96            n_samp = 1
 97        value = []
 98        start = time.time()
 99        intercept = (time.time() - nearesthr) / 1800
100        slope = (time.time() - nearesthr) / 692000
101        for k in range(n_samp):
102            tempval = intercept + slope * (time.time() - nearesthr) + (
103                    random.random() - 0.5) * slope
104            value.append(tempval)
105        end = time.time()
106        time_stamp = (start + end) / 2.0
107        V_avg = sum(value) / len(value) / gain
108        V_max = max(value)
109        V_min = min(value)
110        return V_avg, V_min, V_max, time_stamp, self.Vdd

This routine returns the average voltage for the channel averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec number of seconds. The 0.0012 is the required loop time on a RPI 3B+ in python3. The voltage is rounded to the number of decimals indicated by the standard deviation. The standard deviation and the estimated deviation of the mean are also returned. Parameters chan the channel number 0, 1, 2, 3 gain 2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V), 8 (+/-0.512V), 16 (+/-0.256V) data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475 or 860 Hz) avg_sec seconds to average for, actual averaging interval will be as close as possible for an integer number of samples. Returns a tuple (V_avg, V_min, V_max, time_stamp) V_avg the averaged voltage stdev estimated standard deviation of the measurements stdev_avg estimated standard deviation of the mean time_stamp the time at halfway through the averaging interval in seconds since the beginning of the epoch (OS dependent begin time).

def V_oversampchan_stats(self, chan, gain, avg_sec, data_rate=475):
112    def V_oversampchan_stats(self, chan, gain, avg_sec, data_rate=RATE):
113        """
114        This routine returns the average voltage for the channel
115        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
116        number of seconds. The 0.0012 is the required loop time
117        on a RPI 3B+ in python3. The voltage is rounded to the number
118        of decimals indicated by the standard deviation. The standard
119        deviation and the estimated deviation of the mean are also
120        returned.
121        Parameters
122            chan    the channel number 0, 1, 2, 3
123            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
124                    8 (+/-0.512V), 16 (+/-0.256V)
125            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
126             or 860 Hz)
127            avg_sec seconds to average for, actual averaging interval will be
128             as close as possible for an integer number of samples.
129        Returns a tuple (V_avg, V_min, V_max, time_stamp)
130            V_avg   the averaged voltage
131            stdev   estimated standard deviation of the measurements
132            stdev_avg   estimated standard deviation of the mean
133            time_stamp the time at halfway through the averaging interval in
134              seconds since the beginning of the epoch (OS dependent begin
135              time).
136
137        """
138        time_tuple = time.localtime()
139        currhr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
140                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
141                                 time_tuple.tm_wday, time_tuple.tm_yday,
142                                 time_tuple.tm_isdst))
143        currdy = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
144                                 time_tuple.tm_mday, 0, 0, 0,
145                                 time_tuple.tm_wday, time_tuple.tm_yday,
146                                 time_tuple.tm_isdst))
147        n_samp = int(round(avg_sec / (0.0017 + 1 / data_rate)))
148        if n_samp < 1:
149            n_samp = 1
150        value = []
151        start = time.time()
152        intercept = (currhr - currdy) / 24 / 3600 - 0.5
153        slope = (currhr - currdy) / 24 / 3600 / 300
154        for k in range(n_samp):
155            tempval = intercept + slope * (time.time() - currhr) + (
156                    random.random() - 0.5) * slope
157            value.append(tempval)
158        end = time.time()
159        time_stamp = (start + end) / 2
160        V_avg = sum(value) / len(value) / gain
161        stdev = std(value, ddof=1, dtype=float64) / gain
162        stdev_avg = stdev / sqrt(float(len(value)))
163        decimals = 0
164        if stdev_avg == 0:
165            decimals = 6
166        else:
167            if (stdev_avg != float('inf')) and (stdev_avg > 0):
168                decimals = -int(floor(log10(stdev_avg)))
169        # print('decimals = '+str(decimals))
170        V_avg = around(V_avg, decimals=decimals)
171        stdev = around(stdev, decimals=decimals)
172        stdev_avg = around(stdev_avg, decimals=decimals)
173        return V_avg, stdev, stdev_avg, time_stamp, self.Vdd

This routine returns the average voltage for the channel averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec number of seconds. The 0.0012 is the required loop time on a RPI 3B+ in python3. The voltage is rounded to the number of decimals indicated by the standard deviation. The standard deviation and the estimated deviation of the mean are also returned. Parameters chan the channel number 0, 1, 2, 3 gain 2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V), 8 (+/-0.512V), 16 (+/-0.256V) data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475 or 860 Hz) avg_sec seconds to average for, actual averaging interval will be as close as possible for an integer number of samples. Returns a tuple (V_avg, V_min, V_max, time_stamp) V_avg the averaged voltage stdev estimated standard deviation of the measurements stdev_avg estimated standard deviation of the mean time_stamp the time at halfway through the averaging interval in seconds since the beginning of the epoch (OS dependent begin time).

def V_sampchan(self, chan, gain, data_rate=475):
175    def V_sampchan(self, chan, gain, data_rate=RATE):
176        """
177        This routine returns the average voltage for the channel
178        averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec
179        number of seconds. The 0.0012 is the required loop time
180        on a RPI 3B+ in python3. The voltage is rounded to the number
181        of decimals indicated by the standard deviation. The standard
182        deviation and the estimated deviation of the mean are also
183        returned.
184        Parameters
185            chan    the channel number 0, 1, 2, 3
186            gain    2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V),
187                    8 (+/-0.512V), 16 (+/-0.256V)
188            data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475
189             or 860 Hz) avg_sec seconds to average for, actual averaging
190             interval will be as close as possible for an integer number of
191             samples.
192        Returns a tuple (V_avg, V_min, V_max, time_stamp)
193            V_avg   the averaged voltage
194            stdev   estimated standard deviation of the measurements
195            stdev_avg   estimated standard deviation of the mean
196            time_stamp the time at halfway through the averaging interval in
197             seconds since the beginning of the epoch (OS dependent begin
198             time).
199
200        """
201        time_tuple = time.localtime()
202        nearesthr = time.mktime((time_tuple.tm_year, time_tuple.tm_mon,
203                                 time_tuple.tm_mday, time_tuple.tm_hour, 0, 0,
204                                 time_tuple.tm_wday, time_tuple.tm_yday,
205                                 time_tuple.tm_isdst))
206        start = time.time()
207        intercept = (time.time() - nearesthr) / 1800
208        slope = (time.time() - nearesthr) / 692000
209        V = intercept + slope * (time.time() - nearesthr) + (random.random()
210                                                             - 0.5) * slope
211        end = time.time()
212        time_stamp = (start + end) / 2.0
213        return V, time_stamp, self.Vdd

This routine returns the average voltage for the channel averaged at (0.0012 + 1/data_rate)^-1 Hz for avg_sec number of seconds. The 0.0012 is the required loop time on a RPI 3B+ in python3. The voltage is rounded to the number of decimals indicated by the standard deviation. The standard deviation and the estimated deviation of the mean are also returned. Parameters chan the channel number 0, 1, 2, 3 gain 2/3 (+/-6.144V), 1(+/-4.096V), 2(+/-2.048V), 4(+/-1.024V), 8 (+/-0.512V), 16 (+/-0.256V) data_rate the ADC sample rate in Hz (8, 16, 32, 64, 128, 250, 475 or 860 Hz) avg_sec seconds to average for, actual averaging interval will be as close as possible for an integer number of samples. Returns a tuple (V_avg, V_min, V_max, time_stamp) V_avg the averaged voltage stdev estimated standard deviation of the measurements stdev_avg estimated standard deviation of the mean time_stamp the time at halfway through the averaging interval in seconds since the beginning of the epoch (OS dependent begin time).