Merged revisions 59883-59920 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk

........
  r59887 | neal.norwitz | 2008-01-10 06:42:58 +0100 (Thu, 10 Jan 2008) | 1 line

  Reword entry, not sure I made it much better though.
........
  r59888 | andrew.kuchling | 2008-01-10 14:37:12 +0100 (Thu, 10 Jan 2008) | 1 line

  Check for fd of -1 to save fsync() and fstat() call
........
  r59891 | thomas.heller | 2008-01-10 19:45:40 +0100 (Thu, 10 Jan 2008) | 1 line

  Reflow a paragraph, and fix a typo.
........
  r59892 | raymond.hettinger | 2008-01-10 20:15:10 +0100 (Thu, 10 Jan 2008) | 1 line

  Examples for named tuple subclassing should include __slots__
........
  r59895 | raymond.hettinger | 2008-01-10 21:37:12 +0100 (Thu, 10 Jan 2008) | 1 line

  Clarify how to add a field to a named tuple.
........
  r59896 | amaury.forgeotdarc | 2008-01-10 22:59:42 +0100 (Thu, 10 Jan 2008) | 12 lines

  Closing issue1761.
  Surprising behaviour of the "$" regexp: it matches the
  end of the string, AND just before the newline at the end
  of the string::

      re.sub('$', '#', 'foo\n') == 'foo#\n#'

  Python is consistent with Perl and the pcre library, so
  we just document it.
  Guido prefers "\Z" to match only the end of the string.
........
  r59898 | raymond.hettinger | 2008-01-11 00:00:01 +0100 (Fri, 11 Jan 2008) | 1 line

  Neaten-up the named tuple docs
........
  r59900 | raymond.hettinger | 2008-01-11 01:23:13 +0100 (Fri, 11 Jan 2008) | 1 line

  Run doctests on the collections module
........
  r59903 | raymond.hettinger | 2008-01-11 02:25:54 +0100 (Fri, 11 Jan 2008) | 1 line

  Doctest results return a named tuple for readability
........
  r59904 | raymond.hettinger | 2008-01-11 03:12:33 +0100 (Fri, 11 Jan 2008) | 1 line

  Comment-out missing constant (from rev 59819)
........
  r59905 | raymond.hettinger | 2008-01-11 03:24:13 +0100 (Fri, 11 Jan 2008) | 1 line

  Have Decimal.as_tuple return a named tuple.
........
  r59906 | raymond.hettinger | 2008-01-11 04:04:50 +0100 (Fri, 11 Jan 2008) | 1 line

  Let most inspect functions return named tuples
........
  r59907 | raymond.hettinger | 2008-01-11 04:20:54 +0100 (Fri, 11 Jan 2008) | 1 line

  Improve usability of the SequenceMatcher by returning named tuples describing match ranges.
........
  r59909 | thomas.heller | 2008-01-11 09:04:03 +0100 (Fri, 11 Jan 2008) | 1 line

  Add an important missing blank.
........
  r59910 | georg.brandl | 2008-01-11 10:19:11 +0100 (Fri, 11 Jan 2008) | 2 lines

  Guard definition of TIPC_SUB_CANCEL with an #ifdef.
........
  r59911 | georg.brandl | 2008-01-11 10:20:58 +0100 (Fri, 11 Jan 2008) | 2 lines

  News entries for rev. 5990[567].
........
  r59912 | georg.brandl | 2008-01-11 10:55:53 +0100 (Fri, 11 Jan 2008) | 2 lines

  Documentation for r5990[3567].
........
  r59913 | thomas.heller | 2008-01-11 13:41:39 +0100 (Fri, 11 Jan 2008) | 4 lines

  The sqlite3 dll, when compiled in debug mode, must be linked with /MDd
  to use the debug runtime library.  Further, the dll will be named
  sqlite3_d.dll.
........
  r59919 | thomas.heller | 2008-01-11 16:38:46 +0100 (Fri, 11 Jan 2008) | 6 lines

  Revert revision 59913, because it was wrong:

    The sqlite3 dll, when compiled in debug mode, must be linked with
    /MDd to use the debug runtime library.  Further, the dll will be
    named sqlite3_d.dll.
........
  r59920 | christian.heimes | 2008-01-11 16:42:29 +0100 (Fri, 11 Jan 2008) | 1 line

  Removed unused variable
