[Numpysvn] r8127  in trunk/numpy: doc lib linalg ma polynomial testing
numpysvn@scip...
numpysvn@scip...
Wed Feb 17 17:53:04 CST 2010
Author: jarrod.millman
Date: 20100217 17:53:04 0600 (Wed, 17 Feb 2010)
New Revision: 8127
Modified:
trunk/numpy/doc/basics.py
trunk/numpy/doc/creation.py
trunk/numpy/doc/indexing.py
trunk/numpy/doc/misc.py
trunk/numpy/doc/ufuncs.py
trunk/numpy/lib/financial.py
trunk/numpy/lib/function_base.py
trunk/numpy/lib/io.py
trunk/numpy/lib/shape_base.py
trunk/numpy/linalg/linalg.py
trunk/numpy/ma/core.py
trunk/numpy/polynomial/__init__.py
trunk/numpy/polynomial/chebyshev.py
trunk/numpy/polynomial/polynomial.py
trunk/numpy/polynomial/polytemplate.py
trunk/numpy/polynomial/polyutils.py
trunk/numpy/testing/utils.py
Log:
more docstring updates from pydoc website (thanks to everyone who contributed!)
Modified: trunk/numpy/doc/basics.py
===================================================================
 trunk/numpy/doc/basics.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/doc/basics.py 20100217 23:53:04 UTC (rev 8127)
@@ 44,7 +44,7 @@
the dtypes are available as ``np.bool``, ``np.float32``, etc.
Advanced types, not listed in the table above, are explored in
section `link_here`.
+section :ref:`structured_arrays`.
There are 5 basic numerical types representing booleans (bool), integers (int),
unsigned integers (uint) floating point (float) and complex. Those with numbers
@@ 98,8 +98,8 @@
dtype('uint8')
dtype objects also contain information about the type, such as its bitwidth
and its byteorder. See xxx for details. The data type can also be used
indirectly to query properties of the type, such as whether it is an integer::
+and its byteorder. The data type can also be used indirectly to query
+properties of the type, such as whether it is an integer::
>>> d = np.dtype(int)
>>> d
Modified: trunk/numpy/doc/creation.py
===================================================================
 trunk/numpy/doc/creation.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/doc/creation.py 20100217 23:53:04 UTC (rev 8127)
@@ 9,7 +9,8 @@
There are 5 general mechanisms for creating arrays:
1) Conversion from other Python structures (e.g., lists, tuples)
2) Intrinsic numpy array array creation objects (e.g., arange, ones, zeros, etc.)
+2) Intrinsic numpy array array creation objects (e.g., arange, ones, zeros,
+ etc.)
3) Reading arrays from disk, either from standard or custom formats
4) Creating arrays from raw bytes through the use of strings or buffers
5) Use of special library functions (e.g., random)
@@ 22,17 +23,19 @@
====================================================
In general, numerical data arranged in an arraylike structure in Python can
be converted to arrays through the use of the array() function. The most obvious
examples are lists and tuples. See the documentation for array() for details for
its use. Some objects may support the arrayprotocol and allow conversion to arrays
this way. A simple way to find out if the object can be converted to a numpy array
using array() is simply to try it interactively and see if it works! (The Python Way).
+be converted to arrays through the use of the array() function. The most
+obvious examples are lists and tuples. See the documentation for array() for
+details for its use. Some objects may support the arrayprotocol and allow
+conversion to arrays this way. A simple way to find out if the object can be
+converted to a numpy array using array() is simply to try it interactively and
+see if it works! (The Python Way).
Examples: ::
>>> x = np.array([2,3,1,0])
>>> x = np.array([2, 3, 1, 0])
 >>> x = np.array([[1,2.0],[0,0],(1+1j,3.)]) # note mix of tuple and lists, and types
+ >>> x = np.array([[1,2.0],[0,0],(1+1j,3.)]) # note mix of tuple and lists,
+ and types
>>> x = np.array([[ 1.+0.j, 2.+0.j], [ 0.+0.j, 0.+0.j], [ 1.+1.j, 3.+0.j]])
Intrinsic Numpy Array Creation
@@ 102,7 +105,6 @@
HDF5: PyTables
FITS: PyFITS
 Others? xxx
Examples of formats that cannot be read directly but for which it is not hard
to convert are libraries like PIL (able to read and write many image formats
@@ 125,9 +127,9 @@
simple format then one can write a simple I/O library and use the numpy
fromfile() function and .tofile() method to read and write numpy arrays
directly (mind your byteorder though!) If a good C or C++ library exists that
read the data, one can wrap that library with a variety of techniques (see
xxx) though that certainly is much more work and requires significantly more
advanced knowledge to interface with C or C++.
+read the data, one can wrap that library with a variety of techniques though
+that certainly is much more work and requires significantly more advanced
+knowledge to interface with C or C++.
Use of Special Libraries

@@ 136,6 +138,6 @@
and it isn't possible to enumerate all of them. The most common uses are use
of the many array generation functions in random that can generate arrays of
random values, and some utility functions to generate special matrices (e.g.
diagonal)
+diagonal).
"""
Modified: trunk/numpy/doc/indexing.py
===================================================================
 trunk/numpy/doc/indexing.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/doc/indexing.py 20100217 23:53:04 UTC (rev 8127)
@@ 14,10 +14,10 @@
Assignment vs referencing
=========================
Most of the following examples show the use of indexing when referencing
data in an array. The examples work just as well when assigning to an
array. See the section at the end for specific examples and explanations
on how assignments work.
+Most of the following examples show the use of indexing when
+referencing data in an array. The examples work just as well
+when assigning to an array. See the section at the end for
+specific examples and explanations on how assignments work.
Single element indexing
=======================
@@ 48,39 +48,38 @@
>>> x[0]
array([0, 1, 2, 3, 4])
That is, each index specified selects the array corresponding to the rest
of the dimensions selected. In the above example, choosing 0 means that
remaining dimension of lenth 5 is being left unspecified, and that what
is returned is an array of that dimensionality and size. It must be noted
that the returned array is not a copy of the original, but points to the
same values in memory as does the original array (a new view of the same
data in other words, see xxx for details). In this case,
the 1D array at the first position (0) is returned. So using a single
index on the returned array, results in a single element being returned.
That is: ::
+That is, each index specified selects the array corresponding to the
+rest of the dimensions selected. In the above example, choosing 0
+means that remaining dimension of lenth 5 is being left unspecified,
+and that what is returned is an array of that dimensionality and size.
+It must be noted that the returned array is not a copy of the original,
+but points to the same values in memory as does the original array.
+In this case, the 1D array at the first position (0) is returned.
+So using a single index on the returned array, results in a single
+element being returned. That is: ::
>>> x[0][2]
2
So note that ``x[0,2] = x[0][2]`` though the second case is more inefficient
a new temporary array is created after the first index that is subsequently
indexed by 2.
+So note that ``x[0,2] = x[0][2]`` though the second case is more
+inefficient a new temporary array is created after the first index
+that is subsequently indexed by 2.
Note to those used to IDL or Fortran memory order as it relates to indexing.
Numpy uses Corder indexing. That means that the last index usually (see
xxx for exceptions) represents the most rapidly changing memory location,
unlike Fortran or IDL, where the first index represents the most rapidly
changing location in memory. This difference represents a great potential
for confusion.
+Note to those used to IDL or Fortran memory order as it relates to
+indexing. Numpy uses Corder indexing. That means that the last
+index usually represents the most rapidly changing memory location,
+unlike Fortran or IDL, where the first index represents the most
+rapidly changing location in memory. This difference represents a
+great potential for confusion.
Other indexing options
======================
It is possible to slice and stride arrays to extract arrays of the same
number of dimensions, but of different sizes than the original. The slicing
and striding works exactly the same way it does for lists and tuples except
that they can be applied to multiple dimensions as well. A few
examples illustrates best: ::
+It is possible to slice and stride arrays to extract arrays of the
+same number of dimensions, but of different sizes than the original.
+The slicing and striding works exactly the same way it does for lists
+and tuples except that they can be applied to multiple dimensions as
+well. A few examples illustrates best: ::
>>> x = np.arange(10)
>>> x[2:5]
@@ 95,35 +94,34 @@
[21, 24, 27]])
Note that slices of arrays do not copy the internal array data but
also produce new views of the original data (see xxx for more
explanation of this issue).
+also produce new views of the original data.
It is possible to index arrays with other arrays for the purposes of
selecting lists of values out of arrays into new arrays. There are two
different ways of accomplishing this. One uses one or more arrays of
index values (see xxx for details). The other involves giving a boolean
array of the proper shape to indicate the values to be selected.
Index arrays are a very powerful tool that allow one to avoid looping
over individual elements in arrays and thus greatly improve performance
(see xxx for examples)
+selecting lists of values out of arrays into new arrays. There are
+two different ways of accomplishing this. One uses one or more arrays
+of index values. The other involves giving a boolean array of the proper
+shape to indicate the values to be selected. Index arrays are a very
+powerful tool that allow one to avoid looping over individual elements in
+arrays and thus greatly improve performance.
It is possible to use special features to effectively increase the
number of dimensions in an array through indexing so the resulting
array aquires the shape needed for use in an expression or with a
specific function. See xxx.
+specific function.
Index arrays
============
Numpy arrays may be indexed with other arrays (or any other sequencelike
object that can be converted to an array, such as lists, with the exception
of tuples; see the end of this document for why this is). The use of index
arrays ranges from simple, straightforward cases to complex, hardtounderstand
cases. For all cases of index arrays, what is returned is a copy of the
original data, not a view as one gets for slices.
+Numpy arrays may be indexed with other arrays (or any other sequence
+like object that can be converted to an array, such as lists, with the
+exception of tuples; see the end of this document for why this is). The
+use of index arrays ranges from simple, straightforward cases to
+complex, hardtounderstand cases. For all cases of index arrays, what
+is returned is a copy of the original data, not a view as one gets for
+slices.
Index arrays must be of integer type. Each value in the array indicates which
value in the array to use in place of the index. To illustrate: ::
+Index arrays must be of integer type. Each value in the array indicates
+which value in the array to use in place of the index. To illustrate: ::
>>> x = np.arange(10,1,1)
>>> x
@@ 132,11 +130,12 @@
array([7, 7, 9, 2])
The index array consisting of the values 3, 3, 1 and 8 correspondingly create
an array of length 4 (same as the index array) where each index is replaced by
the value the index array has in the array being indexed.
+The index array consisting of the values 3, 3, 1 and 8 correspondingly
+create an array of length 4 (same as the index array) where each index
+is replaced by the value the index array has in the array being indexed.
Negative values are permitted and work as they do with single indices or slices: ::
+Negative values are permitted and work as they do with single indices
+or slices: ::
>>> x[np.array([3,3,3,8])]
array([7, 7, 4, 2])
@@ 146,9 +145,10 @@
>>> x[np.array([3, 3, 20, 8])]
<type 'exceptions.IndexError'>: index 20 out of bounds 0<=index<9
Generally speaking, what is returned when index arrays are used is an array with
the same shape as the index array, but with the type and values of the array being
indexed. As an example, we can use a multidimensional index array instead: ::
+Generally speaking, what is returned when index arrays are used is
+an array with the same shape as the index array, but with the type
+and values of the array being indexed. As an example, we can use a
+multidimensional index array instead: ::
>>> x[np.array([[1,1],[2,3]])]
array([[9, 9],
@@ 157,77 +157,85 @@
Indexing Multidimensional arrays
=================================
Things become more complex when multidimensional arrays are indexed, particularly
with multidimensional index arrays. These tend to be more unusal uses, but they
are permitted, and they are useful for some problems. We'll start with the
simplest multidimensional case (using the array y from the previous examples): ::
+Things become more complex when multidimensional arrays are indexed,
+particularly with multidimensional index arrays. These tend to be
+more unusal uses, but theyare permitted, and they are useful for some
+problems. We'll start with thesimplest multidimensional case (using
+the array y from the previous examples): ::
>>> y[np.array([0,2,4]), np.array([0,1,2])]
array([ 0, 15, 30])
In this case, if the index arrays have a matching shape, and there is an index
array for each dimension of the array being indexed, the resultant array has the
same shape as the index arrays, and the values correspond to the index set for each
position in the index arrays. In this example, the first index value is 0 for both
index arrays, and thus the first value of the resultant array is y[0,0]. The next
value is y[2,1], and the last is y[4,2].
+In this case, if the index arrays have a matching shape, and there is
+an index array for each dimension of the array being indexed, the
+resultant array has the same shape as the index arrays, and the values
+correspond to the index set for each position in the index arrays. In
+this example, the first index value is 0 for both index arrays, and
+thus the first value of the resultant array is y[0,0]. The next value
+is y[2,1], and the last is y[4,2].
If the index arrays do not have the same shape, there is an attempt to broadcast
them to the same shape. Broadcasting won't be discussed here but is discussed in
detail in xxx. If they cannot be broadcast to the same shape, an exception is
raised: ::
+If the index arrays do not have the same shape, there is an attempt to
+broadcast them to the same shape. If they cannot be broadcast to the
+same shape, an exception is raised: ::
>>> y[np.array([0,2,4]), np.array([0,1])]
 <type 'exceptions.ValueError'>: shape mismatch: objects cannot be broadcast to a single shape
+ <type 'exceptions.ValueError'>: shape mismatch: objects cannot be
+ broadcast to a single shape
The broadcasting mechanism permits index arrays to be combined with scalars for
other indices. The effect is that the scalar value is used for all the corresponding
values of the index arrays: ::
+The broadcasting mechanism permits index arrays to be combined with
+scalars for other indices. The effect is that the scalar value is used
+for all the corresponding values of the index arrays: ::
>>> y[np.array([0,2,4]), 1]
array([ 1, 15, 29])
Jumping to the next level of complexity, it is possible to only partially index an array
with index arrays. It takes a bit of thought to understand what happens in such cases.
For example if we just use one index array with y: ::
+Jumping to the next level of complexity, it is possible to only
+partially index an array with index arrays. It takes a bit of thought
+to understand what happens in such cases. For example if we just use
+one index array with y: ::
>>> y[np.array([0,2,4])]
array([[ 0, 1, 2, 3, 4, 5, 6],
[14, 15, 16, 17, 18, 19, 20],
[28, 29, 30, 31, 32, 33, 34]])
What results is the construction of a new array where each value of the index array
selects one row from the array being indexed and the resultant array has the resulting
shape (size of row, number index elements).
+What results is the construction of a new array where each value of
+the index array selects one row from the array being indexed and the
+resultant array has the resulting shape (size of row, number index
+elements).
An example of where this may be useful is for a color lookup table where we want to map
the values of an image into RGB triples for display. The lookup table could have a shape
(nlookup, 3). Indexing such an array with an image with shape (ny, nx) with dtype=np.uint8
(or any integer type so long as values are with the bounds of the lookup table) will
result in an array of shape (ny, nx, 3) where a triple of RGB values is associated with
each pixel location.
+An example of where this may be useful is for a color lookup table
+where we want to map the values of an image into RGB triples for
+display. The lookup table could have a shape (nlookup, 3). Indexing
+such an array with an image with shape (ny, nx) with dtype=np.uint8
+(or any integer type so long as values are with the bounds of the
+lookup table) will result in an array of shape (ny, nx, 3) where a
+triple of RGB values is associated with each pixel location.
In general, the shape of the resulant array will be the concatenation of the shape of
the index array (or the shape that all the index arrays were broadcast to) with the
shape of any unused dimensions (those not indexed) in the array being indexed.
+In general, the shape of the resulant array will be the concatenation
+of the shape of the index array (or the shape that all the index arrays
+were broadcast to) with the shape of any unused dimensions (those not
+indexed) in the array being indexed.
Boolean or "mask" index arrays
==============================
Boolean arrays used as indices are treated in a different manner entirely than index
arrays. Boolean arrays must be of the same shape as the array being indexed, or
broadcastable to the same shape. In the most straightforward case, the boolean array
has the same shape: ::
+Boolean arrays used as indices are treated in a different manner
+entirely than index arrays. Boolean arrays must be of the same shape
+as the array being indexed, or broadcastable to the same shape. In the
+most straightforward case, the boolean array has the same shape: ::
>>> b = y>20
>>> y[b]
array([21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34])
The result is a 1D array containing all the elements in the indexed array corresponding
to all the true elements in the boolean array. As with index arrays, what is returned
is a copy of the data, not a view as one gets with slices.
+The result is a 1D array containing all the elements in the indexed
+array corresponding to all the true elements in the boolean array. As
+with index arrays, what is returned is a copy of the data, not a view
+as one gets with slices.
With broadcasting, multidimesional arrays may be the result. For example: ::
+With broadcasting, multidimensional arrays may be the result. For
+example: ::
>>> b[:,5] # use a 1D boolean that broadcasts with y
array([False, False, False, True, True], dtype=bool)
@@ 235,8 +243,8 @@
array([[21, 22, 23, 24, 25, 26, 27],
[28, 29, 30, 31, 32, 33, 34]])
Here the 4th and 5th rows are selected from the indexed array and combined to make a
2D array.
+Here the 4th and 5th rows are selected from the indexed array and
+combined to make a 2D array.
Combining index arrays with slices
==================================
@@ 248,8 +256,9 @@
[15, 16],
[29, 30]])
In effect, the slice is converted to an index array np.array([[1,2]]) (shape (1,2)) that is
broadcast with the index array to produce a resultant array of shape (3,2).
+In effect, the slice is converted to an index array
+np.array([[1,2]]) (shape (1,2)) that is broadcast with the index array
+to produce a resultant array of shape (3,2).
Likewise, slicing can be combined with broadcasted boolean indices: ::
@@ 322,7 +331,8 @@
>>> x[1]
1
>>> x[1] = 1.2j
 <type 'exceptions.TypeError'>: can't convert complex to long; use long(abs(z))
+ <type 'exceptions.TypeError'>: can't convert complex to long; use
+ long(abs(z))
Unlike some of the references (such as array and mask indices)
@@ 331,7 +341,12 @@
actions may not work as one may naively expect. This particular
example is often surprising to people: ::
+ >>> x = np.arange(0, 50, 10)
+ >>> x
+ array([ 0, 10, 20, 30, 40])
>>> x[np.array([1, 1, 3, 1])] += 1
+ >>> x
+ array([ 0, 11, 20, 31, 40])
Where people expect that the 1st location will be incremented by 3.
In fact, it will only be incremented by 1. The reason is because
@@ 367,7 +382,8 @@
>>> z[indices]
array([39, 40])
Likewise, ellipsis can be specified by code by using the Ellipsis object: ::
+Likewise, ellipsis can be specified by code by using the Ellipsis
+object: ::
>>> indices = (1, Ellipsis, 1) # same as [1,...,1]
>>> z[indices]
@@ 376,10 +392,11 @@
[46, 49, 52]])
For this reason it is possible to use the output from the np.where()
function directly as an index since it always returns a tuple of index arrays.
+function directly as an index since it always returns a tuple of index
+arrays.
Because the special treatment of tuples, they are not automatically converted
to an array as a list would be. As an example: ::
+Because the special treatment of tuples, they are not automatically
+converted to an array as a list would be. As an example: ::
>>> z[[1,1,1,1]] # produces a large array
array([[[[27, 28, 29],
Modified: trunk/numpy/doc/misc.py
===================================================================
 trunk/numpy/doc/misc.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/doc/misc.py 20100217 23:53:04 UTC (rev 8127)
@@ 30,8 +30,8 @@
isfinite(): True if not nan or inf
nan_to_num(): Map nan to 0, inf to max float, inf to min float
The following corresponds to the usual functions except that nans are excluded from
the results: ::
+The following corresponds to the usual functions except that nans are excluded
+from the results: ::
nansum()
nanmax()
@@ 160,7 +160,8 @@
 Minuses:
  can't use for writing code to be turned into C extensions, only a wrapper tool.
+  can't use for writing code to be turned into C extensions, only a wrapper
+ tool.
5) SWIG (automatic wrapper generator)
@@ 174,11 +175,11 @@
 Minuses:
 generates lots of code between Python and the C code

  can cause performance problems that are nearly impossible to optimize out

+  can cause performance problems that are nearly impossible to optimize
+ out
 interface files can be hard to write
  doesn't necessarily avoid reference counting issues or needing to know API's
+  doesn't necessarily avoid reference counting issues or needing to know
+ API's
7) Weave
@@ 187,8 +188,8 @@
 Phenomenal tool
 can turn many numpy expressions into C code
 dynamic compiling and loading of generated C code
  can embed pure C code in Python module and have weave extract, generate interfaces
 and compile, etc.
+  can embed pure C code in Python module and have weave extract, generate
+ interfaces and compile, etc.
 Minuses:
@@ 198,7 +199,8 @@
 Plusses:
  Turns pure python into efficient machine code through jitlike optimizations
+  Turns pure python into efficient machine code through jitlike
+ optimizations
 very fast when it optimizes well
 Minuses:
@@ 208,15 +210,15 @@
Interfacing to Fortran:

Fortran: Clear choice is f2py. (Pyfort is an older alternative, but not supported
any longer)
+Fortran: Clear choice is f2py. (Pyfort is an older alternative, but not
+supported any longer)
Interfacing to C++:

1) CXX
2) Boost.python
3) SWIG
4) Sage has used cython to wrap C++ (not pretty, but it can be done)
5) SIP (used mainly in PyQT)
+ 1) CXX
+ 2) Boost.python
+ 3) SWIG
+ 4) Sage has used cython to wrap C++ (not pretty, but it can be done)
+ 5) SIP (used mainly in PyQT)
"""
Modified: trunk/numpy/doc/ufuncs.py
===================================================================
 trunk/numpy/doc/ufuncs.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/doc/ufuncs.py 20100217 23:53:04 UTC (rev 8127)
