icecream

Python 2025-08-22

icecream - 切勿使用print()再次调试

您是否曾经使用print()或log()调试代码?当然,您会这样做。 icecream或简称IC,使打印调试更甜蜜。

ic()就像print(),但更好:

  1. 它打印了变量和表达式及其值。
  2. 输入快60%。
  3. 数据结构是格式的,并打印出了漂亮的印刷。
  4. 输出突出显示。
  5. 它选择包括程序上下文:文件名,行号和父函数。

icecream经过良好的测试,允许的许可并支持Python 3和PYPY3。

2025-04-26:Big Scoop:我很高兴分享@Jakeroid现在是icecream的维护者! ? icecream的未来刚好甜美。 ?

检查变量

您是否曾经打印过变量或表达方式来调试程序?如果您曾经输入过类似的内容

 print ( foo ( '123' ))

或更彻底的

 print ( "foo('123')" , foo ( '123' ))

然后IC()会在您的脸上露出微笑。有了参数,IC()自我检查并打印了自己的论点和这些参数的价值观。

icecream import ic def foo(i): return i + 333 ic(foo(123))">
 from icecream import ic

def foo ( i ):
    return i + 333

ic ( foo ( 123 ))

印刷

ic| foo(123): 456

相似地,

 d = { 'key' : { 1 : 'one' }}
ic ( d [ 'key' ][ 1 ])

class klass ():
    attr = 'yep'
ic ( klass . attr )

印刷

ic| d['key'][1]: 'one'
ic| klass.attr: 'yep'

只需给IC()一个变量或表达式即可完成。简单的。

检查执行

您是否曾经使用print()来确定程序的哪些部分执行,以及执行的顺序?例如,如果您曾经在调试代码中添加打印语句

 def foo ():
    print ( 0 )
    first ()

    if expression :
        print ( 1 )
        second ()
    else :
        print ( 2 )
        third ()

然后IC()在这里也有帮助。如果没有参数,IC()会检查自身并打印调用文件名,行号和父函数。

icecream import ic def foo(): ic() first() if expression: ic() second() else: ic() third()">
 from icecream import ic

def foo ():
    ic ()
    first ()

    if expression :
        ic ()
        second ()
    else :
        ic ()
        third ()

印刷

ic| example.py:4 in foo()
ic| example.py:11 in foo()

只需致电IC(),您就完成了。简单的。

返回值

IC()返回其参数,因此可以轻松地将IC()插入到预先存在的代码中。

>>> a = 6
>>> def half ( i ):
>>>     return i / 2
>>> b = half(ic(a))
ic| a: 6
>>> ic(b)
ic| b: 3

各种各样的

ic.format(*args)就像ic(),但输出作为字符串返回而不是写入stderr。

icecream import ic >>> s = 'sup' >>> out = ic.format(s) >>> print(out) ic| s: 'sup'">
>>> from icecream import ic
>>> s = ' sup '
>>> out = ic.format(s)
>>> print (out)
ic| s: 'sup'

此外,IC()的输出可以分别与IC.disable()和ic.enable()分别重新启用,然后重新启用。

icecream import ic ic(1) ic.disable() ic(2) ic.enable() ic(3)">
 from icecream import ic

ic ( 1 )

ic . disable ()
ic ( 2 )

ic . enable ()
ic ( 3 )

印刷

ic| 1: 1
ic| 3: 3

当然,IC()在禁用时继续返回其论点;没有IC()中断的现有代码。

导入技巧

要使每个文件中的IC()可用,而无需在每个文件中导入,则可以安装()。例如,在root a.py中:

icecream import install install() from B import foo foo()">
 #!/usr/bin/env python3
# -*- coding: utf-8 -*-

from icecream import install
install ()

from B import foo
foo ()

然后在由A.Py进口的B.Py中,只需致电IC():

 # -*- coding: utf-8 -*-

def foo ():
    x = 3
    ic ( x )

install()将IC()添加到内置模块,该模块在解释器导入的所有文件中共享。同样,IC()稍后也可以卸载()ed。

如果未安装icecream ,则可以以优雅失败的方式导入IC(),例如在生产环境中(即不开发)。为此,本次后备导入片段可能有用:

