Language: Python
I want the value of a variable to be initialized to zero at the start of the execution. This variable is used in a function & its value may also get changed within the function. But I do not want the value of this variable to reset to zero whenever a function call is made. Instead, its value should be equal to the updated value from its previous function call.
Example:
get_current() is constantly returning a different value when it is called.
ctemp is initially zero.
In the first function call get_current_difference() will return cdiff & then update the value of ctemp such that ctemp = current.
In the second function call, the value of ctemp should not be zero. Instead, it should be equal to the updated value from the first function call.
import serial
arduino = serial.Serial('/dev/ttyACM1',9600)
ctemp = 0
def get_current():
line = arduino.readline()
string = line.replace('\r\n','')
return string
def get_current_difference():
global ctemp
current = get_current()
cdiff = float(current) - ctemp
return cdiff
ctemp = current
while 1:
current = get_current_difference()
print(current)
You return before setting value of ctemp
return cdiff
ctemp = current
must become
ctemp = current
return cdiff
You are describing mutable state and a function to modify it, which is what classes are for.
class Temperature:
def __init__(self, arduino):
self.ctemp = 0
self.arduino = arduino
def current(self):
line = self.arduino.readline()
return line.replace('\r\n', '')
def difference(self):
current = self.current()
cdiff = float(current) - self.ctemp
self.ctemp = current
return cdiff
t = Tempurature(serial.Serial('/dev/ttyACM1', 9600)
while True:
print(t.difference())
Using a class scales if, for example, you have multiple temperature monitors to work with.
Related
I am using Finnhub api to get some live data. I have 2 codes, one which will login the api every once in a day and second one will give the data every hour.
The first function will give details to the second function based on which it will fetch the data.
Here is my first function
def finnhub_login():
finnhub_client = finnhub.Client(api_key="xxxxxxxxxxxx")
symbols = df['SYMBOLS'].to_list()
return symbols,finnhub_client
I would like to use the output i.e symbols and finnhub client to the second function
Here is the second function
def finnhub_api_call(symbols,finnhub_client):
main_value = 0
for i in symbols:
data = finnhub_client.quote(['symbol'])
main_value += data['dp']
return main_value
schedule.every(1).day.do(finnhub_login)
schedule.every(1).hour.do(finnhub_api_call,symbols,finnhub_client)
while True:
schedule.run_pending()
time.sleep(1)
In the above code, how do I save the return values of 1st function and then use it for the second function ?
you can wrap all of this in a class and use class variables.
You can instantiate your class and use the functions from there. Everytime you run the first function class variables will change. Second function will use the class variables instead of function parameters.
class FinnhubCaller:
def __init__(self):
pass
def finnhub_login(self):
self.client = finnhub.Client(api_key="xxxxxxxxxxxx")
self.symbols = df['SYMBOLS'].to_list()
def finnhub_api_call(self):
main_value = 0
for i in self.symbols:
data = self.client.quote(['symbol'])
main_value += data['dp']
return main_value
caller = FinnhubCaller()
schedule.every(1).day.do(caller.finnhub_login)
schedule.every(1).hour.do(caller.finnhub_api_call)
while True:
schedule.run_pending()
time.sleep(1)
I'm wanting to be able to print and update values retrieved from a small GPS in real time. For whatever reason, the code will not update the GPS value, and only prints the same value until I restart the code. My guess is the variable is not able to update, but I wouldn't know how to fix that.
while ser.inWaiting() > 0:
decoded = (ser.read(1).decode)
echo += decoded()
class GPS:
def __init__(self):
#Write GPSinput
out = ''
ser.write(com.GPSstatus.encode())
time.sleep(1)
#Read output
while ser.inWaiting() > 0:
decoded = (ser.read(1).decode)
out += decoded()
strlen = len(str(out))
substr = out[0:strlen-9]
#GPS? information list
variables = substr.splitlines()
#Storing each output in a variable
self.PULSE_SAWTOOTH = [int(s) for s in variables[1] if s.isdigit()]
self.TRACKED_SATELLITES = [int(s) for s in variables[2] if s.isdigit()]
self.VISIBLE_SATELLITES = [int(s) for s in variables[3] if s.isdigit()]
self.LONGITUDE = variables[5]
self.longlen = len(self.LONGITUDE)
self.LONGDEG = self.LONGITUDE[0:self.longlen-7]
self.LONGMIN = self.LONGITUDE[self.longlen-7:]
self.LATITUDE = variables[6]
self.latlen = len(self.LATITUDE)
self.LATDEG = self.LATITUDE[0:self.latlen-7]
self.LATMIN = self.LATITUDE[self.latlen-7:]
self.HEIGHT = variables[7]
self.KNOTS = variables[8]
self.DEGREES = [9]
self.GPS_STATUS = variables[10]
self.TIMING_MODE = variables[17]
self.FIRMWARE_VERSION = variables[20]
if __name__ == "__main__":
#Call the functions
gps = GPS()
for i in range(100):
print(gps.LATITUDE)
#Enterable Parameters
# PULSE_SAWTOOTH
# TRACKED_SATELLITES
# VISIBLE_SATELLITES
# LONGITUDE
# longlen
# LONGDEG
# LONGMIN
# LATITUDE
# latlen
# LATDEG
# LATMIN
# HEIGHT
# KNOTS
# DEGREES
# GPS_STATUS
# TIMING_MODE
# FIRMWARE_VERSION
I'm guessing this is a pretty simple solution, but I'm a beginner and I don't fully understand whats happening enough to fix it. If anyone could shed some knowledge and help with my problem it would be greatly appreciated.
Aside from the while loop indent error and possible decode error. You're getting the same output for print(gps.LATITUDE) every time because you never update it, either by the gps object, or a call to a member function of class GPS. Your initial gps object always has LATITUDE equal to the value variables[6] and if that variable isn't changing, neither will your LATITUDE variable. You have options, you can either update LATITUDE directly:
class GPS:
def __init__(self , latitudeValue = 0):
self.LATITUDE = latitudeValue
if __name__ == "__main__":
gps = GPS()
print(gps.LATITUDE) # Prints 0, default value of latitudeValue
gps.LATITUDE = 5
print(gps.LATITUDE) # Now prints 5, changed value of LATITUDE in gps object
Or you can make it part of a function call:
class GPS:
def __init__(self , latitudeValue = 0):
self.LATITUDE = latitudeValue
def updateLatitude(self , newValue):
self.LATITUDE = newValue
if __name__ == "__main__":
gps = GPS()
print(gps.LATITUDE) # Prints 0
gps.updateLatitude(10) # Updates LATITUDE VALUE
print(gps.LATITUDE) # Prints 10
You can use either method with whatever the value of variables[6] is. Likewise, you can use this with all member variables of your class.
For real-time updating you need to use a event handling function, this scenario possibly calls for a listener. Without knowing more about the device passing data through the bus. If the manufacturer of your device doesn't supply an API to work with, then while you can use a loop to constantly reinitialize an object, another approach is module reloading.
I have designed a function which would take input name from RFID card and prints it. This variable Username is declared global so that I can use it in other functions. Now I want to use this variable in another function which will check if there is value stored in Username or not and performs the corresponding function. At the end of this function this variable should be deleted. so that it takes a new value next time and not use the previous value stored. Therefore I want to delete value stored in my variable so that it can take a new value every time. How can I do this?
def RFID_reading(a,b):
global reader, Username
while True:
Starttime = time.time()
try:
id, Username = reader.read()
print(Username)
def store_unknown(picture_list):
if Username != "":
j=0
while j < len(picture_list):
cv2.imwrite(f'{y}/{picture_list[j][2]}.png', picture_list[j] [0])
j += 1
Username == None
I have tried writing Username == None but it did not work.
Please try using global Username before the last line Username == None. This is to denote that you are aware and going to update the global variable's value.
Id, conf = recognizer.predict(gray[y:y+h,x:x+w]
def hour(cn):
for z in range(9,17):
if now.hour == z:
worksheet(cn, str(z)+":00")
def identify(number):
sht = gc.open("Test")
wks3 = sht.worksheet("NAMES")
b = wks3.acell('B'+str(number)).value
a = wks3.acell('A'+str(number)).value
if(Id == a and conf<65):
print(Id, conf)
Id = str(b)
Time = time.ctime()
hour(number)
elif(conf>64):
print(conf)
Id = "Unknown"
for m in range(2,100):
identify(m)
The above code is being used for facial recognition, I copied what I felt was necessary, it is not the entire code.
I'm trying create a function which I want to call back in a for loop
What am I doing wrong? I've been looking t this for 6 hours now, and anything I try doesn't seem to work.
I get a message back saying "UnboundLocalError: local variable 'Id' referenced before assignment"
It's impossible because I'm assigning with:
a = wks3.acell('A'+str(number)).value
So it grabs the ID number from the google spread sheet and checks if it is equaled to that, can someone tell me where I'm going wrong here?
def identify(number):
sht = gc.open("Test")
wks3 = sht.worksheet("NAMES")
b = wks3.acell('B'+str(number)).value
a = wks3.acell('A'+str(number)).value
#because you did, Id = ?
if(Id == a and conf<65):
print(Id, conf)
Id = str(b)
Time = time.ctime()
hour(number)
elif(conf>64):
print(conf)
Id = "Unknown"
Because you did, variable Id isn't passed as any parameter or global/local variable or as an argument to existing class.
If Id was parameter:
def identify(number,Id):
If Id was global variable:
def identify(number):
global Id
If Id was local variable:
def identify(number):
id = None # or some other data type
And if Id was argument from some class:
some_class.Id
In short you referenced Id before it was initialised. This is rookie mistake and there is some stuff where you can actually init a variable in if elif else statement but you need to trow a none of above logic of the rule.
if True: Id = 2; elif False: Id = 3; else: Id =0 #this is pseudocode, don't paste it in.
Also have in mind that next variable is also Unbound conf
EDIT:
Often to avoid this problem we write code like this:
def somefunction(parm1,parm2... ):
# global variables : description for variable stack is optional
global var1,var2 # if needed
#local variables
var3,var4 = None;
var5 = 'something else'
#in body functions : functions inside functions or just general program functions
def a(... ): return ...
#body : actually what function/program does.
# returning , finishing statement.
I just posted a question about this code, and I am sorry to do it again, but my return statement is not working. Whenever I try to run the code, it asks for a global variable of position, which I am trying to return in the searching method. Any help is appreciated. Thanks.
def main():
names = ['Ava Fischer', 'Bob White', 'Chris Rich', 'Danielle Porter','Gordon Pike', 'Hannah Beauregard', 'Matt Hoyle', 'Ross Harrison', 'Sasha Ricci', 'Xavier Adams']
binarySearch(names, "Ava Fischer")
print("That name is at position "+str(position))
def binarySearch(array, searchedValue):
begin = 0
end = len(array) - 1
position = -1
found = False
while not found and begin<=end:
middle=(begin+end)//2
if array[middle] == searchedValue:
found=True
position = middle
elif array[middle] >searchedValue:
end = middle-1
else:
first = middle+1
return position
At the moment you are calling your function, but just throwing the result away. You don't actually give a value from your function call (you use return just fine):
You want something like:
position = binarySearch(names, "Ava Fischer")
The variable that you are expecting to exist globally is local to the scope of binarySearch. We can get it by assigning a variable to the returned value, like above.
This is a scope issue. In the function binarySearch you are declaring a local variable position, so it is only accessible within that function. Since that function will return a value, you can assign that result to a variable:
position = binarySearch(names, "Ava Fischer")
print("That name is at position " + str(position))