@@ 13,12 +13,11 @@
>>> np.array([0,2,3,4]) + np.array([1,1,1,2])
array([1, 3, 2, 6])
The unfunc module lists all the available ufuncs in numpy. Additional ufuncts
available in xxx in scipy. Documentation on the specific ufuncs may be found
in those modules. This documentation is intended to address the more general
aspects of unfuncs common to most of them. All of the ufuncs that make use of
Python operators (e.g., +, , etc.) have equivalent functions defined
(e.g. add() for +)
+The unfunc module lists all the available ufuncs in numpy. Documentation on
+the specific ufuncs may be found in those modules. This documentation is
+intended to address the more general aspects of unfuncs common to most of
+them. All of the ufuncs that make use of Python operators (e.g., +, , etc.)
+have equivalent functions defined (e.g. add() for +)
Type coercion
=============
@@ 58,10 +57,10 @@
ufunc methods
=============
Binary ufuncs support 4 methods. These methods are explained in detail in xxx
(or are they, I don't see anything in the ufunc docstring that is useful?).
+Binary ufuncs support 4 methods.
**.reduce(arr)** applies the binary operator to elements of the array in sequence. For example: ::
+**.reduce(arr)** applies the binary operator to elements of the array in
+ sequence. For example: ::
>>> np.add.reduce(np.arange(10)) # adds all elements of array
45
@@ 76,22 +75,25 @@
>>> np.add.reduce(np.arange(10).reshape(2,5),axis=1)
array([10, 35])
**.accumulate(arr)** applies the binary operator and generates an an equivalently
shaped array that includes the accumulated amount for each element of the
array. A couple examples: ::
+**.accumulate(arr)** applies the binary operator and generates an an
+equivalently shaped array that includes the accumulated amount for each
+element of the array. A couple examples: ::
>>> np.add.accumulate(np.arange(10))
array([ 0, 1, 3, 6, 10, 15, 21, 28, 36, 45])
>>> np.multiply.accumulate(np.arange(1,9))
array([ 1, 2, 6, 24, 120, 720, 5040, 40320])
The behavior for multidimensional arrays is the same as for .reduce(), as is the use of the axis keyword).
+The behavior for multidimensional arrays is the same as for .reduce(),
+as is the use of the axis keyword).
**.reduceat(arr,indices)** allows one to apply reduce to selected parts of an array.
It is a difficult method to understand. See the documentation at:
+**.reduceat(arr,indices)** allows one to apply reduce to selected parts
+ of an array. It is a difficult method to understand. See the documentation
+ at:
**.outer(arr1,arr2)** generates an outer operation on the two arrays arr1 and arr2. It will work on multidimensional arrays (the shape of the result is the
concatenation of the two input shapes.: ::
+**.outer(arr1,arr2)** generates an outer operation on the two arrays arr1 and
+ arr2. It will work on multidimensional arrays (the shape of the result is
+ the concatenation of the two input shapes.: ::
>>> np.multiply.outer(np.arange(3),np.arange(4))
array([[0, 0, 0, 0],
@@ 101,14 +103,14 @@
Output arguments
================
All ufuncs accept an optional output array. The array must be of the expected output shape. Beware that if the type of the output array is of a
different (and lower) type than the output result, the results may be silently
truncated or otherwise corrupted in the downcast to the lower type. This usage
is useful when one wants to avoid creating large temporary arrays and instead
allows one to reuse the same array memory repeatedly (at the expense of not
being able to use more convenient operator notation in expressions). Note that
when the output argument is used, the ufunc still returns a reference to the
result.
+All ufuncs accept an optional output array. The array must be of the expected
+output shape. Beware that if the type of the output array is of a different
+(and lower) type than the output result, the results may be silently truncated
+or otherwise corrupted in the downcast to the lower type. This usage is useful
+when one wants to avoid creating large temporary arrays and instead allows one
+to reuse the same array memory repeatedly (at the expense of not being able to
+use more convenient operator notation in expressions). Note that when the
+output argument is used, the ufunc still returns a reference to the result.
>>> x = np.arange(2)
>>> np.add(np.arange(2),np.arange(2.),x)
Modified: trunk/numpy/lib/financial.py
===================================================================
 trunk/numpy/lib/financial.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/lib/financial.py 20100217 23:53:04 UTC (rev 8127)
@@ 206,7 +206,7 @@
def nper(rate, pmt, pv, fv=0, when='end'):
"""
 Compute the number of periods.
+ Compute the number of periodic payments.
Parameters

@@ 225,16 +225,16 @@

The number of periods ``nper`` is computed by solving the equation::
 fv + pv*(1+rate)**nper + pmt*(1+rate*when)/rate * ((1+rate)**nper  1) == 0
+ fv + pv*(1+rate)**nper + pmt*(1+rate*when)/rate*((1+rate)**nper1) = 0
 or, when ``rate == 0``::
+ but if ``rate = 0`` then::
 fv + pv + pmt * nper == 0
+ fv + pv + pmt*nper = 0
Examples

 If you only had $150 to spend as payment, how long would it take to payoff
 a loan of $8,000 at 7% annual interest?
+ If you only had $150/month to pay towards the loan, how long would it take
+ to payoff a loan of $8,000 at 7% annual interest?
>>> np.nper(0.07/12, 150, 8000)
64.073348770661852
@@ 244,11 +244,13 @@
The same analysis could be done with several different interest rates
and/or payments and/or total amounts to produce an entire table.
 >>> np.nper(*(np.ogrid[0.06/12:0.071/12:0.01/12, 200:99:100, 6000:7001:1000]))
 array([[[ 32.58497782, 38.57048452],
 [ 71.51317802, 86.37179563]],
 [[ 33.07413144, 39.26244268],
 [ 74.06368256, 90.22989997]]])
+ >>> np.nper(*(np.ogrid[0.07/12: 0.08/12: 0.01/12,
+ ... 150 : 99 : 50 ,
+ ... 8000 : 9001 : 1000]))
+ array([[[ 64.07334877, 74.06368256],
+ [ 108.07548412, 127.99022654]],
+ [[ 66.12443902, 76.87897353],
+ [ 114.70165583, 137.90124779]]])
"""
when = _convert_when(when)
Modified: trunk/numpy/lib/function_base.py
===================================================================
 trunk/numpy/lib/function_base.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/lib/function_base.py 20100217 23:53:04 UTC (rev 8127)
@@ 1366,25 +1366,21 @@
def nanmin(a, axis=None):
"""
 Return the minimum of array elements over the given axis ignoring any NaNs.
+ Return the minimum of an array or minimum along an axis ignoring any NaNs.
Parameters

a : array_like
 Array containing numbers whose sum is desired. If `a` is not
 an array, a conversion is attempted.
+ Array containing numbers whose minimum is desired.
axis : int, optional
Axis along which the minimum is computed.The default is to compute
the minimum of the flattened array.
Returns

 y : {ndarray, scalar}
 An array with the same shape as `a`, with the specified axis removed.
 If `a` is a 0d array, or if axis is None, a scalar is returned. The
 the same dtype as `a` is returned.
+ nanmin : ndarray
+ A new array or a scalar array with the result.

See Also

numpy.amin : Minimum across array including any Not a Numbers.
@@ 1461,7 +1457,7 @@
def nanmax(a, axis=None):
"""
 Return the maximum of array elements over the given axis ignoring any NaNs.
+ Return the maximum of an array or maximum along an axis ignoring any NaNs.
Parameters

@@ 1469,15 +1465,15 @@
Array containing numbers whose maximum is desired. If `a` is not
an array, a conversion is attempted.
axis : int, optional
 Axis along which the maximum is computed.The default is to compute
+ Axis along which the maximum is computed. The default is to compute
the maximum of the flattened array.
Returns

 y : ndarray
+ nanmax : ndarray
An array with the same shape as `a`, with the specified axis removed.
 If `a` is a 0d array, or if axis is None, a scalar is returned. The
 the same dtype as `a` is returned.
+ If `a` is a 0d array, or if axis is None, a ndarray scalar is
+ returned. The the same dtype as `a` is returned.
See Also

Modified: trunk/numpy/lib/io.py
===================================================================
 trunk/numpy/lib/io.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/lib/io.py 20100217 23:53:04 UTC (rev 8127)
@@ 306,9 +306,11 @@
Parameters

 file : file or string
 File or filename to which the data is saved. If the filename
 does not already have a ``.npy`` extension, it is added.
+ file : file or str
+ File or filename to which the data is saved. If file is a fileobject,
+ then the filename is unchanged. If file is a string, a ``.npy``
+ extension will be appended to the file name if it does not already
+ have one.
arr : array_like
Array data to be saved.
@@ 329,7 +331,7 @@
>>> x = np.arange(10)
>>> np.save(outfile, x)
 >>> outfile.seek(0) # only necessary in this example (with tempfile)
+ >>> outfile.seek(0) # Only needed here to simulate closing & reopening file
>>> np.load(outfile)
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
@@ 348,26 +350,30 @@
"""
Save several arrays into a single, compressed file in ``.npz`` format.
 If keyword arguments are given, the names for variables assigned to the
 keywords are the keyword names (not the variable names in the caller).
If arguments are passed in with no keywords, the corresponding variable
 names are arr_0, arr_1, etc.
+ names, in the .npz file, are 'arr_0', 'arr_1', etc. If keyword arguments
+ are given, the corresponding variable names, in the ``.npz`` file will
+ match the keyword names.
Parameters

file : str or file
Either the file name (string) or an open file (filelike object)
 If file is a string, it names the output file. ".npz" will be appended
 to the file name if it is not already there.
 args : Arguments
 Any function arguments other than the file name are variables to save.
 Since it is not possible for Python to know their names outside
 `savez`, they will be saved with names "arr_0", "arr_1", and so on.
 These arguments can be any expression.
 kwds : Keyword arguments
 All keyword=value pairs cause the value to be saved with the name of
 the keyword.
+ where the data will be saved. If file is a string, the ``.npz``
+ extension will be appended to the file name if it is not already there.
+ \\*args : Arguments, optional
+ Arrays to save to the file. Since it is not possible for Python to
+ know the names of the arrays outside `savez`, the arrays will be saved
+ with names "arr_0", "arr_1", and so on. These arguments can be any
+ expression.
+ \\*\\*kwds : Keyword arguments, optional
+ Arrays to save to the file. Arrays will be saved in the file with the
+ keyword names.
+ Returns
+ 
+ None
+
See Also

save : Save a single array to a binary file in NumPy format.
@@ 379,6 +385,11 @@
variables they contain. Each file contains one variable in ``.npy``
format. For a description of the ``.npy`` format, see `format`.
+ When opening the saved ``.npz`` file with `load` a `NpzFile` object is
+ returned. This is a dictionarylike object which can be queried for
+ its list of arrays (with the ``.files`` attribute), and for the arrays
+ themselves.
+
Examples

>>> from tempfile import TemporaryFile
@@ 389,11 +400,11 @@
Using `savez` with \\*args, the arrays are saved with default names.
>>> np.savez(outfile, x, y)
 >>> outfile.seek(0) # only necessary in this example (with tempfile)
 >>> npz = np.load(outfile)
 >>> npz.files
+ >>> outfile.seek(0) # Only needed here to simulate closing & reopening file
+ >>> npzfile = np.load(outfile)
+ >>> npzfile.files
['arr_1', 'arr_0']
 >>> npz['arr_0']
+ >>> npzfile['arr_0']
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
Using `savez` with \\*\\*kwds, the arrays are saved with the keyword names.
@@ 401,10 +412,10 @@
>>> outfile = TemporaryFile()
>>> np.savez(outfile, x=x, y=y)
>>> outfile.seek(0)
 >>> npz = np.load(outfile)
 >>> npz.files
+ >>> npzfile = np.load(outfile)
+ >>> npzfile.files
['y', 'x']
 >>> npz['x']
+ >>> npzfile['x']
array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
"""
@@ 510,8 +521,15 @@
See Also

load, fromstring, fromregex
+ genfromtxt : Load data with missing values handled as specified.
scipy.io.loadmat : reads Matlab(R) data files
+ Notes
+ 
+ This function aims to be a fast reader for simply formatted files. The
+ `genfromtxt` function provides more sophisticated handling of, e.g.,
+ lines with missing values.
+
Examples

>>> from StringIO import StringIO # StringIO behaves like a file object
Modified: trunk/numpy/lib/shape_base.py
===================================================================
 trunk/numpy/lib/shape_base.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/lib/shape_base.py 20100217 23:53:04 UTC (rev 8127)
@@ 301,7 +301,7 @@
Stack arrays in sequence depth wise (along third axis).
Takes a sequence of arrays and stack them along the third axis
 to make a single array. Rebuilds arrays divided by ``dsplit``.
+ to make a single array. Rebuilds arrays divided by `dsplit`.
This is a simple way to stack 2D arrays (images) into a single
3D array for processing.
@@ 325,7 +325,7 @@
Notes

 Equivalent to ``np.concatenate(tup, axis=2)``
+ Equivalent to ``np.concatenate(tup, axis=2)``.
Examples

@@ 420,7 +420,7 @@
If `indices_or_sections` is a 1D array of sorted integers, the entries
indicate where along `axis` the array is split. For example,
 ``[2, 3]`` would, for ``axis = 0``, result in
+ ``[2, 3]`` would, for ``axis=0``, result in
 ary[:2]
 ary[2:3]
@@ 483,8 +483,8 @@
"""
Split an array into multiple subarrays horizontally (columnwise).
 Please refer to the ``split`` documentation. ``hsplit`` is equivalent
 to ``split`` with `axis=1`, the array is always split along the second
+ Please refer to the `split` documentation. `hsplit` is equivalent
+ to `split` with ``axis=1``, the array is always split along the second
axis regardless of the array dimension.
See Also
@@ 596,8 +596,8 @@
"""
Split array into multiple subarrays along the 3rd axis (depth).
 Please refer to the ``split`` documentation. ``dsplit`` is equivalent
 to ``split`` with `axis=2`, the array is always split along the third
+ Please refer to the `split` documentation. `dsplit` is equivalent
+ to `split` with ``axis=2``, the array is always split along the third
axis provided the array dimension is greater than or equal to 3.
See Also
Modified: trunk/numpy/linalg/linalg.py
===================================================================
 trunk/numpy/linalg/linalg.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/linalg/linalg.py 20100217 23:53:04 UTC (rev 8127)
@@ 1175,34 +1175,38 @@
"""
Singular Value Decomposition.
 Factors the matrix `a` into ``u * np.diag(s) * v.H``, where `u` and `v`
 are unitary (i.e., ``u.H = inv(u)`` and similarly for `v`), ``.H`` is the
 conjugate transpose operator (which is the ordinary transpose for
 realvalued matrices), and `s` is a 1D array of `a`'s singular values.
+ Factors the matrix ``a`` into ``u * np.diag(s) * v``, where ``u`` and
+ ``v`` are unitary (i.e., ``u.H = inv(u)`` and similarly for ``v``) and
+ ``s`` is a 1D array of ``a``'s singular values. Note that, in the
+ literature, it is common to see this decomposition expressed as (in
+ NumPy notation) ``a = u * np.diag(s) * v.H``, whereas the ``v`` this
+ function returns is such that ``a`` would be reconstructed as above; in
+ other words, "our" ``v`` is the Hermitian (conjugate transpose) of that
+ commonly seen in the literature.
Parameters

a : array_like
Matrix of shape ``(M, N)`` to decompose.
full_matrices : bool, optional
 If True (default), ``u`` and ``v.H`` have the shapes
 ``(M, M)`` and ``(N, N)``, respectively. Otherwise, the shapes
 are ``(M, K)`` and ``(K, N)``, resp., where ``K = min(M, N)``.
+ If True (default), ``u`` and ``v`` have the shapes ``(M, M)``
+ and ``(N, N)``, respectively. Otherwise, the shapes are ``(M, K)``
+ and ``(K, N)``, resp., where ``K = min(M, N)``.
compute_uv : bool, optional
 Whether or not to compute ``u`` and ``v.H`` in addition to ``s``.
+ Whether or not to compute ``u`` and ``v`` in addition to ``s``.
True by default.
Returns

u : ndarray
 Unitary matrix. The shape of `U` is ``(M, M)`` or ``(M, K)``
 depending on value of `full_matrices`.
+ Unitary matrix. The shape of ``U`` is ``(M, M)`` or ``(M, K)``
+ depending on value of ``full_matrices``.
s : ndarray
The singular values, sorted so that ``s[i] >= s[i+1]``.
 `S` is a 1D array of length ``min(M, N)``
 v.H : ndarray
+ ``S`` is a 1D array of length ``min(M, N)``
+ v : ndarray
Unitary matrix of shape ``(N, N)`` or ``(K, N)``, depending
 on `full_matrices`.
+ on ``full_matrices``.
Raises

@@ 1211,21 +1215,21 @@
Notes

 If `a` is a matrix object (as opposed to an `ndarray`), then so are all
 the return values.
+ If ``a`` is a matrix object (as opposed to an `ndarray`), then so are
+ all the return values.
Examples

>>> a = np.random.randn(9, 6) + 1j*np.random.randn(9, 6)
 >>> U, s, Vh = np.linalg.svd(a)
 >>> U.shape, Vh.shape, s.shape
+ >>> U, s, V = np.linalg.svd(a)
+ >>> U.shape, V.shape, s.shape
((9, 9), (6, 6), (6,))
 >>> U, s, Vh = np.linalg.svd(a, full_matrices=False)
 >>> U.shape, Vh.shape, s.shape
+ >>> U, s, V = np.linalg.svd(a, full_matrices=False)
+ >>> U.shape, V.shape, s.shape
((9, 6), (6, 6), (6,))
>>> S = np.diag(s)
 >>> np.allclose(a, np.dot(U, np.dot(S, Vh)))
+ >>> np.allclose(a, np.dot(U, np.dot(S, V)))
True
>>> s2 = np.linalg.svd(a, compute_uv=False)
Modified: trunk/numpy/ma/core.py
===================================================================
 trunk/numpy/ma/core.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/ma/core.py 20100217 23:53:04 UTC (rev 8127)
@@ 545,6 +545,10 @@
a : ndarray
The filled array.
+ See Also
+ 
+ compressed
+
Examples

>>> x = np.ma.array(np.arange(9).reshape(3, 3), mask=[[1, 0, 0],
Modified: trunk/numpy/polynomial/__init__.py
===================================================================
 trunk/numpy/polynomial/__init__.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/polynomial/__init__.py 20100217 23:53:04 UTC (rev 8127)
@@ 1,3 +1,18 @@
+"""
+A subpackage for efficiently dealing with polynomials.
+
+Within the documentation for this subpackage, a "finite power series,"
+i.e., a polynomial (also referred to simply as a "series") is represented
+by a 1D numpy array of the polynomial's coefficients, ordered from lowest
+order term to highest. For example, array([1,2,3]) represents
+``P_0 + 2*P_1 + 3*P_2``, where P_n is the nth order basis polynomial
+applicable to the specific module in question, e.g., `polynomial` (which
+"wraps" the "standard" basis) or `chebyshev`. For optimal performance,
+all operations on polynomials, including evaluation at an argument, are
+implemented as operations on the coefficients. Additional (modulespecific)
+information can be found in the docstring for the module of interest.
+
+"""
from polynomial import *
from chebyshev import *
from polyutils import *
Modified: trunk/numpy/polynomial/chebyshev.py
===================================================================
 trunk/numpy/polynomial/chebyshev.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/polynomial/chebyshev.py 20100217 23:53:04 UTC (rev 8127)
@@ 1,50 +1,58 @@
"""Functions for dealing with Chebyshev series.
+"""
+Objects for dealing with Chebyshev series.
This module provide s a number of functions that are useful in dealing with
Chebyshev series as well as a ``Chebyshev`` class that encapsuletes the usual
arithmetic operations. All the Chebyshev series are assumed to be ordered
from low to high, thus ``array([1,2,3])`` will be treated as the series
``T_0 + 2*T_1 + 3*T_2``
+This module provides a number of objects (mostly functions) useful for
+dealing with Chebyshev series, including a `Chebyshev` class that
+encapsulates the usual arithmetic operations. (General information
+on how this module represents and works with such polynomials is in the
+docstring for its "parent" subpackage, `numpy.polynomial`).
Constants

 chebdomain  Chebyshev series default domain
 chebzero  Chebyshev series that evaluates to 0.
 chebone  Chebyshev series that evaluates to 1.
 chebx  Chebyshev series of the identity map (x).
+ `chebdomain`  Chebyshev series default domain, [1,1].
+ `chebzero`  (Coefficients of the) Chebyshev series that evaluates
+ identically to 0.
+ `chebone`  (Coefficients of the) Chebyshev series that evaluates
+ identically to 1.
+ `chebx`  (Coefficients of the) Chebyshev series for the identity map,
+ ``f(x) = x``.
Arithmetic

 chebadd  add a Chebyshev series to another.
 chebsub  subtract a Chebyshev series from another.
 chebmul  multiply a Chebyshev series by another
 chebdiv  divide one Chebyshev series by another.
 chebval  evaluate a Chebyshev series at given points.
+ `chebadd`  add two Chebyshev series.
+ `chebsub`  subtract one Chebyshev series from another.
+ `chebmul`  multiply two Chebyshev series.
+ `chebdiv`  divide one Chebyshev series by another.
+ `chebval`  evaluate a Chebyshev series at given points.
Calculus

 chebder  differentiate a Chebyshev series.
 chebint  integrate a Chebyshev series.
+ `chebder`  differentiate a Chebyshev series.
+ `chebint`  integrate a Chebyshev series.
Misc Functions

 chebfromroots  create a Chebyshev series with specified roots.
 chebroots  find the roots of a Chebyshev series.
 chebvander  Vandermode like matrix for Chebyshev polynomials.
 chebfit  least squares fit returning a Chebyshev series.
 chebtrim  trim leading coefficients from a Chebyshev series.
 chebline  Chebyshev series of given straight line
 cheb2poly  convert a Chebyshev series to a polynomial.
 poly2cheb  convert a polynomial to a Chebyshev series.
+ `chebfromroots`  create a Chebyshev series with specified roots.
+ `chebroots`  find the roots of a Chebyshev series.
+ `chebvander`  Vandermondelike matrix for Chebyshev polynomials.
+ `chebfit`  leastsquares fit returning a Chebyshev series.
+ `chebtrim`  trim leading coefficients from a Chebyshev series.
+ `chebline`  Chebyshev series of given straight line.
+ `cheb2poly`  convert a Chebyshev series to a polynomial.
+ `poly2cheb`  convert a polynomial to a Chebyshev series.
Classes

 Chebyshev  Chebyshev series class.
+ `Chebyshev`  A Chebyshev series class.
+See also
+
+`numpy.polynomial`
+
Notes

The implementations of multiplication, division, integration, and
differentiation use the algebraic identities:
+differentiation use the algebraic identities [1]_:
.. math ::
T_n(x) = \\frac{z^n + z^{n}}{2} \\\\
@@ 55,9 +63,15 @@
.. math :: x = \\frac{z + z^{1}}{2}.
These identities allow a Chebyshev series to be expressed as a finite,
symmetric Laurent series. These sorts of Laurent series are referred to as
zseries in this module.
+symmetric Laurent series. In this module, this sort of Laurent series
+is referred to as a "zseries."
+References
+
+.. [1] A. T. Benjamin, et al., "Combinatorial Trigonometry with Chebyshev
+ Polynomials," *Journal of Statistical Planning and Inference 14*, 2008
+ (preprint: http://www.math.hmc.edu/~benjamin/papers/CombTrig.pdf, pg. 4)
+
"""
from __future__ import division
@@ 289,20 +303,24 @@
def poly2cheb(pol) :
 """Convert a polynomial to a Chebyshev series.
+ """
+ poly2cheb(pol)
 Convert a series containing polynomial coefficients ordered by degree
 from low to high to an equivalent Chebyshev series ordered from low to
 high.
+ Convert a polynomial to a Chebyshev series.
 Inputs
 
+ Convert an array representing the coefficients of a polynomial (relative
+ to the "standard" basis) ordered from lowest degree to highest, to an
+ array of the coefficients of the equivalent Chebyshev series, ordered
+ from lowest to highest degree.
+
+ Parameters
+ 
pol : array_like
 1d array containing the polynomial coeffients
+ 1d array containing the polynomial coefficients
Returns

 cseries : ndarray
+ cs : ndarray
1d array containing the coefficients of the equivalent Chebyshev
series.
@@ 310,6 +328,23 @@

cheb2poly
+ Notes
+ 
+ Note that a consequence of the input needing to be array_like and that
+ the output is an ndarray, is that if one is going to use this function
+ to convert a Polynomial instance, P, to a Chebyshev instance, T, the
+ usage is ``T = Chebyshev(poly2cheb(P.coef))``; see Examples below.
+
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> p = P.Polynomial(np.arange(4))
+ >>> p
+ Polynomial([ 0., 1., 2., 3.], [1., 1.])
+ >>> c = P.Chebyshev(P.poly2cheb(p.coef))
+ >>> c
+ Chebyshev([ 1. , 3.25, 1. , 0.75], [1., 1.])
+
"""
[pol] = pu.as_series([pol])
pol = pol[::1]
@@ 322,28 +357,50 @@
def cheb2poly(cs) :
 """Convert a Chebyshev series to a polynomial.
+ """
+ cheb2poly(cs)
 Covert a series containing Chebyshev series coefficients orderd from
 low to high to an equivalent polynomial ordered from low to
 high by degree.
+ Convert a Chebyshev series to a polynomial.
 Inputs
 
+ Convert an array representing the coefficients of a Chebyshev series,
+ ordered from lowest degree to highest, to an array of the coefficients
+ of the equivalent polynomial (relative to the "standard" basis) ordered
+ from lowest to highest degree.
+
+ Parameters
+ 
cs : array_like
 1d array containing the Chebyshev series coeffients ordered from
 low to high.
+ 1d array containing the Chebyshev series coefficients, ordered
+ from lowest order term to highest.
Returns

pol : ndarray
1d array containing the coefficients of the equivalent polynomial
 ordered from low to high by degree.
+ (relative to the "standard" basis) ordered from lowest order term
+ to highest.
See Also

poly2cheb
+ Notes
+ 
+ Note that a consequence of the input needing to be array_like and that
+ the output is an ndarray, is that if one is going to use this function
+ to convert a Chebyshev instance, T, to a Polynomial instance, P, the
+ usage is ``P = Polynomial(cheb2poly(T.coef))``; see Examples below.
+
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> c = P.Chebyshev(np.arange(4))
+ >>> c
+ Chebyshev([ 0., 1., 2., 3.], [1., 1.])
+ >>> p = P.Polynomial(P.cheb2poly(c.coef))
+ >>> p
+ Polynomial([ 2., 8., 4., 12.], [1., 1.])
+
"""
[cs] = pu.as_series([cs])
pol = np.zeros(len(cs), dtype=cs.dtype)
@@ 373,20 +430,34 @@
chebx = np.array([0,1])
def chebline(off, scl) :
 """Chebyshev series whose graph is a straight line
+ """
+ Chebyshev series whose graph is a straight line.
 The line has the formula ``off + scl*x``
 Parameters:
 
+
+ Parameters
+ 
off, scl : scalars
The specified line is given by ``off + scl*x``.
 Returns:
+ Returns
+ 
+ y : ndarray
+ This module's representation of the Chebyshev series for
+ ``off + scl*x``.
+
+ See Also

 series : 1d ndarray
 The Chebyshev series representation of ``off + scl*x``.
+ polyline
+ Examples
+ 
+ >>> import numpy.polynomial.chebyshev as C
+ >>> C.chebline(3,2)
+ array([3, 2])
+ >>> C.chebval(3, C.chebline(3,2)) # should be 3
+ 3.0
+
"""
if scl != 0 :
return np.array([off,scl])
@@ 394,26 +465,56 @@
return np.array([off])
def chebfromroots(roots) :
 """Generate a Chebyschev series with given roots.
+ """
+ Generate a Chebyshev series with the given roots.
 Generate a Chebyshev series whose roots are given by `roots`. The
 resulting series is the produet `(x  roots[0])*(x  roots[1])*...`
+ Return the array of coefficients for the Cseries whose roots (a.k.a.
+ "zeros") are given by *roots*. The returned array of coefficients is
+ ordered from lowest order "term" to highest, and zeros of multiplicity
+ greater than one must be included in *roots* a number of times equal
+ to their multiplicity (e.g., if `2` is a root of multiplicity three,
+ then [2,2,2] must be in *roots*).
 Inputs
 
+ Parameters
+ 
roots : array_like
 1d array containing the roots in sorted order.
+ Sequence containing the roots.
Returns

 series : ndarray
 1d array containing the coefficients of the Chebeshev series
 ordered from low to high.
+ out : ndarray
+ 1d array of the Cseries' coefficients, ordered from low to
+ high. If all roots are real, ``out.dtype`` is a float type;
+ otherwise, ``out.dtype`` is a complex type, even if all the
+ coefficients in the result are real (see Examples below).
See Also

 chebroots
+ polyfromroots
+ Notes
+ 
+ What is returned are the :math:`c_i` such that:
+
+ .. math::
+
+ \\sum_{i=0}^{n} c_i*T_i(x) = \\prod_{i=0}^{n} (x  roots[i])
+
+ where ``n == len(roots)`` and :math:`T_i(x)` is the `i`th Chebyshev
+ (basis) polynomial over the domain `[1,1]`. Note that, unlike
+ `polyfromroots`, due to the nature of the Cseries basis set, the
+ above identity *does not* imply :math:`c_n = 1` identically (see
+ Examples).
+
+ Examples
+ 
+ >>> import numpy.polynomial.chebyshev as C
+ >>> C.chebfromroots((1,0,1)) # x^3  x relative to the standard basis
+ array([ 0. , 0.25, 0. , 0.25])
+ >>> j = complex(0,1)
+ >>> C.chebfromroots((j,j)) # x^2 + 1 relative to the standard basis
+ array([ 1.5+0.j, 0.0+0.j, 0.5+0.j])
+
"""
if len(roots) == 0 :
return np.ones(1)
@@ 427,27 +528,43 @@
def chebadd(c1, c2):
 """Add one Chebyshev series to another.
+ """
+ Add one Chebyshev series to another.
 Returns the sum of two Chebyshev series `c1` + `c2`. The arguments are
 sequences of coefficients ordered from low to high, i.e., [1,2,3] is
 the series "T_0 + 2*T_1 + 3*T_2".
+ Returns the sum of two Chebyshev series `c1` + `c2`. The arguments
+ are sequences of coefficients ordered from lowest order term to
+ highest, i.e., [1,2,3] represents the series ``T_0 + 2*T_1 + 3*T_2``.
Parameters

c1, c2 : array_like
 1d arrays of Chebyshev series coefficients ordered from low to
+ 1d arrays of Chebyshev series coefficients ordered from low to
high.
Returns

out : ndarray
 Chebyshev series of the sum.
+ Array representing the Chebyshev series of their sum.
See Also

chebsub, chebmul, chebdiv, chebpow
+ Notes
+ 
+ Unlike multiplication, division, etc., the sum of two Chebyshev series
+ is a Chebyshev series (without having to "reproject" the result onto
+ the basis set) so addition, just like that of "standard" polynomials,
+ is simply "componentwise."
+
+ Examples
+ 
+ >>> from numpy.polynomial import chebyshev as C
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> C.chebadd(c1,c2)
+ array([ 4., 4., 4.])
+
"""
# c1, c2 are trimmed copies
[c1, c2] = pu.as_series([c1, c2])
@@ 461,29 +578,44 @@
def chebsub(c1, c2):
 """Subtract one Chebyshev series from another.
+ """
+ Subtract one Chebyshev series from another.
 Returns the difference of two Chebyshev series `c1`  `c2`. The
 sequences of coefficients are ordered from low to high, i.e., [1,2,3]
 is the series ``T_0 + 2*T_1 + 3*T_2.``
+ Returns the difference of two Chebyshev series `c1`  `c2`. The
+ sequences of coefficients are from lowest order term to highest, i.e.,
+ [1,2,3] represents the series ``T_0 + 2*T_1 + 3*T_2``.
Parameters

c1, c2 : array_like
 1d arrays of Chebyshev series coefficients ordered from low to
+ 1d arrays of Chebyshev series coefficients ordered from low to
high.
Returns

out : ndarray
 Chebyshev series of the difference.
+ Of Chebyshev series coefficients representing their difference.
See Also

chebadd, chebmul, chebdiv, chebpow
+ Notes
+ 
+ Unlike multiplication, division, etc., the difference of two Chebyshev
+ series is a Chebyshev series (without having to "reproject" the result
+ onto the basis set) so subtraction, just like that of "standard"
+ polynomials, is simply "componentwise."
+
Examples

+ >>> from numpy.polynomial import chebyshev as C
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> C.chebsub(c1,c2)
+ array([2., 0., 2.])
+ >>> C.chebsub(c2,c1) # C.chebsub(c1,c2)
+ array([ 2., 0., 2.])
"""
# c1, c2 are trimmed copies
@@ 499,27 +631,44 @@
def chebmul(c1, c2):
 """Multiply one Chebyshev series by another.
+ """
+ Multiply one Chebyshev series by another.
 Returns the product of two Chebyshev series `c1` * `c2`. The arguments
 are sequences of coefficients ordered from low to high, i.e., [1,2,3]
 is the series ``T_0 + 2*T_1 + 3*T_2.``
+ Returns the product of two Chebyshev series `c1` * `c2`. The arguments
+ are sequences of coefficients, from lowest order "term" to highest,
+ e.g., [1,2,3] represents the series ``T_0 + 2*T_1 + 3*T_2``.
Parameters

c1, c2 : array_like
 1d arrays of chebyshev series coefficients ordered from low to
+ 1d arrays of Chebyshev series coefficients ordered from low to
high.
Returns

out : ndarray
 Chebyshev series of the product.
+ Of Chebyshev series coefficients representing their product.
See Also

chebadd, chebsub, chebdiv, chebpow
+ Notes
+ 
+ In general, the (polynomial) product of two Cseries results in terms
+ that are not in the Chebyshev polynomial basis set. Thus, to express
+ the product as a Cseries, it is typically necessary to "reproject"
+ the product onto said basis set, which typically produces
+ "unintuitive" (but correct) results; see Examples section below.
+
+ Examples
+ 
+ >>> from numpy.polynomial import chebyshev as C
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> C.chebmul(c1,c2) # multiplication requires "reprojection"
+ array([ 6.5, 12. , 12. , 4. , 1.5])
+
"""
# c1, c2 are trimmed copies
[c1, c2] = pu.as_series([c1, c2])
@@ 531,29 +680,49 @@
def chebdiv(c1, c2):
 """Divide one Chebyshev series by another.
+ """
+ Divide one Chebyshev series by another.
 Returns the quotient of two Chebyshev series `c1` / `c2`. The arguments
 are sequences of coefficients ordered from low to high, i.e., [1,2,3]
 is the series ``T_0 + 2*T_1 + 3*T_2.``
+ Returns the quotientwithremainder of two Chebyshev series
+ `c1` / `c2`. The arguments are sequences of coefficients from lowest
+ order "term" to highest, e.g., [1,2,3] represents the series
+ ``T_0 + 2*T_1 + 3*T_2``.
Parameters

c1, c2 : array_like
 1d arrays of chebyshev series coefficients ordered from low to
+ 1d arrays of Chebyshev series coefficients ordered from low to
high.
Returns

 [quo, rem] : ndarray
 Chebyshev series of the quotient and remainder.
+ [quo, rem] : ndarrays
+ Of Chebyshev series coefficients representing the quotient and
+ remainder.
See Also

chebadd, chebsub, chebmul, chebpow
+ Notes
+ 
+ In general, the (polynomial) division of one Cseries by another
+ results in quotient and remainder terms that are not in the Chebyshev
+ polynomial basis set. Thus, to express these results as Cseries, it
+ is typically necessary to "reproject" the results onto said basis
+ set, which typically produces "unintuitive" (but correct) results;
+ see Examples section below.
+
Examples

+ >>> from numpy.polynomial import chebyshev as C
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> C.chebdiv(c1,c2) # quotient "intuitive," remainder not
+ (array([ 3.]), array([8., 4.]))
+ >>> c2 = (0,1,2,3)
+ >>> C.chebdiv(c2,c1) # neither "intuitive"
+ (array([ 0., 2.]), array([2., 4.]))
"""
# c1, c2 are trimmed copies
@@ 627,24 +796,25 @@
return _zseries_to_cseries(prd)
def chebder(cs, m=1, scl=1) :
 """Differentiate a Chebyshev series.
+ """
+ Differentiate a Chebyshev series.
 Returns the series `cs` differentiated `m` times. At each iteration the
 result is multiplied by `scl`. The scaling factor is for use in a
 linear change of variable. The argument `cs` is a sequence of
 coefficients ordered from low to high. i.e., [1,2,3] is the series
+ Returns the series `cs` differentiated `m` times. At each iteration the
+ result is multiplied by `scl` (the scaling factor is for use in a linear
+ change of variable). The argument `cs` is the sequence of coefficients
+ from lowest order "term" to highest, e.g., [1,2,3] represents the series
``T_0 + 2*T_1 + 3*T_2``.
Parameters

cs: array_like
 1d array of chebyshev series coefficients ordered from low to high.
+ 1d array of Chebyshev series coefficients ordered from low to high.
m : int, optional
 Order of differentiation, must be nonnegative. (default: 1)
+ Number of derivatives taken, must be nonnegative. (Default: 1)
scl : scalar, optional
 The result of each derivation is multiplied by `scl`. The end
 result is multiplication by `scl`**`m`. This is for use in a linear
 change of variable. (default: 1)
+ Each differentiation is multiplied by `scl`. The end result is
+ multiplication by ``scl**m``. This is for use in a linear change of
+ variable. (Default: 1)
Returns

@@ 655,8 +825,25 @@

chebint
+ Notes
+ 
+ In general, the result of differentiating a Cseries needs to be
+ "reprojected" onto the Cseries basis set. Thus, typically, the
+ result of this function is "unintuitive," albeit correct; see Examples
+ section below.
+
Examples

+ >>> from numpy.polynomial import chebyshev as C
+ >>> cs = (1,2,3,4)
+ >>> C.chebder(cs)
+ array([ 14., 12., 24.])
+ >>> C.chebder(cs,3)
+ array([ 96.])
+ >>> C.chebder(cs,scl=1)
+ array([14., 12., 24.])
+ >>> C.chebder(cs,2,1)
+ array([ 12., 96.])
"""
# cs is a trimmed copy
@@ 678,49 +865,80 @@
def chebint(cs, m=1, k=[], lbnd=0, scl=1) :
 """Integrate a Chebyshev series.
+ """
+ Integrate a Chebyshev series.
 Returns the series integrated from `lbnd` to x `m` times. At each
 iteration the resulting series is multiplied by `scl` and an
 integration constant specified by `k` is added. The scaling factor is
 for use in a linear change of variable. The argument `cs` is a sequence
 of coefficients ordered from low to high. i.e., [1,2,3] is the series
 ``T_0 + 2*T_1 + 3*T_2``.
+ Returns, as a Cseries, the input Cseries `cs`, integrated `m` times
+ from `lbnd` to `x`. At each iteration the resulting series is
+ **multiplied** by `scl` and an integration constant, `k`, is added.
+ The scaling factor is for use in a linear change of variable. ("Buyer
+ beware": note that, depending on what one is doing, one may want `scl`
+ to be the reciprocal of what one might expect; for more information,
+ see the Notes section below.) The argument `cs` is a sequence of
+ coefficients, from lowest order Cseries "term" to highest, e.g.,
+ [1,2,3] represents the series :math:`T_0(x) + 2T_1(x) + 3T_2(x)`.

Parameters

 cs: array_like
 1d array of chebyshev series coefficients ordered from low to high.
+ cs : array_like
+ 1d array of Cseries coefficients, ordered from low to high.
m : int, optional
 Order of integration, must be positeve. (default: 1)
+ Order of integration, must be positive. (Default: 1)
k : {[], list, scalar}, optional
 Integration constants. The value of the first integral at zero is
 the first value in the list, the value of the second integral at
 zero is the second value in the list, and so on. If ``[]``
 (default), all constants are set zero. If `m = 1`, a single scalar
 can be given instead of a list.
+ Integration constant(s). The value of the first integral at zero
+ is the first value in the list, the value of the second integral
+ at zero is the second value, etc. If ``k == []`` (the default),
+ all constants are set to zero. If ``m == 1``, a single scalar can
+ be given instead of a list.
lbnd : scalar, optional
 The lower bound of the integral. (default: 0)
+ The lower bound of the integral. (Default: 0)
scl : scalar, optional
 Following each integration the result is multiplied by `scl` before
 the integration constant is added. (default: 1)
+ Following each integration the result is *multiplied* by `scl`
+ before the integration constant is added. (Default: 1)
Returns

 der : ndarray
 Chebyshev series of the integral.
+ S : ndarray
+ Cseries coefficients of the integral.
Raises

ValueError
+ If ``m < 1``, ``len(k) > m``, ``np.isscalar(lbnd) == False``, or
+ ``np.isscalar(scl) == False``.
See Also

chebder
+ Notes
+ 
+ Note that the result of each integration is *multiplied* by `scl`.
+ Why is this important to note? Say one is making a linear change of
+ variable :math:`u = ax + b` in an integral relative to `x`. Then
+ :math:`dx = du/a`, so one will need to set `scl` equal to :math:`1/a`
+  perhaps not what one would have first thought.
+
+ Also note that, in general, the result of integrating a Cseries needs
+ to be "reprojected" onto the Cseries basis set. Thus, typically,
+ the result of this function is "unintuitive," albeit correct; see
+ Examples section below.
+
Examples

+ >>> from numpy.polynomial import chebyshev as C
+ >>> cs = (1,2,3)
+ >>> C.chebint(cs)
+ array([ 0.5, 0.5, 0.5, 0.5])
+ >>> C.chebint(cs,3)
+ array([ 0.03125 , 0.1875 , 0.04166667, 0.05208333, 0.01041667,
+ 0.00625 ])
+ >>> C.chebint(cs, k=3)
+ array([ 3.5, 0.5, 0.5, 0.5])
+ >>> C.chebint(cs,lbnd=2)
+ array([ 8.5, 0.5, 0.5, 0.5])
+ >>> C.chebint(cs,scl=2)
+ array([1., 1., 1., 1.])
"""
if np.isscalar(k) :
@@ 839,10 +1057,11 @@
return v
def chebfit(x, y, deg, rcond=None, full=False):
 """Least squares fit of Chebyshev series to data.
+ """
+ Least squares fit of Chebyshev series to data.
 Fit a Chebyshev series ``p(x) = p[0] * T_{deq}(x) + ... + p[deg] *
 T_{0}(x)`` of degree `deg` to points `(x, y)`. Returns a vector of
+ Fit a Chebyshev series ``p(x) = p[0] * T_{0}(x) + ... + p[deg] *
+ T_{deg}(x)`` of degree `deg` to points `(x, y)`. Returns a vector of
coefficients `p` that minimises the squared error.
Parameters
@@ 900,7 +1119,7 @@
The solution are the coefficients ``c[i]`` of the Chebyshev series
``T(x)`` that minimizes the squared error
 ``E = \sum_j y_j  T(x_j)^2``.
+ ``E = \\sum_j y_j  T(x_j)^2``.
This problem is solved by setting up as the overdetermined matrix
equation
@@ 971,24 +1190,45 @@
def chebroots(cs):
 """Roots of a Chebyshev series.
+ """
+ Compute the roots of a Chebyshev series.
 Compute the roots of the Chebyshev series `cs`. The argument `cs` is a
 sequence of coefficients ordered from low to high. i.e., [1,2,3] is the
 series ``T_0 + 2*T_1 + 3*T_2``.
+ Return the roots (a.k.a "zeros") of the Cseries represented by `cs`,
+ which is the sequence of the Cseries' coefficients from lowest order
+ "term" to highest, e.g., [1,2,3] represents the Cseries
+ ``T_0 + 2*T_1 + 3*T_2``.
Parameters

cs : array_like
 1D array of Chebyshev coefficients ordered from low to high.
+ 1d array of Cseries coefficients ordered from low to high.
Returns

out : ndarray
 An array containing the complex roots of the chebyshev series.
+ Array of the roots. If all the roots are real, then so is the
+ dtype of ``out``; otherwise, ``out``'s dtype is complex.
+ See Also
+ 
+ polyroots
+
+ Notes
+ 
+ Algorithm(s) used:
+
+ Remember: because the Cseries basis set is different from the
+ "standard" basis set, the results of this function *may* not be what
+ one is expecting.
+
Examples

+ >>> import numpy.polynomial as P
+ >>> import numpy.polynomial.chebyshev as C
+ >>> P.polyroots((1,1,1,1)) # x^3  x^2 + x  1 has two complex roots
+ array([ 4.99600361e161.j, 4.99600361e16+1.j, 1.00000e+00+0.j])
+ >>> C.chebroots((1,1,1,1)) # T3  T2 + T1  T0 has only real roots
+ array([ 5.00000000e01, 2.60860684e17, 1.00000000e+00])
"""
# cs is a trimmed copy
Modified: trunk/numpy/polynomial/polynomial.py
===================================================================
 trunk/numpy/polynomial/polynomial.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/polynomial/polynomial.py 20100217 23:53:04 UTC (rev 8127)
@@ 1,44 +1,50 @@
"""Functions for dealing with polynomials.
+"""
+Objects for dealing with polynomials.
This module provides a number of functions that are useful in dealing with
polynomials as well as a ``Polynomial`` class that encapsuletes the usual
arithmetic operations. All arrays of polynomial coefficients are assumed to
be ordered from low to high degree, thus `array([1,2,3])` will be treated
as the polynomial ``1 + 2*x + 3*x**2``
+This module provides a number of objects (mostly functions) useful for
+dealing with polynomials, including a `Polynomial` class that
+encapsulates the usual arithmetic operations. (General information
+on how this module represents and works with polynomial objects is in
+the docstring for its "parent" subpackage, `numpy.polynomial`).
Constants

 polydomain  Polynomial default domain
 polyzero  Polynomial that evaluates to 0.
 polyone  Polynomial that evaluates to 1.
 polyx  Polynomial of the identity map (x).
+ `polydomain`  Polynomial default domain, [1,1].
+ `polyzero`  (Coefficients of the) "zero polynomial."
+ `polyone`  (Coefficients of the) constant polynomial 1.
+ `polyx`  (Coefficients of the) identity map polynomial, ``f(x) = x``.
Arithmetic

 polyadd  add a polynomial to another.
 polysub  subtract a polynomial from another.
 polymul  multiply a polynomial by another
 polydiv  divide one polynomial by another.
 polyval  evaluate a polynomial at given points.
+ `polyadd`  add two polynomials.
+ `polysub`  subtract one polynomial from another.
+ `polymul`  multiply two polynomials.
+ `polydiv`  divide one polynomial by another.
+ `polyval`  evaluate a polynomial at given points.
Calculus

 polyder  differentiate a polynomial.
 polyint  integrate a polynomial.
+ `polyder`  differentiate a polynomial.
+ `polyint`  integrate a polynomial.
Misc Functions

 polyfromroots  create a polynomial with specified roots.
 polyroots  find the roots of a polynomial.
 polyvander  Vandermode like matrix for powers.
 polyfit  least squares fit returning a polynomial.
 polytrim  trim leading coefficients from a polynomial.
 polyline  Polynomial of given straight line
+ `polyfromroots`  create a polynomial with specified roots.
+ `polyroots`  find the roots of a polynomial.
+ `polyvander`  Vandermondelike matrix for powers.
+ `polyfit`  leastsquares fit returning a polynomial.
+ `polytrim`  trim leading coefficients from a polynomial.
+ `polyline`  Given a straight line, return the equivalent polynomial
+ object.
Classes

 Polynomial  polynomial class.
+ `Polynomial`  polynomial class.
+See also
+
+`numpy.polynomial`
+
"""
from __future__ import division
@@ 77,20 +83,32 @@
#
def polyline(off, scl) :
 """Polynomial whose graph is a straight line.
+ """
+ Returns an array representing a linear polynomial.
 The line has the formula ``off + scl*x``

 Parameters:
 
+ Parameters
+ 
off, scl : scalars
 The specified line is given by ``off + scl*x``.
+ The "yintercept" and "slope" of the line, respectively.
 Returns:
+ Returns
+ 
+ y : ndarray
+ This module's representation of the linear polynomial ``off +
+ scl*x``.
+
+ See Also

 series : 1d ndarray
 The polynomial equal to ``off + scl*x``.
+ chebline
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> P.polyline(1,1)
+ array([ 1, 1])
+ >>> P.polyval(1, P.polyline(1,1)) # should be 0
+ 0.0
+
"""
if scl != 0 :
return np.array([off,scl])
@@ 98,26 +116,54 @@
return np.array([off])
def polyfromroots(roots) :
 """Generate a polynomial with given roots.
+ """
+ Generate a polynomial with the given roots.
 Generate a polynomial whose roots are given by `roots`. The resulting
 series is the produet `(x  roots[0])*(x  roots[1])*...`
+ Return the array of coefficients for the polynomial whose leading
+ coefficient (i.e., that of the highest order term) is `1` and whose
+ roots (a.k.a. "zeros") are given by *roots*. The returned array of
+ coefficients is ordered from lowest order term to highest, and zeros
+ of multiplicity greater than one must be included in *roots* a number
+ of times equal to their multiplicity (e.g., if `2` is a root of
+ multiplicity three, then [2,2,2] must be in *roots*).
 Inputs
 
+ Parameters
+ 
roots : array_like
 1d array containing the roots in sorted order.
+ Sequence containing the roots.
Returns

 series : ndarray
 1d array containing the coefficients of the Chebeshev series
 ordered from low to high.
+ out : ndarray
+ 1d array of the polynomial's coefficients, ordered from low to
+ high. If all roots are real, ``out.dtype`` is a float type;
+ otherwise, ``out.dtype`` is a complex type, even if all the
+ coefficients in the result are real (see Examples below).
See Also

 polyroots
+ chebfromroots
+ Notes
+ 
+ What is returned are the :math:`a_i` such that:
+
+ .. math::
+
+ \\sum_{i=0}^{n} a_ix^i = \\prod_{i=0}^{n} (x  roots[i])
+
+ where ``n == len(roots)``; note that this implies that `1` is always
+ returned for :math:`a_n`.
+
+ Examples
+ 
+ >>> import numpy.polynomial as P
+ >>> P.polyfromroots((1,0,1)) # x(x  1)(x + 1) = x^3  x
+ array([ 0., 1., 0., 1.])
+ >>> j = complex(0,1)
+ >>> P.polyfromroots((j,j)) # complex returned, though values are real
+ array([ 1.+0.j, 0.+0.j, 1.+0.j])
+
"""
if len(roots) == 0 :
return np.ones(1)
@@ 131,27 +177,37 @@
def polyadd(c1, c2):
 """Add one polynomial to another.
+ """
+ Add one polynomial to another.
 Returns the sum of two polynomials `c1` + `c2`. The arguments are
 sequences of coefficients ordered from low to high, i.e., [1,2,3] is
 the polynomial ``1 + 2*x + 3*x**2"``.
+ Returns the sum of two polynomials `c1` + `c2`. The arguments are
+ sequences of coefficients from lowest order term to highest, i.e.,
+ [1,2,3] represents the polynomial ``1 + 2*x + 3*x**2"``.
Parameters

c1, c2 : array_like
 1d arrays of polynomial coefficients ordered from low to
 high.
+ 1d arrays of polynomial coefficients ordered from low to high.
Returns

out : ndarray
 polynomial of the sum.
+ The coefficient array representing their sum.
See Also

polysub, polymul, polydiv, polypow
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> sum = P.polyadd(c1,c2); sum
+ array([ 4., 4., 4.])
+ >>> P.polyval(2, sum) # 4 + 4(2) + 4(2**2)
+ 28.0
+
"""
# c1, c2 are trimmed copies
[c1, c2] = pu.as_series([c1, c2])
@@ 165,22 +221,23 @@
def polysub(c1, c2):
 """Subtract one polynomial from another.
+ """
+ Subtract one polynomial from another.
 Returns the difference of two polynomials `c1`  `c2`. The arguments
 are sequences of coefficients ordered from low to high, i.e., [1,2,3]
 is the polynomial ``1 + 2*x + 3*x**2``.
+ Returns the difference of two polynomials `c1`  `c2`. The arguments
+ are sequences of coefficients from lowest order term to highest, i.e.,
+ [1,2,3] represents the polynomial ``1 + 2*x + 3*x**2``.
Parameters

c1, c2 : array_like
 1d arrays of polynomial coefficients ordered from low to
+ 1d arrays of polynomial coefficients ordered from low to
high.
Returns

out : ndarray
 polynomial of the difference.
+ Of coefficients representing their difference.
See Also

@@ 188,6 +245,13 @@
Examples

+ >>> from numpy import polynomial as P
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> P.polysub(c1,c2)
+ array([2., 0., 2.])
+ >>> P.polysub(c2,c1) # P.polysub(c1,c2)
+ array([ 2., 0., 2.])
"""
# c1, c2 are trimmed copies
@@ 203,27 +267,36 @@
def polymul(c1, c2):
 """Multiply one polynomial by another.
+ """
+ Multiply one polynomial by another.
 Returns the product of two polynomials `c1` * `c2`. The arguments
 are sequences of coefficients ordered from low to high, i.e., [1,2,3]
 is the polynomial ``1 + 2*x + 3*x**2.``
+ Returns the product of two polynomials `c1` * `c2`. The arguments are
+ sequences of coefficients, from lowest order term to highest, e.g.,
+ [1,2,3] represents the polynomial ``1 + 2*x + 3*x**2.``
Parameters

c1, c2 : array_like
 1d arrays of polyyshev series coefficients ordered from low to
 high.
+ 1d arrays of coefficients representing a polynomial, relative to the
+ "standard" basis, and ordered from lowest order term to highest.
Returns

out : ndarray
 polynomial of the product.
+ Of the coefficients of their product.
See Also

polyadd, polysub, polydiv, polypow
+ Examples
+ 
+ >>> import numpy.polynomial as P
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> P.polymul(c1,c2)
+ array([ 3., 8., 14., 8., 3.])
+
"""
# c1, c2 are trimmed copies
[c1, c2] = pu.as_series([c1, c2])
@@ 232,22 +305,22 @@
def polydiv(c1, c2):
 """Divide one polynomial by another.
+ """
+ Divide one polynomial by another.
 Returns the quotient of two polynomials `c1` / `c2`. The arguments are
 sequences of coefficients ordered from low to high, i.e., [1,2,3] is
 the series ``1 + 2*x + 3*x**2.``
+ Returns the quotientwithremainder of two polynomials `c1` / `c2`.
+ The arguments are sequences of coefficients, from lowest order term
+ to highest, e.g., [1,2,3] represents ``1 + 2*x + 3*x**2``.
Parameters

c1, c2 : array_like
 1d arrays of chebyshev series coefficients ordered from low to
 high.
+ 1d arrays of polynomial coefficients ordered from low to high.
Returns

 [quo, rem] : ndarray
 polynomial of the quotient and remainder.
+ [quo, rem] : ndarrays
+ Of coefficient series representing the quotient and remainder.
See Also

@@ 255,6 +328,13 @@
Examples

+ >>> import numpy.polynomial as P
+ >>> c1 = (1,2,3)
+ >>> c2 = (3,2,1)
+ >>> P.polydiv(c1,c2)
+ (array([ 3.]), array([8., 4.]))
+ >>> P.polydiv(c2,c1)
+ (array([ 0.33333333]), array([ 2.66666667, 1.33333333]))
"""
# c1, c2 are trimmed copies
@@ 331,27 +411,30 @@
return prd
def polyder(cs, m=1, scl=1) :
 """Differentiate a polynomial.
+ """
+ Differentiate a polynomial.
 Returns the polynomial `cs` differentiated `m` times. The argument `cs`
 is a sequence of coefficients ordered from low to high. i.e., [1,2,3]
 is the series ``1 + 2*x + 3*x**2.``
+ Returns the polynomial `cs` differentiated `m` times. At each
+ iteration the result is multiplied by `scl` (the scaling factor is for
+ use in a linear change of variable). The argument `cs` is the sequence
+ of coefficients from lowest order term to highest, e.g., [1,2,3]
+ represents the polynomial ``1 + 2*x + 3*x**2``.
Parameters

cs: array_like
 1d array of chebyshev series coefficients ordered from low to high.
+ 1d array of polynomial coefficients ordered from low to high.
m : int, optional
 Order of differentiation, must be nonnegative. (default: 1)
+ Number of derivatives taken, must be nonnegative. (Default: 1)
scl : scalar, optional
 The result of each derivation is multiplied by `scl`. The end
 result is multiplication by `scl`**`m`. This is for use in a linear
 change of variable. (default: 1)
+ Each differentiation is multiplied by `scl`. The end result is
+ multiplication by ``scl**m``. This is for use in a linear change
+ of variable. (Default: 1)
Returns

der : ndarray
 polynomial of the derivative.
+ Polynomial of the derivative.
See Also

@@ 359,6 +442,16 @@
Examples

+ >>> from numpy import polynomial as P
+ >>> cs = (1,2,3,4) # 1 + 2x + 3x**2 + 4x**3
+ >>> P.polyder(cs) # (d/dx)(cs) = 2 + 6x + 12x**2
+ array([ 2., 6., 12.])
+ >>> P.polyder(cs,3) # (d**3/dx**3)(cs) = 24
+ array([ 24.])
+ >>> P.polyder(cs,scl=1) # (d/d(x))(cs) = 2  6x  12x**2
+ array([ 2., 6., 12.])
+ >>> P.polyder(cs,2,1) # (d**2/d(x)**2)(cs) = 6 + 24x
+ array([ 6., 24.])
"""
# cs is a trimmed copy
@@ 380,49 +473,75 @@
return cs[i+1:].copy()
def polyint(cs, m=1, k=[], lbnd=0, scl=1) :
 """Integrate a polynomial.
+ """
+ Integrate a polynomial.
 Returns the polynomial `cs` integrated from `lbnd` to x `m` times. At
 each iteration the resulting series is multiplied by `scl` and an
 integration constant specified by `k` is added. The scaling factor is
 for use in a linear change of variable. The argument `cs` is a sequence
 of coefficients ordered from low to high. i.e., [1,2,3] is the
 polynomial ``1 + 2*x + 3*x**2``.
+ Returns the polynomial `cs`, integrated `m` times from `lbnd` to `x`.
+ At each iteration the resulting series is **multiplied** by `scl` and
+ an integration constant, `k`, is added. The scaling factor is for use
+ in a linear change of variable. ("Buyer beware": note that, depending
+ on what one is doing, one may want `scl` to be the reciprocal of what
+ one might expect; for more information, see the Notes section below.)
+ The argument `cs` is a sequence of coefficients, from lowest order
+ term to highest, e.g., [1,2,3] represents the polynomial
+ ``1 + 2*x + 3*x**2``.

Parameters

cs : array_like
 1d array of chebyshev series coefficients ordered from low to high.
+ 1d array of polynomial coefficients, ordered from low to high.
m : int, optional
 Order of integration, must be positeve. (default: 1)
+ Order of integration, must be positive. (Default: 1)
k : {[], list, scalar}, optional
 Integration constants. The value of the first integral at zero is
 the first value in the list, the value of the second integral at
 zero is the second value in the list, and so on. If ``[]``
 (default), all constants are set zero. If `m = 1`, a single scalar
 can be given instead of a list.
+ Integration constant(s). The value of the first integral at zero
+ is the first value in the list, the value of the second integral
+ at zero is the second value, etc. If ``k == []`` (the default),
+ all constants are set to zero. If ``m == 1``, a single scalar can
+ be given instead of a list.
lbnd : scalar, optional
 The lower bound of the integral. (default: 0)
+ The lower bound of the integral. (Default: 0)
scl : scalar, optional
 Following each integration the result is multiplied by `scl` before
 the integration constant is added. (default: 1)
+ Following each integration the result is *multiplied* by `scl`
+ before the integration constant is added. (Default: 1)
Returns

 der : ndarray
 polynomial of the integral.
+ S : ndarray
+ Coefficients of the integral.
Raises

ValueError
+ If ``m < 1``, ``len(k) > m``, ``np.isscalar(lbnd) == False``, or
+ ``np.isscalar(scl) == False``.
See Also

polyder
+ Notes
+ 
+ Note that the result of each integration is *multiplied* by `scl`.
+ Why is this important to note? Say one is making a linear change of
+ variable :math:`u = ax + b` in an integral relative to `x`. Then
+ :math:`dx = du/a`, so one will need to set `scl` equal to :math:`1/a`
+  perhaps not what one would have first thought.
+
Examples

+ >>> from numpy import polynomial as P
+ >>> cs = (1,2,3)
+ >>> P.polyint(cs) # should return array([0, 1, 1, 1])
+ array([ 0., 1., 1., 1.])
+ >>> P.polyint(cs,3) # should return array([0, 0, 0, 1/6, 1/12, 1/20])
+ array([ 0. , 0. , 0. , 0.16666667, 0.08333333,
+ 0.05 ])
+ >>> P.polyint(cs,k=3) # should return array([3, 1, 1, 1])
+ array([ 3., 1., 1., 1.])
+ >>> P.polyint(cs,lbnd=2) # should return array([6, 1, 1, 1])
+ array([ 6., 1., 1., 1.])
+ >>> P.polyint(cs,scl=2) # should return array([0, 2, 2, 2])
+ array([ 0., 2., 2., 2.])
"""
if np.isscalar(k) :
@@ 448,7 +567,8 @@
return ret
def polyval(x, cs):
 """Evaluate a polynomial.
+ """
+ Evaluate a polynomial.
If `cs` is of length `n`, this function returns :
@@ 476,16 +596,10 @@

polyfit
 Examples
 

Notes

The evaluation uses Horner's method.
 Examples
 

"""
# cs is a trimmed copy
[cs] = pu.as_series([cs])
@@ 529,50 +643,56 @@
return v
def polyfit(x, y, deg, rcond=None, full=False):
 """Least squares fit of polynomial to data.
+ """
+ Leastsquares fit of a polynomial to data.
 Fit a polynomial ``p(x) = p[0] * T_{deq}(x) + ... + p[deg] *
 T_{0}(x)`` of degree `deg` to points `(x, y)`. Returns a vector of
 coefficients `p` that minimises the squared error.
+ Fit a polynomial ``c0 + c1*x + c2*x**2 + ... + c[deg]*x**deg`` to
+ points (`x`, `y`). Returns a 1d (if `y` is 1d) or 2d (if `y` is 2d)
+ array of coefficients representing, from lowest order term to highest,
+ the polynomial(s) which minimize the total square error.
Parameters

 x : array_like, shape (M,)
 xcoordinates of the M sample points ``(x[i], y[i])``.
 y : array_like, shape (M,) or (M, K)
 ycoordinates of the sample points. Several data sets of sample
 points sharing the same xcoordinates can be fitted at once by
 passing in a 2Darray that contains one dataset per column.
+ x : array_like, shape (`M`,)
+ xcoordinates of the `M` sample (data) points ``(x[i], y[i])``.
+ y : array_like, shape (`M`,) or (`M`, `K`)
+ ycoordinates of the sample points. Several sets of sample points
+ sharing the same xcoordinates can be (independently) fit with one
+ call to `polyfit` by passing in for `y` a 2d array that contains
+ one data set per column.
deg : int
 Degree of the fitting polynomial
+ Degree of the polynomial(s) to be fit.
rcond : float, optional
 Relative condition number of the fit. Singular values smaller than
 this relative to the largest singular value will be ignored. The
 default value is len(x)*eps, where eps is the relative precision of
 the float type, about 2e16 in most cases.
+ Relative condition number of the fit. Singular values smaller
+ than `rcond`, relative to the largest singular value, will be
+ ignored. The default value is ``len(x)*eps``, where `eps` is the
+ relative precision of the platform's float type, about 2e16 in
+ most cases.
full : bool, optional
 Switch determining nature of return value. When it is False (the
 default) just the coefficients are returned, when True diagnostic
 information from the singular value decomposition is also returned.
+ Switch determining the nature of the return value. When ``False``
+ (the default) just the coefficients are returned; when ``True``,
+ diagnostic information from the singular value decomposition (used
+ to solve the fit's matrix equation) is also returned.
Returns

 coef : ndarray, shape (M,) or (M, K)
 Polynomial coefficients ordered from low to high. If `y` was 2D,
 the coefficients for the data in column k of `y` are in column
 `k`.
+ coef : ndarray, shape (`deg` + 1,) or (`deg` + 1, `K`)
+ Polynomial coefficients ordered from low to high. If `y` was 2d,
+ the coefficients in column `k` of `coef` represent the polynomial
+ fit to the data in `y`'s `k`th column.
 [residuals, rank, singular_values, rcond] : present when `full` = True
 Residuals of the leastsquares fit, the effective rank of the
 scaled Vandermonde matrix and its singular values, and the
 specified value of `rcond`. For more details, see `linalg.lstsq`.
+ [residuals, rank, singular_values, rcond] : present when `full` == True
+ Sum of the squared residuals (SSR) of the leastsquares fit; the
+ effective rank of the scaled Vandermonde matrix; its singular
+ values; and the specified value of `rcond`. For more information,
+ see `linalg.lstsq`.
 Warns
 
+ Raises
+ 
RankWarning
 The rank of the coefficient matrix in the leastsquares fit is
 deficient. The warning is only raised if `full` = False. The
 warnings can be turned off by
+ Raised if the matrix in the leastsquares fit is rank deficient.
+ The warning is only raised if `full` == False. The warnings can
+ be turned off by:
>>> import warnings
>>> warnings.simplefilter('ignore', RankWarning)
@@ 587,42 +707,61 @@
Notes

 The solution are the coefficients ``c[i]`` of the polynomial ``P(x)``
 that minimizes the squared error
+ The solutions are the coefficients ``c[i]`` of the polynomial ``P(x)``
+ that minimizes the total squared error:
 ``E = \sum_j y_j  P(x_j)^2``.
+ .. math :: E = \\sum_j (y_j  P(x_j))^2
 This problem is solved by setting up as the overdetermined matrix
 equation
+ This problem is solved by setting up the (typically) overdetermined
+ matrix equation:
 ``V(x)*c = y``,
+ .. math :: V(x)*c = y
 where ``V`` is the Vandermonde matrix of `x`, the elements of ``c`` are
 the coefficients to be solved for, and the elements of `y` are the
 observed values. This equation is then solved using the singular value
 decomposition of ``V``.
+ where `V` is the Vandermonde matrix of `x`, the elements of `c` are the
+ coefficients to be solved for, and the elements of `y` are the observed
+ values. This equation is then solved using the singular value
+ decomposition of `V`.
 If some of the singular values of ``V`` are so small that they are
 neglected, then a `RankWarning` will be issued. This means that the
 coeficient values may be poorly determined. Using a lower order fit
 will usually get rid of the warning. The `rcond` parameter can also be
 set to a value smaller than its default, but the resulting fit may be
 spurious and have large contributions from roundoff error.
+ If some of the singular values of `V` are so small that they are
+ neglected (and `full` == ``False``), a `RankWarning` will be raised.
+ This means that the coefficient values may be poorly determined.
+ Fitting to a lower order polynomial will usually get rid of the warning
+ (but may not be what you want, of course; if you have independent
+ reason(s) for choosing the degree which isn't working, you may have to:
+ a) reconsider those reasons, and/or b) reconsider the quality of your
+ data). The `rcond` parameter can also be set to a value smaller than
+ its default, but the resulting fit may be spurious and have large
+ contributions from roundoff error.
 Fits using double precision and polynomials tend to fail at about
 degree 20. Fits using Chebyshev series are generally better
 conditioned, but much can still depend on the distribution of the
 sample points and the smoothness of the data. If the quality of the fit
 is inadequate splines may be a good alternative.
+ Polynomial fits using double precision tend to "fail" at about
+ (polynomial) degree 20. Fits using Chebyshev series are generally
+ better conditioned, but much can still depend on the distribution of
+ the sample points and the smoothness of the data. If the quality of
+ the fit is inadequate, splines may be a good alternative.
 References
 
 .. [1] Wikipedia, "Curve fitting",
 http://en.wikipedia.org/wiki/Curve_fitting

Examples

+ >>> from numpy import polynomial as P
+ >>> x = np.linspace(1,1,51) # x "data": [1, 0.96, ..., 0.96, 1]
+ >>> y = x**3  x + np.random.randn(len(x)) # x^3  x + N(0,1) "noise"
+ >>> c, stats = P.polyfit(x,y,3,full=True)
+ >>> c # c[0], c[2] should be approx. 0, c[1] approx. 1, c[3] approx. 1
+ array([ 0.01909725, 1.30598256, 0.00577963, 1.02644286])
+ >>> stats # note the large SSR, explaining the rather poor results
+ [array([ 38.06116253]), 4, array([ 1.38446749, 1.32119158, 0.50443316,
+ 0.28853036]), 1.1324274851176597e014]
+ Same thing without the added noise
+
+ >>> y = x**3  x
+ >>> c, stats = P.polyfit(x,y,3,full=True)
+ >>> c # c[0], c[2] should be "very close to 0", c[1] ~= 1, c[3] ~= 1
+ array([ 1.73362882e17, 1.00000000e+00, 2.67471909e16,
+ 1.00000000e+00])
+ >>> stats # note the minuscule SSR
+ [array([ 7.46346754e31]), 4, array([ 1.38446749, 1.32119158,
+ 0.50443316, 0.28853036]), 1.1324274851176597e014]
+
"""
order = int(deg) + 1
x = np.asarray(x) + 0.0
@@ 662,24 +801,39 @@
def polyroots(cs):
 """Roots of a polynomial.
+ """
+ Compute the roots of a polynomial.
 Compute the roots of the Chebyshev series `cs`. The argument `cs` is a
 sequence of coefficients ordered from low to high. i.e., [1,2,3] is the
 polynomial ``1 + 2*x + 3*x**2``.
+ Return the roots (a.k.a. "zeros") of the "polynomial" `cs`, the
+ polynomial's coefficients from lowest order term to highest
+ (e.g., [1,2,3] represents the polynomial ``1 + 2*x + 3*x**2``).
Parameters

 cs : array_like of shape(M,)
 1D array of polynomial coefficients ordered from low to high.
+ cs : array_like of shape (M,)
+ 1d array of polynomial coefficients ordered from low to high.
Returns

out : ndarray
 An array containing the complex roots of the polynomial series.
+ Array of the roots of the polynomial. If all the roots are real,
+ then so is the dtype of ``out``; otherwise, ``out``'s dtype is
+ complex.
+ See Also
+ 
+ chebroots
+
Examples

+ >>> import numpy.polynomial as P
+ >>> P.polyroots(P.polyfromroots((1,0,1)))
+ array([1., 0., 1.])
+ >>> P.polyroots(P.polyfromroots((1,0,1))).dtype
+ dtype('float64')
+ >>> j = complex(0,1)
+ >>> P.polyroots(P.polyfromroots((j,0,j)))
+ array([ 0.00000000e+00+0.j, 0.00000000e+00+1.j, 2.77555756e171.j])
"""
# cs is a trimmed copy
Modified: trunk/numpy/polynomial/polytemplate.py
===================================================================
 trunk/numpy/polynomial/polytemplate.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/polynomial/polytemplate.py 20100217 23:53:04 UTC (rev 8127)
@@ 1,5 +1,13 @@
"""Template for the Chebyshev and Polynomial classes.
+"""
+Template for the Chebyshev and Polynomial classes.
+This module houses a Python string module Template object (see, e.g.,
+http://docs.python.org/library/string.html#templatestrings) used by
+the `polynomial` and `chebyshev` modules to implement their respective
+`Polynomial` and `Chebyshev` classes. It provides a mechanism for easily
+creating additional specific polynomial classes (e.g., Legendre, Jacobi,
+etc.) in the future, such that all these classes will have a common API.
+
"""
import string
import sys
Modified: trunk/numpy/polynomial/polyutils.py
===================================================================
 trunk/numpy/polynomial/polyutils.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/polynomial/polyutils.py 20100217 23:53:04 UTC (rev 8127)
@@ 1,30 +1,34 @@
"""Utililty functions for polynomial modules.
+"""
+Utililty objects for the polynomial modules.
This modules provides errors, warnings, and a polynomial base class along
with some common routines that are used in both the polynomial and
chebyshev modules.
+This module provides: error and warning objects; a polynomial base class;
+and some routines used in both the `polynomial` and `chebyshev` modules.
Errors

 PolyError  base class for errors
 PolyDomainError  mismatched domains
+Error objects
+
+ `PolyError`  base class for this subpackage's errors.
+ `PolyDomainError`  raised when domains are "mismatched."
Warnings

 RankWarning  issued by least squares fits to warn of deficient rank
+Warning objects
+
+ `RankWarning`  raised by a leastsquares fit when a rankdeficient
+ matrix is encountered.
Base Class
+Base class

 PolyBase  Base class for the Polynomial and Chebyshev classes.
+ `PolyBase`  The base class for the `Polynomial` and `Chebyshev`
+ classes.
Functions

 as_series  turns list of array_like into 1d arrays of common type
 trimseq  removes trailing zeros
 trimcoef  removes trailing coefficients less than given magnitude
 getdomain  finds appropriate domain for collection of points
 mapdomain  maps points between domains
 mapparms  parameters of the linear map between domains
+ `as_series`  turns a list of array_likes into 1D arrays of common
+ type.
+ `trimseq`  removes trailing zeros.
+ `trimcoef`  removes trailing coefficients that are less than a given
+ magnitude (thereby removing the corresponding terms).
+ `getdomain`  returns a domain appropriate for a given set of abscissae.
+ `mapdomain`  maps points between domains.
+ `mapparms`  parameters of the linear map between domains.
"""
from __future__ import division
@@ 109,30 +113,45 @@
def as_series(alist, trim=True) :
 """Return arguments as a list of 1d arrays.
+ """
+ Return argument as a list of 1d arrays.
 The return type will always be an array of double, complex double. or
 object.
+ The returned list contains array(s) of dtype double, complex double, or
+ object. A 1d argument of shape ``(N,)`` is parsed into ``N`` arrays of
+ size one; a 2d argument of shape ``(M,N)`` is parsed into ``M`` arrays
+ of size ``N`` (i.e., is "parsed by row"); and a higher dimensional array
+ raises a Value Error if it is not first reshaped into either a 1d or 2d
+ array.
Parameters

 [a1, a2,...] : list of array_like.
 The arrays must have no more than one dimension when converted.
 trim : boolean
+ a : array_like
+ A 1 or 2d array_like
+ trim : boolean, optional
When True, trailing zeros are removed from the inputs.
When False, the inputs are passed through intact.
Returns

[a1, a2,...] : list of 1darrays
 A copy of the input data as a 1darrays.
+ A copy of the input data as a list of 1d arrays.
Raises

ValueError :
 Raised when an input can not be coverted to 1d array or the
 resulting array is empty.
+ Raised when `as_series` cannot convert its input to 1d arrays, or at
+ least one of the resulting arrays is empty.
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> a = np.arange(4)
+ >>> P.as_series(a)
+ [array([ 0.]), array([ 1.]), array([ 2.]), array([ 3.])]
+ >>> b = np.arange(6).reshape((2,3))
+ >>> P.as_series(b)
+ [array([ 0., 1., 2.]), array([ 3., 4., 5.])]
+
"""
arrays = [np.array(a, ndmin=1, copy=0) for a in alist]
if min([a.size for a in arrays]) == 0 :
@@ 161,25 +180,48 @@
def trimcoef(c, tol=0) :
 """Remove small trailing coefficients from a polynomial series.
+ """
+ Remove "small" "trailing" coefficients from a polynomial.
+ "Small" means "small in absolute value" and is controlled by the
+ parameter `tol`; "trailing" means highest order coefficient(s), e.g., in
+ ``[0, 1, 1, 0, 0]`` (which represents ``0 + x + x**2 + 0*x**3 + 0*x**4``)
+ both the 3rd and 4th order coefficients would be "trimmed."
+
Parameters

c : array_like
 1d array of coefficients, ordered from low to high.
 tol : number
 Trailing elements with absolute value less than tol are removed.
+ 1d array of coefficients, ordered from lowest order to highest.
+ tol : number, optional
+ Trailing (i.e., highest order) elements with absolute value less
+ than or equal to `tol` (default value is zero) are removed.
Returns

trimmed : ndarray
 1_d array with tailing zeros removed. If the resulting series would
 be empty, a series containing a singel zero is returned.
+ 1d array with trailing zeros removed. If the resulting series
+ would be empty, a series containing a single zero is returned.
Raises

 ValueError : if tol < 0
+ ValueError
+ If `tol` < 0
+ See Also
+ 
+ trimseq
+
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> P.trimcoef((0,0,3,0,5,0,0))
+ array([ 0., 0., 3., 0., 5.])
+ >>> P.trimcoef((0,0,1e3,0,1e5,0,0),1e3) # item == tol is trimmed
+ array([ 0.])
+ >>> i = complex(0,1) # works for complex
+ >>> P.trimcoef((3e4,1e3*(1i),5e4,2e5*(1+i)), 1e3)
+ array([ 0.0003+0.j , 0.00100.001j])
+
"""
if tol < 0 :
raise ValueError("tol must be nonnegative")
@@ 192,29 +234,42 @@
return c[:ind[1] + 1].copy()
def getdomain(x) :
 """Determine suitable domain for given points.
+ """
+ Return a domain suitable for given abscissae.
 Find a suitable domain in which to fit a function defined at the points
 `x` with a polynomial or Chebyshev series.

+ Find a domain suitable for a polynomial or Chebyshev series
+ defined at the values supplied.
+
Parameters

x : array_like
 1D array of points whose domain will be determined.
+ 1d array of abscissae whose domain will be determined.
Returns

domain : ndarray
 1D ndarray containing two values. If the inputs are complex, then
 the two points are the corners of the smallest rectangle alinged
 with the axes in the complex plane containing the points `x`. If
 the inputs are real, then the two points are the ends of the
 smallest interval containing the points `x`,
+ 1d array containing two values. If the inputs are complex, then
+ the two returned points are the lower left and upper right corners
+ of the smallest rectangle (aligned with the axes) in the complex
+ plane containing the points `x`. If the inputs are real, then the
+ two points are the ends of the smallest interval containing the
+ points `x`.
See Also

mapparms, mapdomain
+ Examples
+ 
+ >>> from numpy.polynomial import polyutils as pu
+ >>> points = np.arange(4)**2  5; points
+ array([5, 4, 1, 4])
+ >>> pu.getdomain(points)
+ array([5., 4.])
+ >>> c = np.exp(complex(0,1)*np.pi*np.arange(12)/6) # unit circle
+ >>> pu.getdomain(c)
+ array([1.1.j, 1.+1.j])
+
"""
[x] = as_series([x], trim=False)
if x.dtype.char in np.typecodes['Complex'] :
@@ 225,27 +280,45 @@
return np.array((x.min(), x.max()))
def mapparms(old, new) :
 """Linear map between domains.
+ """
+ Linear map parameters between domains.
 Return the parameters of the linear map ``off + scl*x`` that maps the
 `old` domain to the `new` domain. The map is defined by the requirement
 that the left end of the old domain map to the left end of the new
 domain, and similarly for the right ends.
+ Return the parameters of the linear map ``offset + scale*x`` that maps
+ `old` to `new` such that ``old[i] > new[i]``, ``i = 0, 1``.
Parameters

old, new : array_like
 The two domains should convert as 1D arrays containing two values.
+ Each domain must (successfully) convert to a 1d array containing
+ precisely two values.
Returns

 off, scl : scalars
 The map `=``off + scl*x`` maps the first domain to the second.
+ offset, scale : scalars
+ The map ``L(x) = offset + scale*x`` maps the first domain to the
+ second.
See Also

getdomain, mapdomain
+ Notes
+ 
+ Also works for complex numbers, and thus can be used to calculate the
+ parameters required to map any line in the complex plane to any other
+ line therein.
+
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> P.mapparms((1,1),(1,1))
+ (0.0, 1.0)
+ >>> P.mapparms((1,1),(1,1))
+ (0.0, 1.0)
+ >>> i = complex(0,1)
+ >>> P.mapparms((i,1),(1,i))
+ ((1+1j), (1+0j))
+
"""
oldlen = old[1]  old[0]
newlen = new[1]  new[0]
@@ 254,30 +327,66 @@
return off, scl
def mapdomain(x, old, new) :
 """Apply linear map to input points.

 The linear map of the form ``off + scl*x`` that takes the `old` domain
 to the `new` domain is applied to the points `x`.
+ """
+ Apply linear map to input points.
+ The linear map ``offset + scale*x`` that maps `old` to `new` is applied
+ to the points `x`.
+
Parameters

x : array_like
 Points to be mapped
+ Points to be mapped.
old, new : array_like
 The two domains that determin the map. They should both convert as
 1D arrays containing two values.
+ The two domains that determine the map. Each must (successfully)
+ convert to 1d arrays containing precisely two values.

Returns

 new_x : ndarray
 Array of points of the same shape as the input `x` after the linear
 map defined by the two domains is applied.
+ x_out : ndarray
+ Array of points of the same shape as `x`, after application of the
+ linear map between the two domains.
See Also

getdomain, mapparms
+ Notes
+ 
+ Effectively, this implements:
+
+ .. math ::
+ x\\_out = new[0] + m(x  old[0])
+
+ where
+
+ .. math ::
+ m = \\frac{new[1]new[0]}{old[1]old[0]}
+
+ Examples
+ 
+ >>> from numpy import polynomial as P
+ >>> old_domain = (1,1)
+ >>> new_domain = (0,2*np.pi)
+ >>> x = np.linspace(1,1,6); x
+ array([1. , 0.6, 0.2, 0.2, 0.6, 1. ])
+ >>> x_out = P.mapdomain(x, old_domain, new_domain); x_out
+ array([ 0. , 1.25663706, 2.51327412, 3.76991118, 5.02654825,
+ 6.28318531])
+ >>> x  P.mapdomain(x_out, new_domain, old_domain)
+ array([ 0., 0., 0., 0., 0., 0.])
+
+ Also works for complex numbers (and thus can be used to map any line in
+ the complex plane to any other line therein).
+
+ >>> i = complex(0,1)
+ >>> old = (1  i, 1 + i)
+ >>> new = (1 + i, 1  i)
+ >>> z = np.linspace(old[0], old[1], 6); z
+ array([1.01.j , 0.60.6j, 0.20.2j, 0.2+0.2j, 0.6+0.6j, 1.0+1.j ])
+ >>> new_z = P.mapdomain(z, old, new); new_z
+ array([1.0+1.j , 0.6+0.6j, 0.2+0.2j, 0.20.2j, 0.60.6j, 1.01.j ])
+
"""
[x] = as_series([x], trim=False)
off, scl = mapparms(old, new)
Modified: trunk/numpy/testing/utils.py
===================================================================
 trunk/numpy/testing/utils.py 20100217 23:42:42 UTC (rev 8126)
+++ trunk/numpy/testing/utils.py 20100217 23:53:04 UTC (rev 8127)
@@ 1081,23 +1081,54 @@
assert(sys.getrefcount(i) >= rc)
def assert_array_almost_equal_nulp(x, y, nulp=1):
 """Compare two arrays relatively to their spacing. It is a relatively
 robust method to compare two arrays whose amplitude is variable.
+ """
+ Compare two arrays relatively to their spacing.
 Note
 
 An assertion is raised if the following condition is not met:
+ This is a relatively robust method to compare two arrays whose amplitude
+ is variable.
+ Parameters
+ 
+ x, y : array_like
+ Input arrays.
+ nulp : int, optional
+ The maximum number of unit in the last place for tolerance (see Notes).
+ Default is 1.
+
+ Returns
+ 
+ None
+
+ Raises
+ 
+ AssertionError
+ If the spacing between `x` and `y` for one or more elements is larger
+ than `nulp`.
+
+ See Also
+ 
+ assert_array_max_ulp : Check that all items of arrays differ in at most
+ N Units in the Last Place.
+ spacing : Return the distance between x and the nearest adjacent number.
+
+ Notes
+ 
+ An assertion is raised if the following condition is not met::
+
abs(x  y) <= nulps * spacing(max(abs(x), abs(y)))
 Parameters
 
 x: array_like
 first input array
 y: array_like
 second input array
 nulp: int
 max number of unit in the last place for tolerance (see Note)
+ Examples
+ 
+ >>> x = np.array([1., 1e10, 1e20])
+ >>> eps = np.finfo(x.dtype).eps
+ >>> np.testing.assert_array_almost_equal_nulp(x, x*eps/2 + x)
+
+ >>> np.testing.assert_array_almost_equal_nulp(x, x*eps + x)
+ 
+ Traceback (most recent call last):
+ ...
+ AssertionError: X and Y are not equal to 1 ULP (max is 2)
+
"""
import numpy as np
ax = np.abs(x)
@@ 1112,8 +1143,41 @@
raise AssertionError(msg)
def assert_array_max_ulp(a, b, maxulp=1, dtype=None):
 """Given two arrays a and b, check that every item differs in at most N
 Unit in the Last Place."""
+ """
+ Check that all items of arrays differ in at most N Units in the Last Place.
+
+ Parameters
+ 
+ a, b : array_like
+ Input arrays to be compared.
+ maxulp : int, optional
+ The maximum number of units in the last place that elements of `a` and
+ `b` can differ. Default is 1.
+ dtype : dtype, optional
+ Datatype to convert `a` and `b` to if given. Default is None.
+
+ Returns
+ 
+ ret : ndarray
+ Array containing number of representable floating point numbers between
+ items in `a` and `b`.
+
+ Raises
+ 
+ AssertionError
+ If one or more elements differ by more than `maxulp`.
+
+ See Also
+ 
+ assert_array_almost_equal_nulp : Compare two arrays relatively to their
+ spacing.
+
+ Examples
+ 
+ >>> a = np.linspace(0., 1., 100)
+ >>> res = np.testing.assert_array_max_ulp(a, np.arcsin(np.sin(a)))
+
+ """
import numpy as np
ret = nulp_diff(a, b, dtype)
if not np.all(ret <= maxulp):
@@ 1282,11 +1346,29 @@
self._module.showwarning = self._showwarning
def assert_warns(warning_class, func, *args, **kw):
 """Fail unless a warning of class warning_class is thrown by callable when
+ """
+ Fail unless the given callable throws the specified warning.
+
+ A warning of class warning_class should be thrown by the callable when
invoked with arguments args and keyword arguments kwargs.

If a different type of warning is thrown, it will not be caught, and the
test case will be deemed to have suffered an error.
+
+ Parameters
+ 
+ warning_class : class
+ The class defining the warning that `func` is expected to throw.
+ func : callable
+ The callable to test.
+ \\*args : Arguments
+ Arguments passed to `func`.
+ \\*\\*kwargs : Kwargs
+ Keyword arguments passed to `func`.
+
+ Returns
+ 
+ None
+
"""
# XXX: once we may depend on python >= 2.6, this can be replaced by the
More information about the Numpysvn
mailing list