当传递集合{1}作为参数时,百分比的特殊错误



我遇到了timeit魔术函数的奇怪行为。

def f(S):
    for x in S:
        pass
%timeit f({3})

提出TypeError: 'int' object is not iterable

这是%timeit f(set([3]))时作品,并且 %timeit f({1,2})作品。

为什么会发生?

ah,您正在击中Magics的边缘情况之一,$variable{variable}是为了插入Python变量。也就是说,{foo}将被str(foo)的值所取代。这对于外壳执行很有用,例如%bash rm {myfile}。要说服自己,请使用-n1 -r1运行时间(仅运行一个循环-r1,一次-n1),然后打印S

In [1]: def f(S):
  ...:     print(S)
  ...:
  ...: %timeit -r1 -n1  f({3})
3
92.6 µs ± 0 ns per loop (mean ± std. dev. of 1 run, 1 loop each)

哦,我们得到了3而不是{3} ....解决方案,双 {}

In [2]: def f(S):
  ...:     print(S)
  ...:
  ...: %timeit -r1 -n1  f({{3}})
{3}
25.9 µs ± 0 ns per loop (mean ± std. dev. of 1 run, 1 loop each)

很好!让我们修复您的示例:

In [3]: def f(S):
  ...:     for x in S:
  ...:         pass
  ...: %timeit f({{3}})
234 ns ± 3.3 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

您可以在https://github.com/ipython/ipython上打开一个错误,我敢肯定,如果有足够的抱怨,我们可能会在某个时候改变行为;或至少记录它。它可能是由{3}触发的,而不是{1,2}触发的,因为{3}{foo}一样是"括号 - 识别器 - 托架",但{1,2}不是。

请注意,如果您完全理解此答案,则可以使用{k}将选项传递给时间IT本身:

In [4]: r=1
   ...: n=2
   ...: %timeit -n{n} -r{r} 1+1
292 ns ± 0 ns per loop (mean ± std. dev. of 1 run, 2 loops each)

最新更新