如何将来自不同函数的两个局部变量加在一起?

时间:2016-01-07 18:33:43

标签: python function variables local user-defined-functions

我试图编写一个程序来计算生产蛋糕需要多少成分,然后将这些成分加在一起计算总需要多少成分。

chocCupcake = int(input("How many chocolate cupcakes would you like to make? "))
lemonDrizzle = int(input("How many lemon drizzle cakes would you like to make? "))


def chocolate_cupcake():
    plainFlour = 12
    sugar = 14
    unsaltButter = 4
    freeRangeEgg = 0.1

    totalFlour = float(plainFlour * chocCupcake)
    totalSugar = float(sugar * chocCupcake)
    totalButter = float(unsaltButter * chocCupcake)
    totalEggs = float(freeRangeEgg * chocCupcake)

    print("""You will need:
"""+str(totalFlour)+""" grams of plain flour
"""+str(totalSugar)+""" grams of sugar
"""+str(totalButter)+""" grams of unsalted butter
"""+str(totalEggs)+" free range eggs ")

chocolate_cupcake()



def lemon_drizzle():
    plainFlour = 240
    sugar = 300
    unsaltButter = 80
    freeRangeEgg = 4.5

    totalFlour = float(plainFlour * lemonDrizzle)
    totalSugar = float(sugar * lemonDrizzle)
    totalButter = float(unsaltButter * lemonDrizzle)
    totalEggs = float(freeRangeEgg * lemonDrizzle)

    print("""You will need:
"""+str(totalFlour)+""" grams of plain flour
"""+str(totalSugar)+""" grams of sugar
"""+str(totalButter)+""" grams of unsalted butter
"""+str(totalEggs)+" free range eggs ")

lemon_drizzle()

所以我需要将两种功能的总面粉加在一起,以及总糖等等。

3 个答案:

答案 0 :(得分:1)

有很多不同的方法可以做到这一点,因为它主要是一个重构问题。在我看来,最简单的方法是将这些成分作为每个函数的结果返回:

def chocolate_cupcake():
    ...
    return [totalFlour, totalSugar, totalButter, totalEggs]

然后在调用时为每个函数存储此信息

chocolate_ingredients = chocolate_cupcake()
lemon_drizzle_ingredients = lemon_drizzle()

然后你可以添加它们

print "Total Flour: " + (chocolate_ingredients[0] + lemon_drizzle_ingredients[0])
...etc

只是要添加一个警告,虽然方法要求最少改变现有代码,但它绝对不是最好的方法。这不是最容易理解的。一个例子是配方方法以随机顺序返回成分列表的原因。

答案 1 :(得分:0)

你现在编写代码的方式 - 不可能做到这一点。局部变量是本地变量。它们属于函数,并不存在于函数之外。

你应该以不同的方式解决问题。您可以将它们存储在数据结构(例如地图)中,而不是将成分存储在函数内部(我只显示了两种成分):

ingredients = {"chocolate_cupcake": {"plainFlour": 12, "sugar": 14}, "lemon_drizzle": {"plainFlour": 240, "sugar": 300}}

然后获取一些蛋糕的成分是字典理解的简单问题:

choc_ingredients = {item: num_choc * required for item, required in ingredients["chocolate_cupcake"].items()}
lemon_ingredients = {item: num_lemon * required for item, required in ingredients["lemon_drizzle"].items()}

你可以使用zip添加它们:

total_ingredients = {x[0][0]: x[0][1] + x[1][1] for x in zip(choc_ingredients.items(), lemon_ingredients.items())}

如果你是初学者,这里有很多新东西,但这些方法对Python来说非常重要,所以你一定要研究它们。

答案 2 :(得分:0)

您正在寻找带有类的面向对象设计(OOP - 面向对象编程)。字典或namedtuple方法可能是最简单,最适合您的项目。

OOP非常强大且很有用。我将向您展示一些您可以用课程做的更高级的事情。你可以让类使用python运算符+, - ,/,*等http://rafekettler.com/magicmethods.html

