sø., 21.02.2010 kl. 13.25 +0100, skrev Vinzent Steinberg:
> 2010/2/21 Øyvind Jensen <jensen.oyv...@gmail.com>:
> > The keyword pretty_indices used to be boolean, but is now a dict of lists
> > containing letters to label the new dummy indices.  This allows the user 
> > much
> > better control over the resulting expression.
> >
> > Docstring and doctests updated accordingly.
> > ---
> >  sympy/physics/secondquant.py |  104 
> > +++++++++++++++++++++++++++---------------
> >  1 files changed, 67 insertions(+), 37 deletions(-)
> >
> > diff --git a/sympy/physics/secondquant.py b/sympy/physics/secondquant.py
> > index 6a5fa60..9285f83 100644
> > --- a/sympy/physics/secondquant.py
> > +++ b/sympy/physics/secondquant.py
> > @@ -2541,7 +2541,7 @@ def _substitute(expr, ordered_dummies, arg_iterator, 
> > **require):
> >     return result
> >
> >
> > -def substitute_dummies(expr, new_indices=False, reverse_order=True, 
> > pretty_indices=True):
> > +def substitute_dummies(expr, new_indices=False, reverse_order=True, 
> > pretty_indices={}):
> >     """
> >     Collect terms by substitution of dummy variables.
> >
> > @@ -2551,19 +2551,22 @@ def substitute_dummies(expr, new_indices=False, 
> > reverse_order=True, pretty_indic
> >     The idea is to substitute all dummy variables consistently depending on
> >     position in the term.  For each term, we collect a sequence of all dummy
> >     variables, where the order is determined by index position.  These 
> > indices
> > -    are then substituted consistently in each term.  E.g.
> > +    are then substituted consistently in each term.
> > +
> > +    Examples
> > +    ========
> >
> >     >>> from sympy import symbols, Function
> >     >>> from sympy.physics.secondquant import substitute_dummies
> > -    >>> a,b = symbols('ab',dummy=True)
> > -    >>> c,d = symbols('cd',dummy=True)
> > +    >>> a,b,c,d = symbols('abcd',dummy=True, above_fermi=True)
> > +    >>> i,j = symbols('ij',dummy=True, below_fermi=True)
> >     >>> f = Function('f')
> >
> >     >>> expr = f(a,b) + f(c,d); expr
> >     f(_a, _b) + f(_c, _d)
> >
> > -    Since a, b, c and d are summation indices, this can be simplified to a
> > -    single summation term with a factor 2
> > +    Since a, b, c and d are equivalent summation indices, the expression 
> > can be
> > +    simplified to a single term (for which the dummy indices are still 
> > summed over)
> >
> >     >>> substitute_dummies(expr, reverse_order=False)
> >     2*f(_a, _b)
> > @@ -2577,37 +2580,67 @@ def substitute_dummies(expr, new_indices=False, 
> > reverse_order=True, pretty_indic
> >     >>> substitute_dummies(expr, reverse_order=True)
> >     2*f(_b, _a)
> >
> > -    """
> > +    Controlling output
> > +    ==================
> >
> > -    # pretty_indices = True    # Prettier
> > -    # pretty_indices = False   # Easier to debug
> > +    By default the dummy symbols that are already present in the expression
> > +    will be reused.  However, if new_indices=True, new dummies will be
> > +    generated and inserted.
> >
> > +    The keyword 'pretty_indices' can be used to control this generation of 
> > new
> > +    symbols.
> >
> > -    if not pretty_indices:
> > -        def _i(number):
> > -            return 'i_'+str(number)
> > -        def _a(number):
> > -            return 'a_'+str(number)
> > -        def _p(number):
> > -            return 'p_'+str(number)
> > +    By default the new dummies will be generated on the form i_1, i_2, a_1,
> > +    etc.  If you supply a dictionary with key:value pairs in the form:
> >
> > +        { index_group: string_of_letters }
> > +
> > +    The letters will be used as labels for the new dummy symbols.  The
> > +    index_groups must be one of 'above', 'below' or 'general'.
> > +
> > +    >>> expr = f(a,b,i,j)
> > +    >>> my_dummies = { 'above':'st','below':'uv' }
> > +    >>> substitute_dummies(expr, new_indices=True, 
> > pretty_indices=my_dummies)
> > +    f(_t, _s, _v, _u)
> > +
> > +    If we run out of letters, or if there is no keyword for some 
> > index_group
> > +    the default dummy generator will be used as a fallback:
> > +
> > +    >>> p,q = symbols('pq',dummy=True)  # general indices
> > +    >>> expr = f(p,q)
> > +    >>> substitute_dummies(expr, new_indices=True, 
> > pretty_indices=my_dummies)
> > +    f(_p_1, _p_0)
> > +
> > +    """
> > +
> > +    # setup the replacing dummies
> > +    if new_indices:
> > +        letters_above  = pretty_indices.get('above',"")
> > +        letters_below  = pretty_indices.get('below',"")
> > +        letters_general= pretty_indices.get('general',"")
> > +        len_above  = len(letters_above)
> > +        len_below  = len(letters_below)
> > +        len_general= len(letters_general)
> >
> > -    else:
> >         def _i(number):
> > -            if number<5:
> > -                return "klmno"[number]
> > -            else:
> > -                return 'o_'+str(number-5)
> > +            try:
> > +                return letters_below[number]
> > +            except IndexError:
> > +                return 'i_'+str(number-len_below)
> > +
> >         def _a(number):
> > -            if number<6:
> > -                return "cdefgh"[number]
> > -            else:
> > -                return 'h_'+str(number-6)
> > +            try:
> > +                return letters_above[number]
> > +            except IndexError:
> > +                return 'a_'+str(number-len_above)
> > +
> >         def _p(number):
> > -            if number<7:
> > -                return "tuvwxyz"[number]
> > -            else:
> > -                return 'z_'+str(number-7)
> > +            try:
> > +                return letters_general[number]
> > +            except IndexError:
> > +                return 'p_'+str(number-len_general)
> > +
> > +
> >
> >     # reverse iterator for use in _get_dummies()
> >     if reverse_order:
> > @@ -2632,21 +2665,20 @@ def arg_iterator(seq):
> >     dummies = [ d for d in expr.atoms() if isinstance(d,Dummy) ]
> >     dummies.sort()
> >
> > +    # generate lists with the dummies we will insert
> >     a = i = p = 0
> >     for d in dummies:
> >         assum = d.assumptions0
> >         assum["dummy"]=True
> > +
> >         if assum.get("above_fermi"):
> > -            sym = _a(a)
> > -            a +=1
> > +            if new_indices: sym = _a(a); a +=1
> >             l1 = aboves
> >         elif assum.get("below_fermi"):
> > -            sym = _i(i)
> > -            i +=1
> > +            if new_indices: sym = _i(i); i +=1
> >             l1 = belows
> >         else:
> > -            sym = _p(p)
> > -            p +=1
> > +            if new_indices: sym = _p(p); p +=1
> >             l1 = generals
> >
> >         if new_indices:
> > @@ -2655,8 +2687,6 @@ def arg_iterator(seq):
> >             l1.append(d)
> >
> >
> > -
> > -
> >     cases = (
> >             ({'above_fermi':True}, aboves),
> >             ({'below_fermi':True}, belows),
> > --
> > 1.6.5
> >
> > --
> > You received this message because you are subscribed to the Google Groups 
> > "sympy-patches" group.
> > To post to this group, send email to sympy-patc...@googlegroups.com.
> > To unsubscribe from this group, send email to 
> > sympy-patches+unsubscr...@googlegroups.com.
> > For more options, visit this group at 
> > http://groups.google.com/group/sympy-patches?hl=en.
> 
> I would prefer if this would use the new assumptions system. Or should
> 'above_fermi' etc. be tied to symbols? The rest of the patches looks
> fine to me, assuming all tests pass.
> 
> Vinzent
> 
I agree, that we should move to the new assumption system, but that does
require a major rewrite of the second quantization module.  This patch
series adresses the porcelain rather than the plumbing.

The assumption 'above_fermi' is currently directly tied to the symbol,
but it just means that 'symbol>fermi_level'.  That information should
ideally be stored in the global assumption database.  I am eager to
start the transition to the new system, but I am too busy at moment.

Øyvind

-- 
You received this message because you are subscribed to the Google Groups 
"sympy-patches" group.
To post to this group, send email to sympy-patc...@googlegroups.com.
To unsubscribe from this group, send email to 
sympy-patches+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/sympy-patches?hl=en.

Reply via email to