You need to distinguish between classes and instances. Once you have defined TimeCounter as a class, you can create one or many instances of it. This is done below in the assignment tc = TimeCounter(), which creates a fresh instance of TimeCounter and assigns it to the variable tc.
When methods (functions) are called on instances of a class, the instance is passed to the method as a parameter, traditionally called self. So when the code below calls tc.startTime(), the self parameter in startTime will refer to the tc instance. Also, when startTime sets self.start_time_of_the_script, it is creating a new property of the tc instance - which is then read again in endTime.
import time
import datetime
class TimeCounter: # Parentheses not necessary
def startTime(self): # Note self parameter
self.start_time_of_the_script = time.time() # Set a property of the instance
def endTime(self): # Note self parameter
end_time_of_the_script = time.time() # This is a local variable
process_time_in_seconds = end_time_of_the_script - self.start_time_of_the_script
print(datetime.timedelta(seconds=process_time_in_seconds))
def main():
tc = TimeCounter() # Create a fresh instance of TimeCounter and assign to tc
tc.startTime() # Call method startTime on the tc instance
tc.endTime()
main()