drled
drled

Reputation: 149

How to check if a variable's value has changed

If I have a variable:

var = 5

I want to detect and jump to a function when the value of the variable changes, so if var is not equal to the value it was before, I want to jump to a function.

What is the easiest way to do this?

Another example:

from datetime import datetime
import time


def dereferentie():
    currentMinute = datetime.now().minute
    checkMinute(currentMinute)

def checkMinute(currentMinute):

    #if currentMinute has changed do:
        printSomething()

def printSomething():
    print "Minute is updated"


def main():
    while (1):
        dereferentie()


if __name__ == '__main__':
    main()

Upvotes: 9

Views: 46516

Answers (3)

trophallaxis
trophallaxis

Reputation: 115

Building on @HelloWorld's answer and @drIed's comment: A nice way would be, to wrap this into a class.

For example:

class Watcher:
    """ A simple class, set to watch its variable. """
    def __init__(self, value):
        self.variable = value
    
    def set_value(self, new_value):
        if self.variable != new_value:
            self.pre_change()
            self.variable = new_value
            self.post_change()
    
    def pre_change(self):
        pass # do stuff before variable is about to be changed
        
    def post_change(self):
        pass # do stuff right after variable has changed
        

Upvotes: 5

Adonis Gaitatzis
Adonis Gaitatzis

Reputation: 3729

A great way is to use the @property and @.setter decorators.

class MyClass:
    @property
    def property_name(self):
        return self.some_value

    @property_name.setter
    def property_name(self, new_value):
       self.some_value = new_value

obj = MyClass()
obj.property_name = "New Value"
stored_value = obj.property_name

By the way this is one of my favorite features in Python.

Original Poster Here's how I would implement your example.

from datetime import datetime

class TimeManager:
    # The actual variable holding data
    # You don't need to declare it, but I like to
    _current_minute = None

    @property
    def current_minute(self):
        """Retrieve the local variable value."""
        return self._current_minute
    @current_minute.setter

    @current_minute.setter
    def current_minute(self, value):
        """Same method name, but set the local variable."""
        self._current_minute = value
        print("Minute has updated to {}".format(self._current_minute))

    @current_minute.deleter
    def current_minute(self):
        """You can also delete variables."""
        del self._current_minute


def main():
    # Create the class
    time_manager = TimeManager()
    for i in range(100):
        current_minute = datetime.now().second
        # set the .currrent_minute using a @property
        time_manager.current_minute = current_minute


if __name__ == '__main__':
    main()

Upvotes: 2

HelloWorld
HelloWorld

Reputation: 1863

I would go with a setter function which triggers your needed function.

def setValue(val):
    global globalVal
    valueChanged= g_val != val
    if valueChanged:
        preFunction()
    globalVal = val
    if valueChanged:
        postFunction()

Upvotes: 3

Related Questions