Python Forum

Full Version: Can my program be simplified?
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Hi All,
I have writen (read stole, modified from others, etc.) this program.
Now that it works reasonably well i was thinking that it may be simplified, restructured or modularized.
Specifically lines 84 to 99, 101 to 116, 156 to 175 which are sort of repetitions.

#!/usr/bin/env python

#====================================================================================
#
#    Version 2.4; 14/07/2018
#    This program read temps and water level sensors and stores the
#    results in a CSV file on HD. Its to be used in a electrically(solar) driven boat.
#    Some results on two 2004 lcd's.
#    All print() statements are for diagnostic purposes.
#    SB stands for starbord, BB for port side of a boat
#
#====================================================================================

#    Import required libs.
import sys
import time
import csv
import os
import spidev
import RPi.GPIO as GPIO
import I2C_LCD_driver_twoLCD   # I2C_LCD_driver.py modified to accept an address as parameter
                               # so i can use two lcd's.

#    Set variables and GPIO pins.
mylcd1 = I2C_LCD_driver_twoLCD.lcd(0x26)
mylcd2 = I2C_LCD_driver_twoLCD.lcd(0x27)

spi = spidev.SpiDev()
spi.open(0,0)

GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(22,GPIO.IN, pull_up_down = GPIO.PUD_DOWN)
GPIO.setup(27,GPIO.OUT)
GPIO.setup(23,GPIO.OUT)
GPIO.setup(24,GPIO.OUT)
GPIO.setup(25,GPIO.OUT)

#    Function to read MCP3008 with sensorid as channel nbr.
def read_MCP(sensorid):
        adc = spi.xfer2([1,(8+sensorid)<<4,0],20000)
        adcread = ((adc[1]&3) << 8) + adc[2]
        return adcread

#    Function to read the ds18b20 sensor.
def read_ds18b20(sensorid):     
        device = "/sys/bus/w1/devices/"+ sensorid +"/w1_slave"
        try:
            with open (device) as tfile:
                text = tfile.read()
        except FileNotFoundError:
            GPIO.output(25,True)   # Turn on GPIO25 with FileNotFound LED to indicate ID not present.
            notemp = 9999
            return notemp
        sensor_data =text.split(" ")[20]   # Extract and format the temp. from rcvd data.
        temp_raw = float(sensor_data[2:])
        temp = temp_raw / 1000
        return digitemp
    

GPIO.output(25,False)    # Reset FileNotFound LED

while True:
    
    datum = (time.strftime('%d/%m/%Y'))
    tijd = (time.strftime('%H:%M:%S'))

    while True:

       datum = (time.strftime('%d/%m/%Y'))
       tijd = (time.strftime('%H:%M:%S'))

#    Checks for main switch on or off
       time.sleep(1)
       if GPIO.input(22):           # Key is ON.
            GPIO.output(27,True)    # Turn on LED indicator.
            break
       else:                        # Key is OFF.
            GPIO.output(27,False)   # Turn off LED indicator.
#            print ('Schakelaar is UIT')

#    Check water level with key off.

#    Check watersensor SB, channel 0 van MCP.         
            level = read_MCP(0)
            level_SB = round(level,1)
#            print (level_SB ,'SB')
            
#    Turns on SB pump by comparing read value to fixed variable.
            if (level_SB) > 590:
                GPIO.output(23,GPIO.HIGH)    # Pump relay SB ON.
                mylcd1.lcd_display_string('SB pomp actief',4)   # Display text on SB lcd line 4.
                pompSB = ('SB pomp ON')   # define variable pompSB.
#                print (pompSB)
            else:
                GPIO.output(23,GPIO.LOW)     # pump relay SB OFF.
                pompSB = ('SB pomp OFF')
#                print (pompSB)
                mylcd1.lcd_display_string('                    ',4)    # Clear line 4 of SB lcd

#    Check watersensor SB, channel 1 van MCP. 
            level = read_MCP(1)
            level_BB = round(level,1)
#            print (level_BB ,'BB')
            
#    Turns on SB pump by comparing read value to fixed variable.
            if (level) > 450:
                GPIO.output(24,GPIO.HIGH)    # Pump relay BB ON.
                mylcd2.lcd_display_string('BB pomp actief',4)   # Display text on BB lcd line 4.
                pompBB = ('BB pomp ON')
#                print (pompBB)
            else:
                GPIO.output(24,GPIO.LOW)     # Pump relay BB OFF.
                pompBB = ('BB pomp OFF')