icecream import ic except ImportError: # Graceful fallback if icecream isn't installed. ic = lambda *a: None if not a else (a[0] if len(a) == 1 else a) # noqa">
 try :
    from icecream import ic
except ImportError :  # Graceful fallback if icecream isn't installed.
    ic = lambda * a : None if not a else ( a [ 0 ] if len ( a ) == 1 else a )  # noqa

配置

IC.ConfigureOutput(前缀,输出函数,argtoStringFunction,includeContext,contextAbspath)控制IC()的输出。

前缀(如果提供)采用自定义输出前缀。前缀可以是字符串,例如

icecream import ic >>> ic.configureOutput(prefix='hello -> ') >>> ic('world') hello -> 'world'">
>>> from icecream import ic
>>> ic.configureOutput( prefix = ' hello -> ' )
>>> ic( ' world ' )
hello -> 'world'

或功能。

icecream import ic >>> >>> def unixTimestamp(): >>> return '%i |> ' % int(time.time()) >>> >>> ic.configureOutput(prefix=unixTimestamp) >>> ic('world') 1519185860 |> 'world': 'world'">
>>> import time
>>> from icecream import ic
>>>  
>>> def unixTimestamp ():
>>>     return ' %i |> ' % int (time.time())
>>>
>>> ic.configureOutput( prefix = unixTimestamp)
>>> ic( ' world ' )
1519185860 |> 'world': 'world'

前缀的默认值是IC | 。

输出功能(如果提供),则以IC()的输出为字符串,而不是写入stderr(默认值)的每个IC()呼叫一次。

icecream import ic >>> >>> def warn(s): >>> logging.warning("%s", s) >>> >>> ic.configureOutput(outputFunction=warn) >>> ic('eep') WARNING:root:ic| 'eep': 'eep'">
>>> import logging
>>> from icecream import ic
>>>
>>> def warn ( s ):
>>>     logging.warning( " %s " , s)
>>>
>>> ic.configureOutput( outputFunction = warn)
>>> ic( ' eep ' )
WARNING:root:ic| 'eep': 'eep'

如果提供了ArgToStringFunction,则将参数值序列化为可显示字符串。默认值是PrettyPrint的pprint.pformat(),但可以将其更改为例如以自定义方式处理非标准数据类型。

icecream import ic >>> >>> def toString(obj): >>> if isinstance(obj, str): >>> return '[!string %r with length %i!]' % (obj, len(obj)) >>> return repr(obj) >>> >>> ic.configureOutput(argToStringFunction=toString) >>> ic(7, 'hello') ic| 7: 7, 'hello': [!string 'hello' with length 5!]">
>>> from icecream import ic
>>>
>>> def toString ( obj ):
>>>    if isinstance (obj, str ):
>>>        return ' [!string %r with length %i !] ' % (obj, len (obj))
>>>    return repr (obj)
>>>
>>> ic.configureOutput( argToStringFunction = toString)
>>> ic( 7 , ' hello ' )
ic| 7: 7, 'hello': [!string 'hello' with length 5!]

默认的ArgToStringFunction是icecream .ArgumentTostring,并且具有使用Functool.SingledIsPatch派遣和未注册的函数进行注册和未注册函数。它还具有注册属性以查看注册功能。

icecream import ic, argumentToString >>> import numpy as np >>> >>> # Register a function to summarize numpy array >>> @argumentToString.register(np.ndarray) >>> def _(obj): >>> return f"ndarray, shape={obj.shape}, dtype={obj.dtype}" >>> >>> x = np.zeros((1, 2)) >>> ic(x) ic| x: ndarray, shape=(1, 2), dtype=float64 >>> >>> # View registered functions >>> argumentToString.registry mappingproxy({object: <function icecream . icecream .argumentToString(obj)>, numpy.ndarray: <function __main__._(obj)>}) >>> >>> # Unregister a function and fallback to the default behavior >>> argumentToString.unregister(np.ndarray) >>> ic(x) ic| x: array([[0., 0.]])">
>>> from icecream import ic, argumentToString
>>> import numpy as np
>>>
>>> # Register a function to summarize numpy array
>>> @ argumentToString.register(np.ndarray)
>>> def _ ( obj ):
>>>     return f " ndarray, shape= { obj.shape } , dtype= { obj.dtype } "
>>>
>>> x = np.zeros(( 1 , 2 ))
>>> ic(x)
ic| x: ndarray, shape=(1, 2), dtype=float64
>>>
>>> # View registered functions
>>> argumentToString.registry
mappingproxy({object: <function icecream . icecream .argumentToString(obj)>,
              numpy.ndarray: <function __main__._(obj)>})
