开发者

best practice for passing values between functions in Python

What is pythonic best practice for allowing one function to use another function's returned values? e.g. Is it better to call one function within another, or better that function1 returns to the class, and cl开发者_StackOverflow中文版ass variables are assigned that are then used by function2? Secondly, how many different ways could you pass values between functions?

class adding:

    def get_values(self):
        x = input("input x")
        y = input("input y")
        z = input("input z")
        return x, y, z

    def use_values(self, x, y, z):
        print x+y+z

if name == 'main':
    dave = adding()
    x, y, z = dave.get_values()
    dave.use_values(x, y, z)

Or

    dave = adding()
    dave.use_values(*dave.get_values())


As import this would say, "explicit is better than implicit"; so go with the first form.

If the number of return values becomes large, let use_value take a sequence argument instead.


All ways are valid and depend completely on your subject domain and the compartmentalisation of functionality, the separation of concerns. In other words, it depends.

For example, you could have a class whose public API has 2 methods that both depend on a 3rd method, that you deem to be private. It is your choice as a developer not to make that 3rd method part of the public API, yet it's there in your source code:

class FooAPI(object):
    def publicMethodOne(*args, **kw):
        return self._privateMethod(1, *args, **kw) + 7

    def publicMethodTwo(*args, **kw):
        return self._privateMethod(2, *args, **kw) + 11

    def _privateMethod(somevalue, *args, **kw):
        return somevalue * 3

In that case, there is absolutely no need for users of your API to call _privateMethod directly and pass it's return value to either publicMethod.

However, if you feel that consumers of your API should provide your method with specific information for which there is an easy default method that could calculate that specific information for them in most cases, you would want to pass in the return value of that default method. That way, those consumers can also use their own method of calculation and use those values instead:

def publicMethod(value1, value2):
    return value1 / value2

def mostCommonValues():
    return (1.0, 4.0)

publicMethod(*mostCommonValues())
publicMethod(4, 2)

And when to use instance variables? Only when the return values of a function are to persist with the instance, when they reflect the internal state of that instance.

For example, if your class represents a car, it may make sense for your application to store the location of the car between operations on that car. So if you want to know if it needs to stop for a traffic light right now, call the updatePosition() method first, then use another method to calculate the distance from the traffic light. You wouldn't pass the output of the updatePosition() call to the distance calculation method, you would just keep the position updated in the instance.

If however, you need to update the position of the car in a collision, you'll need to take data from the car (based on return values from methods called on the car), combined with external information (position of other object, resistance of the road surface, etc.) to feed back into the updatePosition method on the car. Because you now need to add additional information from outside the car instance, you'll have to pass in the values from one method call to the other via your public API.

Remember, software development is more an artform than a strict engineering discipline, and thus the answer as to how to do this varies from developer to developer and from software project to software project. There never is no one answer. Just try to make it explicit and obvious, natural.


I would argue that get_values is not a vital part of adding and should thus be a separate function. If it should be I would say:

class adding:

def get_values(self):
    self.x = input("input x")
    self.y = input("input y")
    self.z = input("input z")

def use_values(self):
    print self.x+self.y+self.z

if name == 'main':
    dave = adding()
    dave.get_values()
    dave.use_values()

is a more sound solution.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