#                print (pompBB)
                mylcd2.lcd_display_string('                    ',4)    # Clear line 4 of BB lcd.
                
#    Write pump status to file.
            pompstat = [datum,tijd,pompSB,pompBB]
            csvfile = "/home/pi/programs/testdata.csv"
            with open (csvfile,'a') as output:
                writer = csv.writer(output, delimiter = ',' ,lineterminator = '\n')
                writer.writerow(pompstat)
                
#    Execute the ds18b20 function for defined ID's.
    temp1 = float(read_ds18b20('28-000009adc801'))      #Motor 1#
    temp2 = float(read_ds18b20('28-000009adc801'))      #Motor 2
    temp3 = float(read_ds18b20('28-000009adc801'))      #Buiten temperatuur

#    xxxadc801 is  temporary the only sensor.

#   Read MCP3008 ch0 to ch7.
    lijst = []
    for offset in range(0,8):
        adcread = read_MCP(offset)
#        print (adcread)
        lijst.append(adcread)
        
    data = [datum,tijd,temp1,temp2,temp3,round(lijst[0],1),round(lijst[1],1),
            round((((lijst[2]*3.3/1024)-0.52)/0.08),1),
            round((((lijst[3]*3.3/1024)-0.52)/0.08),1),round(((lijst[4]*330/1024)-50),1)]

#=========================================================
#
#    'temp1' is temparatuur motor SB.
#    'temp2' is temperatuur motor BB
#    'temp3' is not used
#    'lijst[0]' is watersensor SB.
#    'lijst[1]' is watersensor BB.
#    'lijst[2]' is accustroom SB.
#    'lijst[3]' is accustroom BB.
#    'lijst[4]' is buiten temperatuur met TMP36.
#
#=========================================================
#    Turns on SB pump by comparing read value to fixed variable.
    if (lijst[0]) > 510:
        GPIO.output(23,GPIO.HIGH)       # Pump relay SB ON.
        mylcd1.lcd_display_string('SB pomp actief',4)
        pompSB = ('SB pomp ON')
#        print (pompSB)
        mylcd1.lcd_display_string('SB pomp actief',4)
    else:
        GPIO.output(23,GPIO.LOW)        # Pump relay SB OFF.
        mylcd1.lcd_display_string('                    ',4)    # Clear line 4 of SB lcd.

#    Turns on BB pump by comparing read value to fixed variable.
    if (lijst[1]) > 510:
        GPIO.output(24,GPIO.HIGH)       # Pump relay BB ON.
        mylcd2.lcd_display_string('BB pomp actief',4)
        pompBB = ('BB pomp ON')
#        print (pompBB)
    else:
        GPIO.output(24,GPIO.LOW)        # Pum relay BB OFF.
        pompBB = ('BB pomp OFF')
        mylcd2.lcd_display_string('                    ',4)    # Clear line 4 of BB lcd.
        
#    Clear both lcd's lines 1 to 3.   
    mylcd1.lcd_display_string('                    ',1)
    mylcd2.lcd_display_string('                    ',1)
    mylcd1.lcd_display_string('                    ',2)
    mylcd2.lcd_display_string('                    ',2)    
    mylcd1.lcd_display_string('                    ',3)
    mylcd2.lcd_display_string('                    ',3)

#blinks temp if > limit
    
    if  int(temp1) > 25:
        for i in range(1,5):
            mylcd1.lcd_display_string('BB motor='+str(temp1)+chr(223)+'C',1)
            time.sleep(1)
            mylcd1.lcd_clear()
            time.sleep(1)
            
    mylcd2.lcd_display_string('BB motor='+str(temp1)+chr(223)+'C',1)
    mylcd1.lcd_display_string('SB motor='+str(temp2)+chr(223)+'C',1)
    mylcd1.lcd_display_string('Outside='+str(round((lijst[4]*330/1024)-50,1))+chr(223)+'C',3)

#    print (data)

#    Write output naar csv file
#    csvfile = "/home/pi/programs/testdata.csv"
    csvfile = "/media/pi/Seagate Portable/testdata.csv"
    with open (csvfile,'a') as output:
        writer = csv.writer(output, delimiter = ',' ,lineterminator = '\n')
        writer.writerow(data)
        
#    time.sleep(2)
Can i rewrite those sections as a single function that i can reuse.
I did some trying but i stumble over the number of variables that is required to do the jobs.

If you spot something else that look like beginners rubbish to you i would gladly receive your
scoldings in exchange for improvementsTongue

In essence: would you please review my program and comment.

Regards and thanks in advance,
Steffen