示例:

    import collections

class Ingredients(collections.OrderedDict):
    """List of ingredients with their amounts.

    You could customize this more to force each key to have a unit.
    You could also create your own Ingredient class that has a unit and
    force every value in this dictionary to be an Ingredient with the
    __setitem__ magic method.
    """
    def __init__(self, items):
        super().__init__(sorted(items)) # sort the items

        # Remove name
        if "name" in self:
            self.pop("name")

        # Force servings as the first item
        if "servings" not in self:
            self["servings"] = 1
        self.move_to_end("servings", last=False)
    # end Constructor

    def __str__(self):
        """Return the string representation."""
        return ", ".join((key+": "+str(self[key]) for key in self))
# end class Ingredients


class Cake(object):
    """Create a cake."""
    def __init__(self, number=1):
        super().__init__()

        self.name = "Cake"
        self.servings = 1

        self.init_ingredients()

        if number > 1:
            self *= number

    def init_ingredients(self):
        """Initialize ingredients."""
        self.flour = 240
        self.sugar = 300
    # end init_ingredients

    def ingredients(self):
        """Return a copy of the ingredients."""
        # self.__dict__ contains all of the users variables
        return Ingredients(self.__dict__.items())
    # end ingredients

    def update_ingredients(self, other):
        """Update the ingredients values from a dictionary."""
        self.__dict__.update(other)
    # end update_ingredients

    def show_ingredients(self):
        ingred = str(self).replace(", ", "\n")
        print(ingred)
    # end show_ingredients

    def __str__(self):
        return self.name +", "+ str(self.ingredients())
    # end __str__

    def __add__(self, other):
        """Add the total number of ingredients. Uses + operator (mycake + 2)."""
        if not isinstance(other, Cake):
            raise TypeError

        # Add ingredients
        ingredients = self.ingredients()
        otheri = other.ingredients()
        for key in otheri:
            try:
                ingredients[key] = ingredients[key] + otheri[key]
            except KeyError:
                ingredients[key] = otheri[key]                

        # Edit the name?
        ingredients["name"] = self.name
        if other.name not in self.name:
            ingredients["name"] = self.name + " & " + other.name

        new_cake = self.__class__()
        new_cake.update_ingredients(ingredients)
        return new_cake
    # end __add__

    def __iadd__(self, other):
        """Add and store."""
        ingredients = self + other
        self.update_ingredients(ingredients) 
        return self
    # end __iadd__

    def __imul__(self, other):
        """multiply and store. Uses * operator (mycake *= 2)."""
        ingredients = self.ingredients()
        for key in ingredients:
            ingredients[key] *= other
        self.update_ingredients(ingredients)
        return self
    # end __imul__

    def __mul__(self, other):
        """Copy and return the multiplied value. Uses * operator (mycake * 2)."""
        new_cake = self.__class__()
        new_cake.update_ingredients(self.ingredients())
        new_cake *= other
        return new_cake
    # end __mul__

    def __rmul__(self, other):
        """Copy and return the multiplied value. Uses * operator (2 * mycake)."""
        return self.__mul__(other)
    # end __rmul__
# end class Cake


class ChocolateCupcake(Cake):
    """Create chocolate cupcakes."""
    def init_ingredients(self):
        """Initialize ingredients."""
        super().init_ingredients() # Cake.init_ingredients(self)
        self.name = "Chocolate Cupcakes"
        self.servings = 12
        self.flour = 12
        self.sugar = 14
        self.chocolate_chips = 8
    # end init_ingredients
# end class ChocolateCupcake


mycake = Cake()
print(mycake*2)
print(mycake)
mycake *= 3
print()
mycake.show_ingredients()

choco = ChocolateCupcake(2)
print()
choco.show_ingredients()
print()
print("Total Ingredients", mycake+choco)
print()
both = mycake + choco
both.show_ingredients()