>>>
>>> # Unregister a function and fallback to the default behavior
>>> argumentToString.unregister(np.ndarray)
>>> ic(x)
ic| x: array([[0., 0.]])

includeContext(如果提供),并且将IC()呼叫的文件名,行号和父函数添加到IC()的输出中。

icecream import ic >>> ic.configureOutput(includeContext=True) >>> >>> def foo(): >>> i = 3 >>> ic(i) >>> foo() ic| example.py:12 in foo()- i: 3">
>>> from icecream import ic
>>> ic.configureOutput( includeContext = True )
>>>
>>> def foo ():
>>>   i = 3
>>>   ic(i)
>>> foo()
ic| example.py:12 in foo()- i: 3

默认情况下,IncludeContext是错误的。

contextabspath(如果提供且真实),则输出绝对的filepath,例如/path/path/foo.py,在诸如foo.py之类的fileAnames上,当inc(Incl.ycontext == true)调用ic(iC())时。当调试共享相同文件名的多个文件时,这很有用。此外,某些编辑器(例如VSCODE)将绝对文件放置为单击的链接,这些链接打开了调用IC()的文件。

icecream import ic >>> ic.configureOutput(includeContext=True, contextAbsPath=True) >>> >>> i = 3 >>> >>> def foo(): >>> ic(i) >>> foo() ic| /absolute/path/to/example.py:12 in foo()- i: 3 >>> >>> ic.configureOutput(includeContext=True, contextAbsPath=False) >>> >>> def foo(): >>> ic(i) >>> foo() ic| example.py:18 in foo()- i: 3">
>>> from icecream import ic
>>> ic.configureOutput( includeContext = True , contextAbsPath = True )
>>>
>>> i = 3
>>>
>>> def foo ():
>>>   ic(i)
>>> foo()
ic| /absolute/path/to/example.py:12 in foo()- i: 3
>>>
>>> ic.configureOutput( includeContext = True , contextAbsPath = False )
>>>
>>> def foo ():
>>>   ic(i)
>>> foo()
ic| example.py:18 in foo()- i: 3

默认情况下,ContextAbSpath是错误的。

如果要使用多个日志级别的icecream ,例如使用Python的日志记录模块,则可以使用ic.format()将icecream的调试与Logger集成:

icecream import ic foo = 'bar' logging.debug(ic.format(foo))">
 import logging
from icecream import ic

foo = 'bar'
logging . debug ( ic . format ( foo ))

❕这有点笨拙。您是否更喜欢icecream中的内置日志级别支持?如果是这样,请分享您的想法。

安装

使用PIP安装icecream很容易。

$ pip install icecream

相关的Python库

IC()使用@AlexMoJaki执行,可在Python源中可靠地找到IC()调用。这是魔术。

其他语言的icecream

每种语言都应享受美味的icecream 。

  • 飞镖: icecream
  • 锈: icecream -rs
  • node.js:node- icecream
  • C ++: icecream -CPP
  • C99: icecream -C
  • PHP: icecream -PHP
  • 去: icecream -Go
  • Ruby:r icecream
  • Java: icecream -Java
  • R: icecream
  • lua: icecream -Lua
  • clojure(脚本): icecream -cljc
  • bash: icecream -bash
  • SystemVerilog: icecream _SV

如果您想要使用您喜欢的语言的类似IC()函数,请打开“拉”请求! icecream的目标是用每种语言中的方便的iC()功能加甜打印调试。

下载源码

通过命令行克隆项目:

git clone https://github.com/gruns/icecream.git