........
diff --git a/Lib/inspect.py b/Lib/inspect.py
index c0db4bc..074754f 100644
--- a/Lib/inspect.py
+++ b/Lib/inspect.py
@@ -31,6 +31,7 @@
 
 import sys, os, types, re, dis, imp, tokenize, linecache
 from operator import attrgetter
+from collections import namedtuple
 
 # ----------------------------------------------------------- type-checking
 def ismodule(object):
@@ -208,6 +209,8 @@
     results.sort()
     return results
 
+Attribute = namedtuple('Attribute', 'name kind defining_class object')
+
 def classify_class_attrs(cls):
     """Return list of attribute-descriptor tuples.
 
@@ -274,7 +277,7 @@
         else:
             kind = "data"
 
-        result.append((name, kind, homecls, obj))
+        result.append(Attribute(name, kind, homecls, obj))
 
     return result
 
@@ -362,6 +365,8 @@
     raise TypeError('arg is not a module, class, method, '
                     'function, traceback, frame, or code object')
 
+ModuleInfo = namedtuple('ModuleInfo', 'name suffix mode module_type')
+
 def getmoduleinfo(path):
     """Get the module name, suffix, mode, and module type for a given file."""
     filename = os.path.basename(path)
@@ -370,7 +375,7 @@
     suffixes.sort() # try longest suffixes first, in case they overlap
     for neglen, suffix, mode, mtype in suffixes:
         if filename[neglen:] == suffix:
-            return filename[:neglen], suffix, mode, mtype
+            return ModuleInfo(filename[:neglen], suffix, mode, mtype)
 
 def getmodulename(path):
     """Return the module name for a given file, or None."""
@@ -668,6 +673,8 @@
 # These constants are from Python's compile.h.
 CO_OPTIMIZED, CO_NEWLOCALS, CO_VARARGS, CO_VARKEYWORDS = 1, 2, 4, 8
 
+Arguments = namedtuple('Arguments', 'args, varargs, varkw')
+
 def getargs(co):
     """Get information about the arguments accepted by a code object.
 
@@ -676,7 +683,7 @@
     lists. Keyword-only arguments are appended. 'varargs' and 'varkw'
     are the names of the * and ** arguments or None."""
     args, varargs, kwonlyargs, varkw = _getfullargs(co)
-    return args + kwonlyargs, varargs, varkw
+    return Arguments(args + kwonlyargs, varargs, varkw)
 
 def _getfullargs(co):
     """Get information about the arguments accepted by a code object.
@@ -706,6 +713,9 @@
         varkw = co.co_varnames[nargs]
     return args, varargs, kwonlyargs, varkw
 
+
+ArgSpec = namedtuple('ArgSpec', 'args varargs keywords defaults')
+
 def getargspec(func):
     """Get the names and default values of a function's arguments.
 
@@ -725,7 +735,10 @@
     if kwonlyargs or ann:
         raise ValueError("Function has keyword-only arguments or annotations"
                          ", use getfullargspec() API which can support them")
-    return (args, varargs, varkw, defaults)
+    return ArgSpec(args, varargs, varkw, defaults)
+
+FullArgSpec = namedtuple('FullArgSpec',
+    'args, varargs, varkw, defaults, kwonlyargs, kwdefaults, annotations')
 
 def getfullargspec(func):
     """Get the names and default values of a function's arguments.
@@ -747,9 +760,11 @@
     if not isfunction(func):
         raise TypeError('arg is not a Python function')
     args, varargs, kwonlyargs, varkw = _getfullargs(func.__code__)
-    return (args, varargs, varkw, func.__defaults__,
+    return FullArgSpec(args, varargs, varkw, func.__defaults__,
             kwonlyargs, func.__kwdefaults__, func.__annotations__)
 
+ArgInfo = namedtuple('ArgInfo', 'args varargs keywords locals')
+
 def getargvalues(frame):
     """Get information about arguments passed into a particular frame.
 
@@ -859,6 +874,9 @@
     return '(' + ', '.join(specs) + ')'
 
 # -------------------------------------------------- stack frame extraction
+
+Traceback = namedtuple('Traceback', 'filename lineno function code_context index')
+
 def getframeinfo(frame, context=1):
     """Get information about a frame or traceback object.
 
@@ -890,7 +908,7 @@
     else:
         lines = index = None
 
-    return (filename, lineno, frame.f_code.co_name, lines, index)
+    return Traceback(filename, lineno, frame.f_code.co_name, lines, index)
 
 def getlineno(frame):
     """Get the line number from a frame object, allowing for optimization."""