[Python-talk] Generator Question

Bruce Labitt bruce.labitt at myfairpoint.net
Wed Aug 12 21:14:20 EDT 2009


Kent Johnson wrote:
>
> It sounds fine :-) Beazley's chained generators might work very well for you
> - initial generator creates the arrays
> - next generator computes FFT
> - next compute power
>
> Output goes to the optimizer to make a decision, then start over.
>
> One advantage to breaking it up this way is you can test each step
> independently. You need a function to generate an array, a function to
> compute FFT, and a function to compute power. Each of these can be
> separately developed and tested. Then you have
>
> seeds = [ <some sequence that defines the arrays to be created> ]
> score = 0
> while score < threshold:
>   arrays = (make_array(seed) for seed in seeds)
>   fft_results = (compute_fft(array) for array in arrays)
>   powers = (compute_power(result) for result in fft_results)
>   score, seeds = optimize(powers)
>
> Kent
>
>   
It sounds so easy when you say it this way. vbg. 

Right now I'm trying to wrap my mind around how to just code the 
make_array part.  For some reason, I'm having trouble with the concept 
of some of the values inside the function being persistent.

Say I have an array which is 100 elements.  I need to generate a second 
array which is also 100 elements, but it is composed of 25 repetitions 
of 4 elements of a different array.  ( f[0], f[1], f[2], f[3] ) I then 
multiply the two arrays.  The result is returned by the generator.  The 
next time the generator is called, I use the first array again, but have 
to create a 'new' second array which is 25 repetitions of f[4], 25 
repetitions of f[5],..., 25 repetitions of f[7].

I understand the repetitions and concatenation, which is very easy in 
scipy/numpy.  It is the persistence which I don't yet understand.

In the above example, it is clear that the first array doesn't need to 
be inside the generator, although it may be convenient. 

Here is a snippet off the top of my head - no real thought into this 
yet, but...

from numpy import ones, concatenate # don't know which module size is in...

def make_array( freqsequence, firstarray, dt, otherparams ):
    n = freqsequence.size
    idx = 0
    quartarray = ones(firstarray.size/4) # makes an array of ones
    t = dt*range(n)
    while idx<n/4:
       freqarray = freqsequence[idx]*quartarray
       freqarray = concatenate([freqarray, 
freqsequence[idx+1]*quartarray],1)
       freqarray = concatenate([freqarray, 
freqsequence[idx+2]*quartarray],1)
       freqarray = concatenate([freqarray, 
freqsequence[idx+3]*quartarray],1)
       yield firstarray*exp(2.0*pi*freqarray*t*1j)
       t = t + n*dt
       idx = idx+1

Forgive the concatenations, there is a better way of doing this...  
Which I will figure out about 50 microseconds after I hit send.

Would this work?  Assuming of course that freqsequence.size is really 
divisible by 4.

Will the values for t keep on increasing continuously?  At least until 
we run out of elements in freqsequence?

Am I pointed in the right direction?  I probably would create firstarray 
from a function call rather than passing in the array.  In real life 
first array is on the order of a million points.

Thanks Again,
Bruce


   



More information about the Python-talk mailing list