Skip to content

Instantly share code, notes, and snippets.

@zzzeek
Created May 17, 2019 02:28
Show Gist options
  • Save zzzeek/0eb0636fa3917f36ffd887d9f765c208 to your computer and use it in GitHub Desktop.
Save zzzeek/0eb0636fa3917f36ffd887d9f765c208 to your computer and use it in GitHub Desktop.
Python getargspec, getfullargspec, Signature performance comparison
# So interestingly, Signature seems to be twice as fast in Python 3.6 and 3.7 as it
# was in Python 3.3 and 3.4. However, it is still 6-18 times slower than the old
# getargspec or getfullargspec that was in Python 3.3.
Python 2.7 getargspec (doesn't use Signature) : specimen_one (6 args) : 0.0503
Python 2.7 getargspec (doesn't use Signature) : specimen_two (0 args) : 0.0496
Python 2.7 getargspec (doesn't use Signature) : specimen_three (6 args) : 0.0500
Python 2.7 getargspec (doesn't use Signature) : specimen_four (13 args) : 0.0652
Python 3.3 getfullargspec (doesn't use Signature) : specimen_one (6 args) : 0.0539
Python 3.3 getfullargspec (doesn't use Signature) : specimen_two (0 args) : 0.0590
Python 3.3 getfullargspec (doesn't use Signature) : specimen_three (6 args) : 0.0596
Python 3.3 getfullargspec (doesn't use Signature) : specimen_four (13 args) : 0.0568
Python 3.3 signature : specimen_one (6 args) : 0.6158
Python 3.3 signature : specimen_two (0 args) : 0.2562
Python 3.3 signature : specimen_three (6 args) : 0.4190
Python 3.3 signature : specimen_four (13 args) : 0.8836
Python 3.4 signature : specimen_one (6 args) : 0.5991
Python 3.4 signature : specimen_two (0 args) : 0.2798
Python 3.4 signature : specimen_three (6 args) : 0.4509
Python 3.4 signature : specimen_four (13 args) : 0.8818
Python 3.6 signature : specimen_one (6 args) : 0.3167
Python 3.6 signature : specimen_two (0 args) : 0.1298
Python 3.6 signature : specimen_three (6 args) : 0.2366
Python 3.6 signature : specimen_four (13 args) : 0.5633
Python 3.7 signature : specimen_one (6 args) : 0.2447
Python 3.7 signature : specimen_two (0 args) : 0.1301
Python 3.7 signature : specimen_three (6 args) : 0.1784
Python 3.7 signature : specimen_four (13 args) : 0.4597
Python 3.4 getfullargspec (uses Signature internally) : specimen_one (6 args) : 0.7807
Python 3.4 getfullargspec (uses Signature internally) : specimen_two (0 args) : 0.3409
Python 3.4 getfullargspec (uses Signature internally) : specimen_three (6 args) : 0.5325
Python 3.4 getfullargspec (uses Signature internally) : specimen_four (13 args) : 1.2213
Python 3.6 getfullargspec (uses Signature internally) : specimen_one (6 args) : 0.3634
Python 3.6 getfullargspec (uses Signature internally) : specimen_two (0 args) : 0.1247
Python 3.6 getfullargspec (uses Signature internally) : specimen_three (6 args) : 0.2484
Python 3.6 getfullargspec (uses Signature internally) : specimen_four (13 args) : 0.6777
Python 3.7 getfullargspec (uses Signature internally) : specimen_one (6 args) : 0.3142
Python 3.7 getfullargspec (uses Signature internally) : specimen_two (0 args) : 0.1060
Python 3.7 getfullargspec (uses Signature internally) : specimen_three (6 args) : 0.2232
Python 3.7 getfullargspec (uses Signature internally) : specimen_four (13 args) : 0.5562
from __future__ import print_function
def specimens():
def specimen_one(a, b, c=10, d=15):
pass
def specimen_two():
pass
def specimen_three(*args, **kw):
pass
def specimen_four(
argument_one,
argument_two,
argument_three,
argument_four,
argument_five,
argument_six,
argument_seven,
argument_eight=None,
argument_nine=None,
argument_ten=None,
):
pass
return specimen_one, specimen_two, specimen_three, specimen_four
import inspect
import sys
import timeit
def tests():
try:
yield inspect.getfullargspec
except AttributeError:
yield inspect.getargspec
try:
yield inspect.signature
except AttributeError:
pass
def run_tests():
global spec
global test
for test in tests():
for spec in specimens():
time = timeit.timeit(
"test(spec)", "from __main__ import spec, test", number=10000
)
argspec = inspect.getargspec(spec)
header = "Python %s %s%s" % (
".".join(str(x) for x in sys.version_info[0:2]),
test.__name__,
" (uses Signature internally)"
if sys.version_info >= (3, 4)
and test.__name__ == "getfullargspec"
else " (doesn't use Signature)"
if test.__name__ in ("getfullargspec", "getargspec")
else "",
)
header += " " * (54 - len(header))
header = "%s: %s (%s args)" % (
header,
spec.__name__,
sum(
len(element) if element is not None else 0
for element in argspec
),
)
header += " " * (80 - len(header))
print(
"%s: %.4f"
% (
header,
time,
)
)
print("\n")
if __name__ == "__main__":
run_tests()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment