inspect.isfunction doesn't work for all modules?
Question: I'm attempting to use the answer to [Is it possible to list all functions in a
module?](http://stackoverflow.com/questions/4040620/is-it-possible-to-list-
all-functions-in-a-module) to list functions in a range of modules. But in my
interpreter I get as follows:

    
    
    Python 3.3.2 (v3.3.2:d047928ae3f6, May 16 2013, 00:03:43) [MSC v.1600 32 bit (In
    tel)] on win32
    Type "help", "copyright", "credits" or "license" for more information.
    >>> import inspect
    >>> import math
    >>> math.pow(5,4)
    625.0
    >>> inspect.getmembers(math, inspect.isfunction)
    []
    >>> inspect.getmembers(inspect, inspect.isfunction)
    [('_check_class', <function _check_class at 0x00C9F9C0>), ('_check_instance', <f
    unction _check_instance at 0x00C9F978>), ('_get_user_defined_method', <function
    _get_user_defined_method at 0x00C9FB70>), ('_getfullargs', <function _getfullarg
    s at 0x00C6A4F8>), ('_is_type', <function _is_type at 0x00C9FA08>), ('_missing_a
    rguments', <function _missing_arguments at 0x00C9F198>), ('_shadowed_dict', <fun
    ction _shadowed_dict at 0x00C9FA50>)... foo, bar, etc]
    
    >>> math
    <module 'math' (built-in)>
    >>> inspect
    <module 'inspect' from 'E:\\Python33\\lib\\inspect.py'>
    
    >>> import win32api
    >>> inspect.getmembers(win32api, inspect.isfunction)
    []
    >>> win32api
    <module 'win32api' from 'E:\\Python33\\lib\\site-packages\\win32\\win32api.pyd'>
    

As per usual, I assume there's some blindingly obvious reason as to why this
is failing to list all functions in half the modules I try. The best I can
guess is isfunction() only works for .py modules? If there is an innate
problem not related to my stupidity, is there a way to rectify this matter?

It's clearly an issue with the isfunction(), as getmembers seems to work fine:

    
    
    >>> import math
    >>> import inspect
    >>> inspect.getmembers(math)
    [('__doc__', 'This module is always available.  It provides access to the\nmathe
    matical functions defined by the C standard.'), ('__loader__', <class '_frozen_i
    mportlib.BuiltinImporter'>), ('__name__', 'math'), ('__package__', ''), ('acos',
     <built-in function acos>), ('acosh', <built-in function acosh>), ('asin', <buil
    t-in function asin>)... foo, bar, etc]
    

I understand there's a dir() which can be used, but it's not really quite as
neat.


Answer: C-defined functions are not instances of the user-defined `function` type;
they are defined in C instead, for which you _could_ use
[`inspect.isbuiltin()`](http://docs.python.org/2/library/inspect.html#inspect.isbuiltin).

The fool-proof method to list all functions in modules is to use
[`inspect.isroutine()`](http://docs.python.org/2/library/inspect.html#inspect.isroutine)
instead:

> Return true if the object is a user-defined or built-in function or method.

Demo on the `math` module:

    
    
    >>> import inspect
    >>> import math
    >>> inspect.getmembers(math, inspect.isroutine)
    [('acos', <built-in function acos>), ('acosh', <built-in function acosh>), ('asin', <built-in function asin>), ('asinh', <built-in function asinh>), ('atan', <built-in function atan>), ('atan2', <built-in function atan2>), ('atanh', <built-in function atanh>), ('ceil', <built-in function ceil>), ('copysign', <built-in function copysign>), ('cos', <built-in function cos>), ('cosh', <built-in function cosh>), ('degrees', <built-in function degrees>), ('erf', <built-in function erf>), ('erfc', <built-in function erfc>), ('exp', <built-in function exp>), ('expm1', <built-in function expm1>), ('fabs', <built-in function fabs>), ('factorial', <built-in function factorial>), ('floor', <built-in function floor>), ('fmod', <built-in function fmod>), ('frexp', <built-in function frexp>), ('fsum', <built-in function fsum>), ('gamma', <built-in function gamma>), ('hypot', <built-in function hypot>), ('isinf', <built-in function isinf>), ('isnan', <built-in function isnan>), ('ldexp', <built-in function ldexp>), ('lgamma', <built-in function lgamma>), ('log', <built-in function log>), ('log10', <built-in function log10>), ('log1p', <built-in function log1p>), ('modf', <built-in function modf>), ('pow', <built-in function pow>), ('radians', <built-in function radians>), ('sin', <built-in function sin>), ('sinh', <built-in function sinh>), ('sqrt', <built-in function sqrt>), ('tan', <built-in function tan>), ('tanh', <built-in function tanh>), ('trunc', <built-in function trunc>)]
    

Note the `built-in` part of the string representation of each function object.

`isroutine()` returns true if one of
[`inspect.isbuiltin()`](http://docs.python.org/2/library/inspect.html#inspect.isbuiltin),
[`inspect.isfunction()`](http://docs.python.org/2/library/inspect.html#inspect.isfunction),
[`inspect.ismethod()`](http://docs.python.org/2/library/inspect.html#inspect.ismethod)
or
[`inspect.ismethoddescriptor()`](http://docs.python.org/2/library/inspect.html#inspect.ismethoddescriptor)
returns True.

