“内省”预期的功能回报量

时间:2017-07-27 12:58:01

标签: python python-3.x function-calls

大家好,
我目前正在开发一个python模块,为同事提供工具使用,我试图提供的一些函数可以返回相当多的有用信息(例如,5个返回值),但在大多数用例中,只需要前两个。

我知道python非常适合编写高度动态的程序,特别是因为我们可以询问有关当前正在运行的系统的信息,所以我虽然搜索了一下,但我似乎无法找到。 (我发现了很多有趣的讨论,但实际上没有讨论我的问题。)

是否有办法从函数中知道预期回报值的数量?

例如,可能有函数:

def lazyOdd():
    return 1, 3, 5, 7, 9, 11, 13, 15, 17, 19, 21

使用one, three, five = lazyOdd()调用哪个。

编辑:显然它根本不清楚,我寻求的是:

def lazyReturn():
    return (val1, val2) if expectedReturns == 2 else (val1, val2, val3, val4)

我知道在这种情况下,它绝对不是最好的方法,几乎​​任何类型的迭代都可以做,但是根本没有链接的值,它不会那么简单。如果可能的话,因为大多数用例只会使用两个结果,我想避免返回一个大元组,因为许多同事甚至不知道函数返回其他值,这将是非常错误的 - 易发生。

我能这样做吗?

编辑:另外,我不介意解决方案是否包含一些开销,因为我很可能会因为不处理最后三个值而赢得很多时间。

Edit²:也许最好的方法是传递另一个参数来指定预期值的数量?

2 个答案:

答案 0 :(得分:2)

缓存

您的描述很难说明,但似乎您需要caching

这样,您可以编写多个函数。一个用于繁重的计算,其他用于输出正确的格式和值的数量。如果使用相同的输入值第二次调用繁重计算,则返回先前的结果。

from functools import lru_cache

@lru_cache(maxsize=32)
def heavy_common_calculation(x):
    print("HEAVY CALCULATION FOR %d. Should only be done once!" % x)
    result = x**2
    return result

def get_two_values(x):
    return x, heavy_common_calculation(x)

def get_four_values(x):
    y = heavy_common_calculation(x)
    return x, y, y**2, y**3

print(get_two_values(3))
# HEAVY CALCULATION FOR 3. Should only be done once!
# (3, 9)
print(get_four_values(3))
# (3, 9, 81, 729)

发电机

您要实施generator吗?

def lazyOdd():
    x = 1
    while True:
        yield x
        x = x + 2

odd_gen = lazyOdd()
print(next(odd_gen))
# 1
print(next(odd_gen))
# 3
print(next(odd_gen))
# 5
print(next(odd_gen))
# 7

如果您想要一个值,它会被计算出来。如果你不需要它,没有任何事情发生,没有任何东西是徒劳的。

len(odd_gen)未定义,因为它会启动无限循环。

关键字参数

您可以使用参数告诉函数您需要多少结果:

def f(x, detail='low'):
    a, b = x, x**2
    if detail == 'high':
        return a, b, 'something', 'else'
    else:
        return a, b


print(f(3))
# (3, 9)
print(f(3, detail='high'))
# (3, 9, 'something', 'else')

答案 1 :(得分:1)

我不知道你想做什么。由函数返回的元组中元素的数量由函数决定,或者更具体地由编写函数的程序员决定。如果您的同事只对前两个元素感兴趣,他们可以这样做:

one, three, *_ = lazyOdd()

_是一个垃圾变量,用于存储元组的其余部分。