Пример #1
0
def load_rcd(filename):
    '''
    save intracellular signal
    hirschlab binary format
    '''
    from scipy import io
    byteswap = (sys.byteorder=='big')
    fil = open(filename,'r')
    sig_size = io.fread(fil,1,'i','d',byteswap)
    sig = io.fread(fil,sig_size,'h','d',byteswap)/ 32768*5;
    sig = D.TimeSeries(sig,samplingrate=10**4)
    sig.i.t1 = float(io.fread(fil,1,'f','d',byteswap))
    fil.close()
    if len(sig)!=sig_size: assert 0, 'wrong file size'
    return sig
Пример #2
0
def fort_read(fid, num, read_type, mem_type=None, byteswap=0, length=4):
    """read fortran unformatted binary data

    the meaning of argumetn is the same as scipy.io.fread except for `length',
    which is is the size (in bytes) of header/footer.
    """
    if mem_type == None:
        mem_type = read_type
    if length == 0: # without header/footer
        return io.fread(fid, num, read_type, mem_type, byteswap)
    # with header/footer
    fid.read(length) # header
    result = io.fread(fid, num, read_type, mem_type, byteswap)
    fid.read(length) # footer
    return result
Пример #3
0
def _get_block_headers(fhead, chan_info):
    '''
    Returns a matrix containing the SON data block headers for a
    channel.
    'fhead' is a FileHeader instance, and 'chan_info' is a
    ChannelInfo instance.

    The returned header in memory contains, for each disk block,
    a column with rows 0-4 representing:
    Offset to start of block in file
    Start time in clock ticks
    End time in clock ticks
    Chan number
    Items
    '''
    from scipy import io, zeros, arange, take
    if chan_info.firstblock == -1:
        raise ValueError('No data on channel ' + str(chan_info.chan))
    succ_block = 1
    # Pre-allocate memory for header data:
    header = zeros([6, chan_info.blocks], int)
    # Get first data block:
    fhead.fid.seek(chan_info.firstblock)
    # Last and next block pointers, start and end times in clock ticks
    header[0:4, 0] = io.fread(fhead.fid, 4, 'l')
    # Channel number and number of items in block:
    header[4:6, 0] = io.fread(fhead.fid, 2, 'h')
    # If only one block:
    if header[succ_block, 0] == -1:
        header[0, 0] = int(chan_info.firstblock)
    # Loop if more blocks:
    else:
        fhead.fid.seek(header[succ_block, 0])
        for i in arange(1, chan_info.blocks):
            header[0:4, i] = io.fread(fhead.fid, 4, 'l')
            header[4:6, i] = io.fread(fhead.fid, 2, 'h')
            if header[succ_block, i] > 0:
                fhead.fid.seek(header[succ_block, i])
            header[0, i-1] = header[0, i]
        # Replace pred_block for previous column:
        header[0, -1] = header[1, -2]
    # Delete succ_block data:
    header = take(header, (0,2,3,4,5), axis=0)
    return header
Пример #4
0
def _get_block_headers(fhead, chan_info):
    '''
    Returns a matrix containing the SON data block headers for a
    channel.
    'fhead' is a FileHeader instance, and 'chan_info' is a
    ChannelInfo instance.

    The returned header in memory contains, for each disk block,
    a column with rows 0-4 representing:
    Offset to start of block in file
    Start time in clock ticks
    End time in clock ticks
    Chan number
    Items
    '''
    from scipy import io, zeros, arange, take
    if chan_info.firstblock == -1:
        raise ValueError('No data on channel ' + str(chan_info.chan))
    succ_block = 1
    # Pre-allocate memory for header data:
    header = zeros([6, chan_info.blocks], int)
    # Get first data block:
    fhead.fid.seek(chan_info.firstblock)
    # Last and next block pointers, start and end times in clock ticks
    header[0:4, 0] = io.fread(fhead.fid, 4, 'l')
    # Channel number and number of items in block:
    header[4:6, 0] = io.fread(fhead.fid, 2, 'h')
    # If only one block:
    if header[succ_block, 0] == -1:
        header[0, 0] = int(chan_info.firstblock)
    # Loop if more blocks:
    else:
        fhead.fid.seek(header[succ_block, 0])
        for i in arange(1, chan_info.blocks):
            header[0:4, i] = io.fread(fhead.fid, 4, 'l')
            header[4:6, i] = io.fread(fhead.fid, 2, 'h')
            if header[succ_block, i] > 0:
                fhead.fid.seek(header[succ_block, i])
            header[0, i - 1] = header[0, i]
        # Replace pred_block for previous column:
        header[0, -1] = header[1, -2]
    # Delete succ_block data:
    header = take(header, (0, 2, 3, 4, 5), axis=0)
    return header
Пример #5
0
def TECanalysis():
    A_coef = 80.6
    c_speed = 2.998e8   # speed of light
    fr = 50.0e6         # basic frequency
    R=6378.14 #Earth radius, km
    hi=300 #height of ionosphere in a singe thin layer model, km
    h2407=989.2 #average altitude of Cosmos 2407, km
    h2414=948.5 #average altitude of Cosmos 2414, km
    h2429=993.3 #average altitude of Cosmos 2429, km
    T2407=104.7*60 #orbital period of Cosmos 2407, s
    T2414=103.8*60 #orbital period of Cosmos 2414, s
    T2429=104.7*60 #orbital period of Cosmos 2429, s
    ratio2407=14997.0/39992.0 #central frequencies ratio for Cosmos 2407
    ratio2414=14997.0/39992.0 #central frequencies ratio for Cosmos 2414
    ratio2429=15003.0/40008.0 #central frequencies ratio for Cosmos 2429
    halfband=16#halfband for the 400MHz ifft (should be divisible by 8)
    file150 = '_data150.dat'
    file400 = '_data400.dat'
    if os.path.exists(file400)& os.path.exists(file150):
        data_size = os.stat(file400)[6] # Get filesisze
        data_size = min(data_size, os.stat(file150)[6]) # Get filesize
    else:
        return
    sample_f = 125000.0
    nfft = 16384
    delta_f = sample_f / float(nfft)  #frequency resolution
#########################################################################################
    skip_sec = 0.0
    read_sec = 999.0
    maxelev = 80.0	#max elevation angle, deg
    sat = 2414
    if sat==2407:
	hs=h2407
	Ts=T2407
	ratio=ratio2407
    if sat==2414:
	hs=h2414
	Ts=T2414
	ratio=ratio2414
    if sat==2429:
	hs=h2429
	Ts=T2429
	ratio=ratio2429
    ws=2*pi/Ts #angular velocity, rad/s
    time0 = 734.0/2-skip_sec
    theta0 = -time0*ws #starting zenith angle in equatorial coordinates, rad
    print 'Starting zenith angle:',theta0/pi*180, 'deg. Initializing arrays...'
#########################################################################################
    if read_sec == 999.0:
        read_sec = float((data_size // (8 * sample_f)) - skip_sec)
    nskip_bytes = int((sample_f * skip_sec) // nfft) * nfft * 8
    ntdata = int((sample_f * read_sec) // nfft) * nfft
    nparam = ntdata / nfft * 2 -1 # Number of spectral data (half interleave)
    npfact = 128
    npst = nfft/npfact/4
    n_phase = ntdata / npfact      #Number of phase data for TEC evaluation (125000*128*<length_in_seconds>//16384)
    freq = arange(nfft, dtype = 'f') * delta_f - sample_f/2.0
    buf = arange(ntdata, dtype = 'F')
    ser = arange(nfft, dtype = 'D')
    fft_result = arange(nfft, dtype = 'D')
    power = arange(nfft, dtype = 'd')
    if150 = arange(nparam, dtype = 'l')
    if400 = arange(nparam, dtype = 'l')
    if400_a = arange(nparam, dtype = 'l')
    if400_b = arange(nparam, dtype = 'l')
    freq400 = arange(nparam, dtype = 'f')
    sigpow150 = arange(nparam, dtype = 'f')
    sigpow400 = arange(nparam, dtype = 'f')
    fil_ser150 = arange(n_phase, dtype = 'F')
    fil_ser400 = arange(n_phase, dtype = 'F')
    dif_p = arange(n_phase, dtype = 'f')
    pTEC = arange(n_phase, dtype = 'f')
    differ = arange(n_phase, dtype = 'f') * 0.0 # store the derivative
    phase_sec = arange(n_phase, dtype = 'f') * (float(npfact)/sample_f) + skip_sec
    param_sec = linspace(skip_sec, (nparam-1)*(float(0.5*nfft*ntdata/(ntdata-0.5*nfft))/sample_f) + skip_sec, nparam)
    theta = abs((phase_sec-skip_sec) * ws + theta0)
    d=sqrt(R*R+(R+hs)*(R+hs)-2*R*(R+hs)*cos(theta))
    slant_phi=arccos((R+hs)*sin(theta)/d)
    phi=arcsin(sin(slant_phi)*sin(maxelev/180.0*pi)) #take into account the satellite orbit inclination
    ksi=arcsin(R/(R+hi)*cos(phi))
    cos_ksi=cos(ksi)
    sec=1/cos_ksi
    arg=sec.argmin()

    plot(phase_sec,d)
    xlabel('time (s)')
    ylabel('distance (km)')
    title('distance to the satellite')
    savefig('_dist.png')
    close()

    plot(phase_sec,phi/pi*180)
    xlabel('time (s)')
    ylabel('phi (deg)')
    title('elevation angle')
    savefig('_phi.png')
    close()

    plot(phase_sec,sec)
    xlabel('time (s)')
    ylabel('sec(ksi)')
    title('secant effect')
    savefig('_sec.png')
    close()

    #print 'elevation at the start:',(slant_phi[0]/pi*180),' deg (',(phi[0]/pi*180),' deg after correcting for inclination)'
    #print 'elevation at the end:',(slant_phi[n_phase-1]/pi*180),' deg (',(phi[n_phase-1]/pi*180),' deg after correcting for inclination)'

    print 'Skipping',int(skip_sec),'seconds (',nskip_bytes,'bytes), reading',int(read_sec),'seconds containing',int(sample_f * read_sec),'samples, i.e.',int((sample_f * read_sec) // nfft),'bins of',nfft,'samples each for a total of',ntdata,'samples'

#########################################################################################
    f400 = open(file400, 'rb')
    f400.seek(nskip_bytes)
    print 'Buffering 400MHz data..'
    buf = io.fread(f400, ntdata, 'F')
    for ip in range(0, nparam):
        noffset = ip * nfft / 2
	if (ip % 2000) == 0:
		print int(float(ip)/nparam*25),'% complete'
        ser = buf[noffset: noffset+nfft]
	ser=ser*nfft*0.5 # scale the data so that the max value is 1
        fft_result = fft(ser)/nfft
        fft_result = fftpack.fftshift(fft_result)   #Rotate freq.
	fft_result[8192] = 0.0 + 0.0j
        power = fft_result.real **2 + fft_result.imag **2     #Signal power
	if (ip == 0):
		if400[ip] = power.argmax()
	if (ip > 0):
		if_init=if400[ip-1]-halfband #start one halfband off of the previous result
		if400[ip] = power[if_init: if_init+(2*halfband+1)].argmax() + if_init #look around +-halfband of the previous result#8514
    del buf
    f400.close
#########################################################################################
    fitfunc = lambda p, x: p[3] - p[0] * tanh(p[1] * (x - p[2])) # Target function
    errfunc = lambda p, x, y: fitfunc(p, x) - y # Distance to the target function

    P0 = [1070., 0.007, phase_sec[n_phase/2], 8216] # Initial guess for the parameters

    P1, success = optimize.leastsq(errfunc, P0[:], args=(param_sec, if400))
    #P1 = [9.11939377e+02, 4.50602823e-03, 3.14300432e+02, 8.49913297e+03]
    if400_a = fitfunc(P1, param_sec)
    #print P1

    for ip in range(0, nparam):
	if (if400[ip-1]-if400[ip])>1:
	    if400_b[ip]=int(if400_a[ip])
	else:
	    if400_b[ip]=if400[ip]

    figure()
    plot(param_sec, abs(if400_b-if400), 'r')
    savefig('_dif.png')
    close()

    figure()
    plot(param_sec, if400) # Plot the data and the fit
    plot(param_sec, if400_b) # Plot the data and the fit
    savefig('_initguess.png')
    close()

    for ip in range(0, nparam):
	if400[ip]=int(if400_b[ip])
#########################################################################################
    f400 = open(file400, 'rb')
    f400.seek(nskip_bytes)
    buf = io.fread(f400, ntdata, 'F')
    fil_ser400[0:npst] = 1.0 + 0.0j
    fil_ser400[-npst:] = 1.0 + 0.0j
    ifst = nfft/4
    ifen = ifst * 3
    for ip in range(0, nparam):
        noffset = ip * nfft / 2
	if (ip % 2000) == 0:
		print 25+int(float(ip)/nparam*25),'% complete'
        ser = buf[noffset: noffset+nfft]
	ser=ser*nfft*0.5 # scale the data so that the max value is 1
        fft_result = fft(ser)/nfft
        fft_result = fftpack.fftshift(fft_result)   #Rotate freq.
        power = fft_result.real **2 + fft_result.imag **2     #Signal power
        sigpow400[ip] = 0.0
        freq400[ip] = 0.0
        for j in range(if400[ip]-halfband, if400[ip]+(halfband+1)):#        for j in range(if400[ip]-2, if400[ip]+3):
            sigpow400[ip] = sigpow400[ip] + power[j]
            freq400[ip] = freq400[ip] + freq[j] * power[j]
        freq400[ip] = freq400[ip] / sigpow400[ip]
        ist = ip*npst*2 + npst
        ien = ist + npst*2
        if if400[ip]<8176 or if400[ip]>8208
            fft_result[:if400[ip]-halfband] = 0.0 + 0.0j
            fft_result[if400[ip]+(halfband+1):] = 0.0 + 0.0j
            fft_result = fftpack.ifftshift(fft_result)  #Rotate freq. back
            ser = ifft(fft_result)
            fil_ser400[ist:ien] = ser[ifst:ifen:npfact]
        else:
	    print 'Filling with dummy signal'
            fil_ser400[ist:ien] = 1.0 + 0.0j
    del buf
#########################################################################################
    f150 = open(file150, 'rb')
    f150.seek(nskip_bytes)
    print 'Buffering 150MHz data..'
    f150.seek(nskip_bytes, 0)
    buf = io.fread(f150, ntdata, 'F')
    fil_ser150[0:npst] = 1.0 + 0.0j
    fil_ser150[-npst:] = 1.0 + 0.0j
    ifst = nfft/4
    ifen = ifst * 3
    halfband=int(halfband/8*3) #set the halfband for 150MHz
    for ip in range(0, nparam):
        noffset = ip * nfft / 2
	if (ip % 1000) == 0:
		print 50+int(float(ip)/nparam*50),'% complete'

        ser = buf[noffset: noffset+nfft]
	ser=ser*nfft*0.5 # scale the data so that the max value is 1
        fft_result = fft(ser)/nfft
        fft_result = fftpack.fftshift(fft_result)   #Rotate freq.
        power = fft_result.real **2 + fft_result.imag **2     #Signal power
        if isnan(abs(freq400[ip])):
	     print 'freq400[',ip,'] = NaN, excluding...'
             freq400[ip]=freq400[ip-1] #exclude the NaNs
        if_init = int(((freq400[ip]*ratio) + sample_f/2.0)/delta_f) - halfband
        if150[ip] = power[if_init: if_init+2*halfband+1].argmax() + if_init
        sigpow150[ip] = 0.0
        for j in range(if150[ip]-halfband, if150[ip]+(halfband+1)):
            sigpow150[ip] = sigpow150[ip] + power[j]
        ist = ip*npst*2 + npst
        ien = ist + npst*2
        if if150[ip]<8186 or if150[ip]>8198: 
            fft_result[:if150[ip]-halfband] = 0.0 + 0.0j
            fft_result[if150[ip]+(halfband+1):] = 0.0 + 0.0j
            fft_result = fftpack.ifftshift(fft_result)  #Rotate freq. back
            ser = ifft(fft_result)
            fil_ser150[ist:ien] = ser[ifst:ifen:npfact]
        else:
	    print 'Filling with dummy signal'
            fil_ser150[ist:ien] = 1.0 + 0.0j
    del buf
#########################################################################################
    print 'Processing data..'
    for ip in range(0, n_phase):
        dif_p[ip] = angle((fil_ser150[ip] ** 8) / (fil_ser400[ip] ** 3))
    pTEC = unwrap(dif_p)#pTEC = unwrap(dif_p)/8.0
    coef = pi * A_coef / fr / c_speed * 55.0 / 24.0
    pTEC = pTEC / coef
    f_out1 = open('_TEC1.txt', 'w')
    f_out1.write('Non-corrected non-calibrated slant TEC (Total %d lines)\n' % n_phase)
    for ip in range(0, n_phase):
        write_buf = '%g %g %g %g\n' % (phase_sec[ip], pTEC[ip], fil_ser150[ip], fil_ser400[ip])
        f_out1.write(write_buf)
    f_out1.close

    span=min(arg, 10000) #if overhead point is closer than 10000 samples
    (correction,b) = polyfit(phase_sec[arg-span:arg+span],pTEC[arg-span:arg+span],1)
    print 'correction =', correction/1.0e16, 'TECU/s'
    #plot the overhead region
    plot(phase_sec[arg-span:arg+span],pTEC[arg-span:arg+span]/1.0e16)
    plot(phase_sec[arg-span:arg+span],(phase_sec[arg-span:arg+span]*correction+b)/1.0e16)
    xlabel('time (s)')
    ylabel('relative TEC (TECU)')
    title('Overhead slope fitting')
    savefig('_corr.png')
    close()
 
    #plot the measured TEC
    plot(phase_sec,pTEC/1.0e16)
    plot(phase_sec,(phase_sec*correction+b)/1.0e16)
    xlabel('time (s)')
    ylabel('relative TEC (TECU)')
    title('Non-corrected non-calibrated slant TEC')
    savefig('_TEC1.png')
    close()

    #plot the peaks
    plot(param_sec, if400)
    plot(param_sec, if400_a)
    xlabel('time (s)')
    ylabel('FFT index (out of 16384)')
    title('400MHz peak indices')
    savefig('_peaks400.png')
    close()

    plot(param_sec, if150)
    xlabel('time (s)')
    ylabel('FFT index (out of 16384)')
    title('150MHz peak indices')
    savefig('_peaks150.png')
    close()

    #plot signal power
    sigpow150 = 10.0 * log10(sigpow150)
    plot(param_sec, sigpow150)
    xlabel('time (s)')
    ylabel('signal power (dB)')
    title('150MHz signal power')
    savefig('_sigpow150.png')
    close()

    sigpow400 = 10.0 * log10(sigpow400)
    plot(param_sec, sigpow400)
    xlabel('time (s)')
    ylabel('signal power (dB)')
    title('400MHz signal power')
    savefig('_sigpow400.png')
    close()

#########################################################################################

    pTEC = pTEC - correction * phase_sec #correct for the phase incursion
    #plot the corrected TEC
    plot(phase_sec,pTEC/1.0e16)
    xlabel('time (s)')
    ylabel('relative TEC (TECU)')
    title('Corrected non-calibrated slant TEC')
    savefig('_TEC2.png')
    close()

    (calibration,b) = polyfit(sec,pTEC,1)
    print 'calibration =', calibration/1.0e16, 'TECU'
    #plot the TEC vs. sec
    plot(sec,pTEC/1.0e16,'.')
    plot(sec,(sec*calibration+b)/1.0e16)
    xlabel('secant (1/rad)')
    ylabel('relative TEC (TECU)')
    title('Finding the calibration')
    savefig('_cali.png')
    close()

    pTEC = pTEC+calibration*sec[arg]-average(pTEC[arg-span:arg+span]) #calibrate for flat Vertical TEC
    #plot the calibrated TEC
    plot(phase_sec,pTEC/1.0e16)
    xlabel('time (s)')
    ylabel('relative TEC (TECU)')
    title('Calibrated slant TEC')
    savefig('_TEC3.png')
    close()

    #compare the secant and slant TEC
    plot(phase_sec,(pTEC-min(pTEC))/max(pTEC-min(pTEC)))
    plot(phase_sec,(sec-min(sec))/max(sec-min(sec)))
    xlabel('time (s)')
    ylabel('normalized values')
    title('matching the secant with the slant TEC')
    savefig('_comp.png')
    close()

    vTEC = pTEC*cos(ksi)
    print 'average TEC =', average(vTEC)/1.0e16, 'TECU'

    plot(phase_sec,vTEC/1.0e16)
    xlabel('time (s)')
    ylabel('relative TEC (TECU)')
    title('vertical TEC')
    savefig('_TEC4.png')
    close()

    print 'theoretical TEC minimum is at', phase_sec[ksi.argmin()], 's'
    print '     actual TEC minimum is at', phase_sec[pTEC.argmin()], 's'

    f_out2 = open('_peaks.txt', 'w')
    f_out2.write('time, 400MHz peak, 150MHz peak (Total %d lines)\n' % nparam)
    for ip in range(0, nparam):
        write_buf = '%g %g %g\n' % (param_sec[ip], if400[ip], if150[ip])
        f_out2.write(write_buf)
    f_out2.close

    f150.close
    f400.close
Пример #6
0
def data(chan, start=None, stop=None, timeunits='seconds', as_float=True):
    '''
    Reads data from an event/marker channel (ie, Event, Marker, AdcMark,
    RealMark, or TextMark channel) from a SON file.

    'start', 'stop' set the data limits to be returned, in blocks. If
    only start is set, data from only that block will be returned.

    'timeunits' scales time to appropriate unit. Valid options are 'ticks',
    'microseconds', 'milliseconds' or 'seconds'.

    'as_float' only makes sense for AdcMark or RealMark channels. If
    True, returns data as floating point values (scaling and applying
    offset for Adc data). Else, data will be of type int16.
    '''
    from scipy import io, zeros
    fid = chan.fhead.fid
    blockheader = chan.blockheader
    size_of_header = 20  # Block header is 20 bytes long

    # ====================================
    # = Set start and end blocks to read =
    # ====================================
    if not start and not stop:
        start_block, end_block = 0, chan.info.blocks
    elif start and not stop:
        start_block, end_block = start - 1, start
    elif start and stop:
        start_block, end_block = start - 1, min([stop, chan.info.blocks])

    # == Sum of samples in required blocks ==
    n_items = sum(blockheader[4, start_block:end_block])

    # =============
    # = Read data =
    # =============
    #       + Event data +
    if chan.info.kind in [2, 3, 4]:
        # pre-allocate memory:
        timings = zeros(n_items, 'int32')
        # read data:
        pointer = 0
        for block in range(start_block, end_block):
            fid.seek(blockheader[0, block] + size_of_header)
            timings[pointer : pointer+blockheader[4, block]] = \
             io.fread(fid, blockheader[4, block], 'l')
            pointer += blockheader[4, block]

    #       + Marker data +
    elif chan.info.kind == 5:
        # pre-allocate memory:
        timings = zeros(n_items, 'int32')
        markers = zeros([n_items, 4], 'uint8')
        # read data:
        count = 0
        for block in range(start_block, end_block):
            # start of block:
            fid.seek(blockheader[0, block] + size_of_header)
            # loop for each marker:
            for i in range(blockheader[4, block]):
                timings[count] = io.fread(fid, 1, 'l')  # time
                markers[count] = io.fread(fid, 4, 'B')  # 4x marker bytes
                count += 1
        markers = [chr(x) for x in markers[:, 0]]

    #       + AdcMark data +
    elif chan.info.kind == 6:
        n_values = chan.info.n_extra / 2
        # 2 because 2 bytes per int16 value
        # pre-allocate memory:
        timings = zeros(n_items, 'int32')
        markers = zeros([n_items, 4], 'uint8')
        adc = zeros([n_items, n_values], 'int16')
        # read data:
        count = 0
        for block in range(start_block, end_block):
            # start of block:
            fid.seek(blockheader[0, block] + size_of_header)
            # loop for each marker:
            for i in range(blockheader[4, block]):
                timings[count] = io.fread(fid, 1, 'l')  # time
                markers[count] = io.fread(fid, 4, 'B')
                # 4x marker bytes
                adc[count] = io.fread(fid, n_values, 'h')
                count += 1
        if as_double:
            from _waveform import _adc_to_double
            adc = _adc_to_double(chan, adc)

    #       + RealMark data +
    elif chan.info.kind == 7:
        n_values = chan.info.n_extra / 4
        # each value has 4 bytes (single precision)
        # pre-allocate:
        timings = zeros(n_items, 'int32')
        markers = zeros([n_items, 4], 'uint8')
        real = zeros([n_items, n_values], 'single')
        # read data:
        count = 0
        for block in range(start_block, end_block):
            # start of block
            fid.seek(blockheader[0, block] + size_of_header)
            # loop for each marker
            for i in range(blockheader[4, block]):
                timings[count] = io.fread(fid, 1, 'l')  # time
                markers[count] = io.fread(fid, 4, 'B')
                # 4x marker bytes
                real[count] = io.fread(fid, n_values, 'f')
                count += 1
        if not as_double:
            from _waveform import _real_to_adc
            real = _real_to_adc(real)

    #       + TextMark data +
    elif chan.info.kind == 8:
        # pre-allocate memory:
        timings = zeros(n_items, 'int32')
        markers = zeros([n_items, 4], 'uint8')
        text = zeros([n_items, chan.info.n_extra], 'S1')
        # read data:
        count = 0
        for block in range(start_block, end_block):
            # start of block
            fid.seek(blockheader[0, block] + size_of_header)
            # loop for each marker
            for i in range(blockheader[4, block]):
                timings[count] = io.fread(fid, 1, 'l')  # time
                markers[count] = io.fread(fid, 4, 'B')
                # 4x marker bytes
                text[count] = io.fread(fid, chan.info.n_extra, 'c')
                count += 1

    # ================
    # = Convert time =
    # ================
    timings = chan.fhead._ticks_to_seconds(timings, timeunits)
    chan.info.timeunits = timeunits
    chan.info.epochs_str = '%i--%i of %i block(s)'\
      %(start_block+1, end_block, chan.info.blocks)

    # ===============
    # = Return data =
    # ===============
    if chan.info.kind in [2, 3, 4]:
        data = timings
    elif chan.info.kind == 5:
        data = zip(timings, markers)
    elif chan.info.kind == 6:
        data = zip(timings, markers, adc)
    elif chan.info.kind == 7:
        data = zip(timings, markers, real)
    elif chan.info.kind == 8:
        data = zip(timings, markers, text)
    return data
Пример #7
0
for harmnum in range(1, numharm+1):
    print "Computing harmonic", harmnum
    ldr = dr * harmnum
    ldz = dz * harmnum
    lor = startr * harmnum
    loz = 0.0 - (numzs-1)/2 * ldz
    rs = N.arange(numrs) * ldr + lor
    zs = N.arange(numzs) * ldz + loz
    if harmnum==1:
        rs0, zs0 = rs[:], zs[:]
    lo_file_r = int(rs.min()) - 1000
    hi_file_r = int(rs.max()) + 1000

    # Read and normalize the raw spectrum
    infile.seek(lo_file_r * 8, 0)
    fftamps = fread(infile, hi_file_r-lo_file_r+1, 'F')
    fftpows = spectralpower(fftamps)
    pownorm = 1.0 / (1.442695 * N.median(fftpows))
    fftamps *= sqrt(pownorm)

    ffd = ffdot_plane(fftamps, lor-lo_file_r, ldr, numrs, loz, ldz, numzs)
    ffd_pows = (ffd * ffd.conj()).real
    ffdps.append(ffd_pows)
    if (harmnum==1):
        sumpows = N.zeros_like(ffd_pows)
    sumpows += ffd_pows

    argmax = ffd_pows.argmax()
    maxvals.append(ffd_pows.max())
    maxargs.append((argmax / numrs, argmax % numrs))
    print "  Maximum power for harmonic %d = %.2f"%(harmnum, maxvals[-1])
Пример #8
0
 def __init__(self, filename):
     from scipy import io, zeros
     self.name = filename
     self.fid = open(filename, 'rb')
     self.fid.seek(0)
     self.system_id   = io.fread(self.fid, 1, 'h')
     self.copyright  = self.fid.read(10)
     self.creator    = self.fid.read(8)
     self.us_per_time  = io.fread(self.fid, 1, 'h')
     self.time_per_adc = io.fread(self.fid, 1, 'h')
     self.filestate  = io.fread(self.fid, 1, 'h')
     self.first_data  = io.fread(self.fid, 1, 'l')
     self.channels   = io.fread(self.fid, 1, 'h')
     self.chan_size   = io.fread(self.fid, 1, 'h')
     self.extra_data  = io.fread(self.fid, 1, 'h')
     self.buffersize = io.fread(self.fid, 1, 'h')
     self.os_format   = io.fread(self.fid, 1, 'h')
     self.max_ftime   = io.fread(self.fid, 1, 'l')
     self.dtime_base  = io.fread(self.fid, 1, 'd')
     if self.system_id < 6: self.dtime_base = 1e-6
     self.time_date = {
                     'Detail' : io.fread(self.fid, 6, 'B'),
                     'Year' :   io.fread(self.fid, 1, 'h')}
     if self.system_id < 6:
         self.time_date['Detail'] = zeros(6)
         self.time_date['Year'] = 0
     pad = self.fid.read(52)
     self.file_comment = {}
     pointer = self.fid.tell()
     for i in range(1, 6):
         bytes = io.fread(self.fid, 1, 'B')
         self.file_comment[i] = self.fid.read(bytes)
         pointer = pointer + 80
         self.fid.seek(pointer)
Пример #9
0
    def __init__(self, fhead, channel):
        from scipy import io
        self.chan = channel
        # Offset due to file header and preceding channel headers:
        base = 512 + (140*(channel-1))
        fhead.fid.seek(base)
        self.del_size       = io.fread(fhead.fid, 1, 'h')
        self.next_del_block = io.fread(fhead.fid, 1, 'l')
        self.firstblock     = io.fread(fhead.fid, 1, 'l')
        self.lastblock      = io.fread(fhead.fid, 1, 'l')
        self.blocks         = io.fread(fhead.fid, 1, 'h')
        self.n_extra        = io.fread(fhead.fid, 1, 'h')
        self.pre_trig       = io.fread(fhead.fid, 1, 'h')
        self.free0          = io.fread(fhead.fid, 1, 'h')
        self.py_sz          = io.fread(fhead.fid, 1, 'h')
        self.max_data       = io.fread(fhead.fid, 1, 'h')
        bytes               = io.fread(fhead.fid, 1, 'B')
        pointer             = fhead.fid.tell()
        self.comment        = fhead.fid.read(bytes)
        fhead.fid.seek(pointer+71)
        self.max_chan_time  = io.fread(fhead.fid, 1, 'l')
        self.l_chan_dvd     = io.fread(fhead.fid, 1, 'l')
        self.phy_chan       = io.fread(fhead.fid, 1, 'h')
        bytes               = io.fread(fhead.fid, 1, 'B')
        pointer             = fhead.fid.tell()
        self.title          = fhead.fid.read(bytes)
        fhead.fid.seek(pointer+9)
        self.ideal_rate     = io.fread(fhead.fid, 1, 'f')
        self.kind           = io.fread(fhead.fid, 1, 'B')
        pad                 = io.fread(fhead.fid, 1, 'b')

        if self.kind in [1, 6]:
            self.scale    = io.fread(fhead.fid, 1, 'f')
            self.offset   = io.fread(fhead.fid, 1, 'f')
            bytes         = io.fread(fhead.fid, 1, 'B')
            pointer       = fhead.fid.tell()
            self.units    = fhead.fid.read(bytes).strip()
            fhead.fid.seek(pointer+5)
            if fhead.system_id < 6: self.divide = io.fread(fhead.fid, 1, 'l')
            else: self.interleave = io.fread(fhead.fid, 1, 'l')
        elif self.kind in [7, 9]:
            self.min       = io.fread(fhead.fid, 1, 'f')
            self.max       = io.fread(fhead.fid, 1, 'f')
            bytes          = io.fread(fhead.fid, 1, 'B')
            pointer        = fhead.fid.tell()
            self.units     = fhead.fid.read(bytes).strip()
            fhead.fid.seek(pointer+5)
            if fhead.system_id < 6: self.divide = io.fread(fhead.fid, 1, 'l')
            else: self.interleave = io.fread(fhead.fid, 1, 'l')
        elif self.kind in [4]:
            self.init_low   = io.fread(fhead.fid, 1, 'B')
            self.next_low   = io.fread(fhead.fid, 1, 'B')
Пример #10
0
    def __init__(self, fhead, channel):
        from scipy import io
        self.chan = channel
        # Offset due to file header and preceding channel headers:
        base = 512 + (140 * (channel - 1))
        fhead.fid.seek(base)
        self.del_size = io.fread(fhead.fid, 1, 'h')
        self.next_del_block = io.fread(fhead.fid, 1, 'l')
        self.firstblock = io.fread(fhead.fid, 1, 'l')
        self.lastblock = io.fread(fhead.fid, 1, 'l')
        self.blocks = io.fread(fhead.fid, 1, 'h')
        self.n_extra = io.fread(fhead.fid, 1, 'h')
        self.pre_trig = io.fread(fhead.fid, 1, 'h')
        self.free0 = io.fread(fhead.fid, 1, 'h')
        self.py_sz = io.fread(fhead.fid, 1, 'h')
        self.max_data = io.fread(fhead.fid, 1, 'h')
        bytes = io.fread(fhead.fid, 1, 'B')
        pointer = fhead.fid.tell()
        self.comment = fhead.fid.read(bytes)
        fhead.fid.seek(pointer + 71)
        self.max_chan_time = io.fread(fhead.fid, 1, 'l')
        self.l_chan_dvd = io.fread(fhead.fid, 1, 'l')
        self.phy_chan = io.fread(fhead.fid, 1, 'h')
        bytes = io.fread(fhead.fid, 1, 'B')
        pointer = fhead.fid.tell()
        self.title = fhead.fid.read(bytes)
        fhead.fid.seek(pointer + 9)
        self.ideal_rate = io.fread(fhead.fid, 1, 'f')
        self.kind = io.fread(fhead.fid, 1, 'B')
        pad = io.fread(fhead.fid, 1, 'b')

        if self.kind in [1, 6]:
            self.scale = io.fread(fhead.fid, 1, 'f')
            self.offset = io.fread(fhead.fid, 1, 'f')
            bytes = io.fread(fhead.fid, 1, 'B')
            pointer = fhead.fid.tell()
            self.units = fhead.fid.read(bytes).strip()
            fhead.fid.seek(pointer + 5)
            if fhead.system_id < 6: self.divide = io.fread(fhead.fid, 1, 'l')
            else: self.interleave = io.fread(fhead.fid, 1, 'l')
        elif self.kind in [7, 9]:
            self.min = io.fread(fhead.fid, 1, 'f')
            self.max = io.fread(fhead.fid, 1, 'f')
            bytes = io.fread(fhead.fid, 1, 'B')
            pointer = fhead.fid.tell()
            self.units = fhead.fid.read(bytes).strip()
            fhead.fid.seek(pointer + 5)
            if fhead.system_id < 6: self.divide = io.fread(fhead.fid, 1, 'l')
            else: self.interleave = io.fread(fhead.fid, 1, 'l')
        elif self.kind in [4]:
            self.init_low = io.fread(fhead.fid, 1, 'B')
            self.next_low = io.fread(fhead.fid, 1, 'B')
Пример #11
0
    def __init__(self, filename):
        from scipy import io, zeros

        self.name = filename
        self.fid = open(filename, "rb")
        self.fid.seek(0)
        self.systemID = io.fread(self.fid, 1, "h")
        self.copyright = self.fid.read(10)
        self.creator = self.fid.read(8)
        self.usPerTime = io.fread(self.fid, 1, "h")
        self.timePerADC = io.fread(self.fid, 1, "h")
        self.filestate = io.fread(self.fid, 1, "h")
        self.firstdata = io.fread(self.fid, 1, "l")
        self.channels = io.fread(self.fid, 1, "h")
        self.chansize = io.fread(self.fid, 1, "h")
        self.extraData = io.fread(self.fid, 1, "h")
        self.buffersize = io.fread(self.fid, 1, "h")
        self.osFormat = io.fread(self.fid, 1, "h")
        self.maxFTime = io.fread(self.fid, 1, "l")
        self.dTimeBase = io.fread(self.fid, 1, "d")
        if self.systemID < 6:
            self.dTimeBase = 1e-6
        self.timeDate = {"Detail": io.fread(self.fid, 6, "B"), "Year": io.fread(self.fid, 1, "h")}
        if self.systemID < 6:
            self.timeDate["Detail"] = zeros(6)
            self.timeDate["Year"] = 0
        pad = self.fid.read(52)
        self.fileComment = {}
        pointer = self.fid.tell()
        for i in range(1, 6):
            bytes = io.fread(self.fid, 1, "B")
            self.fileComment[i] = self.fid.read(bytes)
            pointer = pointer + 80
            self.fid.seek(pointer)
Пример #12
0
    def __init__(self, fhead, channel):
        from scipy import io

        self.chan = channel
        # Offset due to file header and preceding channel headers:
        base = 512 + (140 * (channel - 1))
        fhead.fid.seek(base)
        self.delSize = io.fread(fhead.fid, 1, "h")
        self.nextDelBlock = io.fread(fhead.fid, 1, "l")
        self.firstblock = io.fread(fhead.fid, 1, "l")
        self.lastblock = io.fread(fhead.fid, 1, "l")
        self.blocks = io.fread(fhead.fid, 1, "h")
        self.nExtra = io.fread(fhead.fid, 1, "h")
        self.preTrig = io.fread(fhead.fid, 1, "h")
        self.free0 = io.fread(fhead.fid, 1, "h")
        self.phySz = io.fread(fhead.fid, 1, "h")
        self.maxData = io.fread(fhead.fid, 1, "h")
        bytes = io.fread(fhead.fid, 1, "B")
        pointer = fhead.fid.tell()
        self.comment = fhead.fid.read(bytes)
        fhead.fid.seek(pointer + 71)
        self.maxChanTime = io.fread(fhead.fid, 1, "l")
        self.lChanDvd = io.fread(fhead.fid, 1, "l")
        self.phyChan = io.fread(fhead.fid, 1, "h")
        bytes = io.fread(fhead.fid, 1, "B")
        pointer = fhead.fid.tell()
        self.title = fhead.fid.read(bytes)
        fhead.fid.seek(pointer + 9)
        self.idealRate = io.fread(fhead.fid, 1, "f")
        self.kind = io.fread(fhead.fid, 1, "B")
        pad = io.fread(fhead.fid, 1, "b")

        if self.kind in [1, 6]:
            self.scale = io.fread(fhead.fid, 1, "f")
            self.offset = io.fread(fhead.fid, 1, "f")
            bytes = io.fread(fhead.fid, 1, "B")
            pointer = fhead.fid.tell()
            self.units = fhead.fid.read(bytes)
            fhead.fid.seek(pointer + 5)
            if fhead.systemID < 6:
                self.divide = io.fread(fhead.fid, 1, "l")
            else:
                self.interleave = io.fread(fhead.fid, 1, "l")
        elif self.kind in [7, 9]:
            self.min = io.fread(fhead.fid, 1, "f")
            self.max = io.fread(fhead.fid, 1, "f")
            bytes = io.fread(fhead.fid, 1, "B")
            pointer = fhead.fid.tell()
            self.units = fhead.fid.read(bytes)
            fhead.fid.seek(pointer + 5)
            if fhead.systemID < 6:
                self.divide = io.fread(fhead.fid, 1, "l")
            else:
                self.interleave = io.fread(fhead.fid, 1, "l")
        elif self.kind in [4]:
            self.initLow = io.fread(fhead.fid, 1, "B")
            self.nextLow = io.fread(fhead.fid, 1, "B")
        try:
            self.units = self.units.strip()
        except AttributeError:
            pass
            # setst the dt, to be used in NeuroTools
        interval = self.lChanDvd
        if interval == 0:
            interval = 1.0
        # in milliseconds
        # have to multiply by 2, I dont know why, I have to check that
        self.dt = interval * fhead.usPerTime * fhead.dTimeBase * 1e3 * 2
Пример #13
0
 def __init__(self, filename):
     from scipy import io, zeros
     self.name = filename
     self.fid = open(filename, 'rb')
     self.fid.seek(0)
     self.systemID = io.fread(self.fid, 1, 'h')
     self.copyright = self.fid.read(10)
     self.creator = self.fid.read(8)
     self.usPerTime = io.fread(self.fid, 1, 'h')
     self.timePerADC = io.fread(self.fid, 1, 'h')
     self.filestate = io.fread(self.fid, 1, 'h')
     self.firstdata = io.fread(self.fid, 1, 'l')
     self.channels = io.fread(self.fid, 1, 'h')
     self.chansize = io.fread(self.fid, 1, 'h')
     self.extraData = io.fread(self.fid, 1, 'h')
     self.buffersize = io.fread(self.fid, 1, 'h')
     self.osFormat = io.fread(self.fid, 1, 'h')
     self.maxFTime = io.fread(self.fid, 1, 'l')
     self.dTimeBase = io.fread(self.fid, 1, 'd')
     if self.systemID < 6: self.dTimeBase = 1e-6
     self.timeDate = {
         'Detail': io.fread(self.fid, 6, 'B'),
         'Year': io.fread(self.fid, 1, 'h')
     }
     if self.systemID < 6:
         self.timeDate['Detail'] = zeros(6)
         self.timeDate['Year'] = 0
     pad = self.fid.read(52)
     self.fileComment = {}
     pointer = self.fid.tell()
     for i in range(1, 6):
         bytes = io.fread(self.fid, 1, 'B')
         self.fileComment[i] = self.fid.read(bytes)
         pointer = pointer + 80
         self.fid.seek(pointer)
Пример #14
0
    def __init__(self, fhead, channel):
        from scipy import io
        self.chan = channel
        # Offset due to file header and preceding channel headers:
        base = 512 + (140 * (channel - 1))
        fhead.fid.seek(base)
        self.delSize = io.fread(fhead.fid, 1, 'h')
        self.nextDelBlock = io.fread(fhead.fid, 1, 'l')
        self.firstblock = io.fread(fhead.fid, 1, 'l')
        self.lastblock = io.fread(fhead.fid, 1, 'l')
        self.blocks = io.fread(fhead.fid, 1, 'h')
        self.nExtra = io.fread(fhead.fid, 1, 'h')
        self.preTrig = io.fread(fhead.fid, 1, 'h')
        self.free0 = io.fread(fhead.fid, 1, 'h')
        self.phySz = io.fread(fhead.fid, 1, 'h')
        self.maxData = io.fread(fhead.fid, 1, 'h')
        bytes = io.fread(fhead.fid, 1, 'B')
        pointer = fhead.fid.tell()
        self.comment = fhead.fid.read(bytes)
        fhead.fid.seek(pointer + 71)
        self.maxChanTime = io.fread(fhead.fid, 1, 'l')
        self.lChanDvd = io.fread(fhead.fid, 1, 'l')
        self.phyChan = io.fread(fhead.fid, 1, 'h')
        bytes = io.fread(fhead.fid, 1, 'B')
        pointer = fhead.fid.tell()
        self.title = fhead.fid.read(bytes)
        fhead.fid.seek(pointer + 9)
        self.idealRate = io.fread(fhead.fid, 1, 'f')
        self.kind = io.fread(fhead.fid, 1, 'B')
        pad = io.fread(fhead.fid, 1, 'b')

        if self.kind in [1, 6]:
            self.scale = io.fread(fhead.fid, 1, 'f')
            self.offset = io.fread(fhead.fid, 1, 'f')
            bytes = io.fread(fhead.fid, 1, 'B')
            pointer = fhead.fid.tell()
            self.units = fhead.fid.read(bytes)
            fhead.fid.seek(pointer + 5)
            if fhead.systemID < 6: self.divide = io.fread(fhead.fid, 1, 'l')
            else: self.interleave = io.fread(fhead.fid, 1, 'l')
        elif self.kind in [7, 9]:
            self.min = io.fread(fhead.fid, 1, 'f')
            self.max = io.fread(fhead.fid, 1, 'f')
            bytes = io.fread(fhead.fid, 1, 'B')
            pointer = fhead.fid.tell()
            self.units = fhead.fid.read(bytes)
            fhead.fid.seek(pointer + 5)
            if fhead.systemID < 6: self.divide = io.fread(fhead.fid, 1, 'l')
            else: self.interleave = io.fread(fhead.fid, 1, 'l')
        elif self.kind in [4]:
            self.initLow = io.fread(fhead.fid, 1, 'B')
            self.nextLow = io.fread(fhead.fid, 1, 'B')
        try:
            self.units = self.units.strip()
        except AttributeError:
            pass
        # setst the dt, to be used in NeuroTools
        interval = self.lChanDvd
        if interval == 0: interval = 1.
        # in milliseconds
        # have to multiply by 2, I dont know why, I have to check that
        self.dt = interval * fhead.usPerTime * fhead.dTimeBase * 1e3 * 2
Пример #15
0
 def __init__(self, filename):
     from scipy import io, zeros
     self.name = filename
     self.fid = open(filename, 'rb')
     self.fid.seek(0)
     self.system_id = io.fread(self.fid, 1, 'h')
     self.copyright = self.fid.read(10)
     self.creator = self.fid.read(8)
     self.us_per_time = io.fread(self.fid, 1, 'h')
     self.time_per_adc = io.fread(self.fid, 1, 'h')
     self.filestate = io.fread(self.fid, 1, 'h')
     self.first_data = io.fread(self.fid, 1, 'l')
     self.channels = io.fread(self.fid, 1, 'h')
     self.chan_size = io.fread(self.fid, 1, 'h')
     self.extra_data = io.fread(self.fid, 1, 'h')
     self.buffersize = io.fread(self.fid, 1, 'h')
     self.os_format = io.fread(self.fid, 1, 'h')
     self.max_ftime = io.fread(self.fid, 1, 'l')
     self.dtime_base = io.fread(self.fid, 1, 'd')
     if self.system_id < 6: self.dtime_base = 1e-6
     self.time_date = {
         'Detail': io.fread(self.fid, 6, 'B'),
         'Year': io.fread(self.fid, 1, 'h')
     }
     if self.system_id < 6:
         self.time_date['Detail'] = zeros(6)
         self.time_date['Year'] = 0
     pad = self.fid.read(52)
     self.file_comment = {}
     pointer = self.fid.tell()
     for i in range(1, 6):
         bytes = io.fread(self.fid, 1, 'B')
         self.file_comment[i] = self.fid.read(bytes)
         pointer = pointer + 80
         self.fid.seek(pointer)
Пример #16
0
def data(chan, start=None, stop=None, timeunits='seconds', as_float=True):
    '''
    Reads data from a RealWave or Adc channel from a SON file.

    'chan' is a Channel intance.

    'start', 'stop' set the data limits to be returned, in blocks for
    continuous data or in epochs for triggered data. If only start
    is set, data from only the block/epoch selected will be returned.

    'timeunits' scales time to appropriate unit. Valid options are 'ticks',
    'microseconds', 'milliseconds' or 'seconds'.

    'as_float=True' returns data as floating point values (scaling and
    applying offset for Adc channel data). Else, data will be of type int16.

    RETURNS data, which can be a simple vector (for continuously sampled
    data) or a two-dimensional matrix with each epoch (frame) of data
    in a separate row (if sampling was triggered).
    '''
    from scipy import array, io, histogram, zeros
    fid = chan.fhead.fid
    blockheader = chan.blockheader
    size_of_header = 20 # block header is 20 bytes long
    # sample interval in clock ticks:
    sample_interval = ((blockheader[2,0]-blockheader[1,0])/
                       (blockheader[4,0]-1))

    # =======================================================
    # = Set data types according to channel type to be read =
    # =======================================================
    if chan.info.kind == 1:   datatype = 'h' # Adc channel, 'int16'
    elif chan.info.kind == 9: datatype = 'f' # RealWave channel, 'single'

    # ============================================
    # = Check for discontinuities in data record =
    # ============================================
    num_frames = 1 # number of frames. Initialize to one
    frame = [1]
    for i in range(chan.info.blocks-1): 
        interval_between_blocks = blockheader[1, i+1] - blockheader[2, i]
        if interval_between_blocks > sample_interval:
            # if true, data is discontinuous
            num_frames += 1 # count discontinuities (num_frames)
            #record the frame number that each block belongs to:
            frame.append(num_frames)
        else:
            frame.append(frame[i]) # pad between discontinuities
    frame = array(frame)

    # =================================
    # = Set start and stop boundaries =
    # =================================
    if not start and not stop:
        frames_to_return = num_frames
        chan.info.npoints = zeros(frames_to_return)
        start_epoch = 0 # read all data
        end_epoch = chan.info.blocks
    elif start and not stop:
        if num_frames == 1: # read one epoch
            start_epoch = start-1
            end_epoch = start
        else:
            frames_to_return = 1
            chan.info.npoints = 0
            indx = arange(frame.size)
            start_epoch = indx[frame == start][0]
            end_epoch = indx[frame == start][-1] + 1
    elif start and stop:
        if num_frames == 1: # read a range of epochs
            start_epoch = start-1
            end_epoch = stop
        else:
            frames_to_return = stop-start + 1
            chan.info.npoints = zeros(frames_to_return)
            indx = arange(frame.size)
            start_epoch = indx[frame == start][0]
            end_epoch = indx[frame == stop][-1] + 1

    # Make sure we are in range if using 'start' and 'stop'
    if (start_epoch > chan.info.blocks) | (start_epoch > end_epoch):
        raise ValueError('Invalid start and/or stop')
    if end_epoch > chan.info.blocks: end_epoch = chan.info.blocks

    # =============
    # = Read data =
    # =============
    if num_frames == 1:
        # ++ Continuous sampling - one frame only. Epochs correspond to
        # blocks in the SON file.
        # sum of samples in all blocks:
        number_of_samples = sum(blockheader[4, start_epoch:end_epoch])
        # pre-allocate memory for data:
        data = zeros(number_of_samples, datatype)
        # read data:
        pointer = 0
        for i in range(start_epoch, end_epoch):
            fid.seek(blockheader[0, i] + size_of_header)
            data[pointer : pointer+blockheader[4, i]] =\
                         io.fread(fid, blockheader[4, i], datatype)
            pointer += blockheader[4, i]
        # set extra channel information:
        chan.info.mode       = 'continuous'
        chan.info.epochs     = [start_epoch+1, end_epoch]
        chan.info.npoints    = number_of_samples
        # first data point (clock ticks):
        chan.info.start      = blockheader[1, start_epoch]
        # end of data (clock ticks):
        chan.info.stop       = blockheader[2, end_epoch-1]
        chan.info.epochs_str = '%i--%i of %i blocks' % (start_epoch+1,
                                                        end_epoch,
                                                        chan.info.blocks)

    else:
        # ++ Frame-based data -  multiple frames. Epochs correspond to
        # frames of data.
        # sum of samples in required epochs:
        number_of_samples = sum(blockheader[4, start_epoch:end_epoch])
        # maximum data points to a frame:
        frame_length = (
                histogram(frame, range(start_epoch,end_epoch))[0].max()*
                blockheader[4, start_epoch:end_epoch].max())
        # pre-allocate memory:
        data = zeros([frames_to_return, frame_length], datatype)
        chan.info.start = zeros(frames_to_return)
        chan.info.stop = zeros(frames_to_return)
        # read data:
        pointer = 0 # pointer into data array for each disk data block
        index = 0   # epoch counter
        for i in range(start_epoch, end_epoch):
            fid.seek(blockheader[0, i] + size_of_header)
            data[index, pointer : pointer+blockheader[4, i]] =\
                            io.fread(
                    fid, blockheader[4, i], datatype)
            chan.info.npoints[index] = (chan.info.npoints[index]+
                                        blockheader[4,i])
            try: frame[i+1]
            except IndexError:
                chan.info.stop[index] = blockheader[2, i]
                # time at eof
            else:
                if frame[i+1] == frame[i]:
                    pointer += blockheader[4, i]
                    # increment pointer or...
                else:
                    chan.info.stop[index] = blockheader[2, i]
                    # end time for this frame
                    if i < end_epoch-1:
                        pointer = 0 # begin new frame
                        index += 1
                        # time of first data
                        # point in next frame
                        # (clock ticks):
                        chan.info.start[index] = \
                                blockheader[1, i+1]
        # set extra channel information:
        chan.info.mode = 'triggered'
        chan.info.start[0] = blockheader[1, start_epoch] 
        chan.info.epochs_str = '%i--%i of %i epochs' % (
                start_epoch+1, end_epoch,num_frames)

    # ================
    # = Convert time =
    # ================
    chan.info.start = chan.fhead._ticks_to_seconds(
            chan.info.start, timeunits)
    chan.info.stop =  chan.fhead._ticks_to_seconds(
            chan.info.stop, timeunits)
    chan.info.timeunits = timeunits

    # =========================
    # = Scale and return data =
    # =========================
    if as_float and chan.info.kind == 1:     # Adc
        data = _adc_to_double(chan, data)
    if not as_float and chan.info.kind == 9: # RealWave
        data = _real_to_adc(data)
    return data
Пример #17
0
def data(Chan, start=None, stop=None, timeunits='seconds', as_float=True):
	'''
	Reads data from an event/marker channel (ie, Event, Marker, AdcMark,
	RealMark, or TextMark channel) from a Son file.

	'start', 'stop' set the data limits to be returned, in blocks. If
	only start is set, data from only that block will be returned.

	'timeunits' scales time to appropriate unit. Valid options are 'ticks',
	'microseconds', 'milliseconds' or 'seconds'.

	'as_float' only makes sense for AdcMark or RealMark channels. If
	True, returns data as floating point values (scaling and applying
	offset for Adc data). Else, data will be of type int16.
	'''
	from scipy import io, zeros
	fid = Chan.fhead.fid
	blockheader = Chan.blockheader
	SizeOfHeader = 20 # Block header is 20 bytes long
	
	# ====================================
	# = Set start and end blocks to read =
	# ====================================
	if not start and not stop:
		startBlock, endBlock = 0, Chan.info.blocks
	elif start and not stop:
		startBlock, endBlock = start-1, start
	elif start and stop:
		startBlock, endBlock = start-1, min([stop, Chan.info.blocks])

	# == Sum of samples in required blocks ==
	nItems = sum(blockheader[4, startBlock:endBlock])
	
	# =============
	# = Read data =
	# =============
	#	+ Event data +
	if Chan.info.kind in [2, 3, 4]:
		# pre-allocate memory:
		timings = zeros(nItems, 'int32')
		# read data:
		pointer = 0
		for block in range(startBlock, endBlock):
			fid.seek(blockheader[0, block] + SizeOfHeader)
			timings[pointer : pointer+blockheader[4, block]] =\
					io.fread(fid, blockheader[4, block], 'l')
			pointer += blockheader[4, block]

	#	+ Marker data +
	elif Chan.info.kind == 5:
		# pre-allocate memory:
		timings = zeros(nItems, 'int32')
		markers = zeros([nItems, 4], 'uint8')
		# read data:
		count = 0
		for block in range(startBlock, endBlock):
			fid.seek(blockheader[0, block] + SizeOfHeader) # start of block
			for i in range(blockheader[4, block]):         # loop for each marker
				timings[count] = io.fread(fid, 1, 'l')     # time
				markers[count] = io.fread(fid, 4, 'B')     # 4x marker bytes
				count += 1
		markers = [chr(x) for x in markers[:,0]]

	#	+ AdcMark data +
	elif Chan.info.kind == 6:
		nValues = Chan.info.nExtra/2 # 2 because 2 bytes per int16 value
		# pre-allocate memory:
		timings = zeros(nItems, 'int32')
		markers = zeros([nItems, 4], 'uint8')
		adc     = zeros([nItems, nValues], 'int16')
		# read data:
		count = 0
		for block in range(startBlock, endBlock):
			fid.seek(blockheader[0, block] + SizeOfHeader) # start of block
			for i in range(blockheader[4, block]):         # loop for each marker
				timings[count] = io.fread(fid, 1, 'l')     # time
				markers[count] = io.fread(fid, 4, 'B')     # 4x marker bytes
				adc[count]     = io.fread(fid, nValues, 'h')
				count += 1
		if as_double:
			from _waveform import _adc_to_double
			adc = _adc_to_double(Chan, adc)

	#	+ RealMark data +
	elif Chan.info.kind == 7:
		nValues = Chan.info.nExtra/4 # each value has 4 bytes (single precision)
		# pre-allocate:
		timings = zeros(nItems, 'int32')
		markers = zeros([nItems, 4], 'uint8')
		real =    zeros([nItems, nValues], 'single')
		# read data:
		count = 0
		for block in range(startBlock, endBlock):
			fid.seek(blockheader[0, block] + SizeOfHeader) # start of block
			for i in range(blockheader[4, block]):         # loop for each marker
				timings[count] = io.fread(fid, 1, 'l')     # time
				markers[count] = io.fread(fid, 4, 'B')     # 4x marker bytes
				real[count]    = io.fread(fid, nValues, 'f')
				count += 1
		if not as_double:
			from _waveform import _real_to_adc
			real = _real_to_adc(real)

	#	+ TextMark data +
	elif Chan.info.kind == 8:
		# pre-allocate memory:
		timings = zeros(nItems, 'int32')
		markers = zeros([nItems, 4], 'uint8')
		text = zeros([nItems, Chan.info.nExtra], 'S1')
		# read data:
		count = 0
		for block in range(startBlock, endBlock):
			fid.seek(blockheader[0, block] + SizeOfHeader) # start of block
			for i in range(blockheader[4, block]):         # loop for each marker
				timings[count] = io.fread(fid, 1, 'l')     # time
				markers[count] = io.fread(fid, 4, 'B')     # 4x marker bytes
				text[count]    = io.fread(fid, Chan.info.nExtra, 'c')
				count += 1

	# ================
	# = Convert time =
	# ================
	timings = Chan.fhead._ticks_to_seconds(timings, timeunits)
	Chan.info.timeunits = timeunits
	Chan.info.Epochs = '%i--%i of %i block(s)'\
			%(startBlock+1, endBlock, Chan.info.blocks)

	# ===============
	# = Return data =
	# ===============
	if Chan.info.kind in [2, 3, 4]:
		data = timings
	elif Chan.info.kind == 5:
		data = zip(timings, markers)
	elif Chan.info.kind == 6:
		data = zip(timings, markers, adc)
	elif Chan.info.kind == 7:
		data = zip(timings, markers, real)
	elif Chan.info.kind == 8:
		data = zip(timings, markers, text)
	return data
Пример #18
0
def data(chan, start=None, stop=None, timeunits='seconds', as_float=True):
    '''
    Reads data from a RealWave or Adc channel from a SON file.

    'chan' is a Channel intance.

    'start', 'stop' set the data limits to be returned, in blocks for
    continuous data or in epochs for triggered data. If only start
    is set, data from only the block/epoch selected will be returned.

    'timeunits' scales time to appropriate unit. Valid options are 'ticks',
    'microseconds', 'milliseconds' or 'seconds'.

    'as_float=True' returns data as floating point values (scaling and
    applying offset for Adc channel data). Else, data will be of type int16.

    RETURNS data, which can be a simple vector (for continuously sampled
    data) or a two-dimensional matrix with each epoch (frame) of data
    in a separate row (if sampling was triggered).
    '''
    from scipy import array, io, histogram, zeros
    fid = chan.fhead.fid
    blockheader = chan.blockheader
    size_of_header = 20 # block header is 20 bytes long
    # sample interval in clock ticks:
    sample_interval = ((blockheader[2,0]-blockheader[1,0])/
                       (blockheader[4,0]-1))

    # =======================================================
    # = Set data types according to channel type to be read =
    # =======================================================
    if chan.info.kind == 1:   datatype = 'h' # Adc channel, 'int16'
    elif chan.info.kind == 9: datatype = 'f' # RealWave channel, 'single'

    # ============================================
    # = Check for discontinuities in data record =
    # ============================================
    num_frames = 1 # number of frames. Initialize to one
    frame = [1]
    for i in range(chan.info.blocks-1): 
        interval_between_blocks = blockheader[1, i+1] - blockheader[2, i]
        if interval_between_blocks > sample_interval:
            # if true, data is discontinuous
            num_frames += 1 # count discontinuities (num_frames)
            #record the frame number that each block belongs to:
            frame.append(num_frames)
        else:
            frame.append(frame[i]) # pad between discontinuities
    frame = array(frame)

    # =================================
    # = Set start and stop boundaries =
    # =================================
    if not start and not stop:
        frames_to_return = num_frames
        chan.info.npoints = zeros(frames_to_return)
        start_epoch = 0 # read all data
        end_epoch = chan.info.blocks
    elif start and not stop:
        if num_frames == 1: # read one epoch
            start_epoch = start-1
            end_epoch = start
        else:
            frames_to_return = 1
            chan.info.npoints = 0
            indx = arange(frame.size)
            start_epoch = indx[frame == start][0]
            end_epoch = indx[frame == start][-1] + 1
    elif start and stop:
        if num_frames == 1: # read a range of epochs
            start_epoch = start-1
            end_epoch = stop
        else:
            frames_to_return = stop-start + 1
            chan.info.npoints = zeros(frames_to_return)
            indx = arange(frame.size)
            start_epoch = indx[frame == start][0]
            end_epoch = indx[frame == stop][-1] + 1

    # Make sure we are in range if using 'start' and 'stop'
    if (start_epoch > chan.info.blocks) | (start_epoch > end_epoch):
        raise ValueError('Invalid start and/or stop')
    if end_epoch > chan.info.blocks: end_epoch = chan.info.blocks

    # =============
    # = Read data =
    # =============
    if num_frames == 1:
        # ++ Continuous sampling - one frame only. Epochs correspond to
        # blocks in the SON file.
        # sum of samples in all blocks:
        number_of_samples = sum(blockheader[4, start_epoch:end_epoch])
        # pre-allocate memory for data:
        data = zeros(number_of_samples, datatype)
        # read data:
        pointer = 0
        for i in range(start_epoch, end_epoch):
            fid.seek(blockheader[0, i] + size_of_header)
            data[pointer : pointer+blockheader[4, i]] =\
                         io.fread(fid, blockheader[4, i], datatype)
            pointer += blockheader[4, i]
        # set extra channel information:
        chan.info.mode       = 'continuous'
        chan.info.epochs     = [start_epoch+1, end_epoch]
        chan.info.npoints    = number_of_samples
        # first data point (clock ticks):
        chan.info.start      = blockheader[1, start_epoch]
        # end of data (clock ticks):
        chan.info.stop       = blockheader[2, end_epoch-1]
        chan.info.epochs_str = '%i--%i of %i blocks' % (start_epoch+1,
                                                        end_epoch,
                                                        chan.info.blocks)

    else:
        # ++ Frame-based data -  multiple frames. Epochs correspond to
        # frames of data.
        # sum of samples in required epochs:
        number_of_samples = sum(blockheader[4, start_epoch:end_epoch])
        # maximum data points to a frame:
        frame_length = (
                histogram(frame, range(start_epoch,end_epoch))[0].max()*
                blockheader[4, start_epoch:end_epoch].max())
        # pre-allocate memory:
        data = zeros([frames_to_return, frame_length], datatype)
        chan.info.start = zeros(frames_to_return)
        chan.info.stop = zeros(frames_to_return)
        # read data:
        pointer = 0 # pointer into data array for each disk data block
        index = 0   # epoch counter
        for i in range(start_epoch, end_epoch):
            fid.seek(blockheader[0, i] + size_of_header)
            data[index, pointer : pointer+blockheader[4, i]] =\
                            io.fread(
                    fid, blockheader[4, i], datatype)
            chan.info.npoints[index] = (chan.info.npoints[index]+
                                        blockheader[4,i])
            try: frame[i+1]
            except IndexError:
                chan.info.stop[index] = blockheader[2, i]
                # time at eof
            else:
                if frame[i+1] == frame[i]:
                    pointer += blockheader[4, i]
                    # increment pointer or...
                else:
                    chan.info.stop[index] = blockheader[2, i]
                    # end time for this frame
                    if i < end_epoch-1:
                        pointer = 0 # begin new frame
                        index += 1
                        # time of first data
                        # point in next frame
                        # (clock ticks):
                        chan.info.start[index] = \
                                blockheader[1, i+1]
        # set extra channel information:
        chan.info.mode = 'triggered'
        chan.info.start[0] = blockheader[1, start_epoch] 
        chan.info.epochs_str = '%i--%i of %i epochs' % (
                start_epoch+1, end_epoch,num_frames)

    # ================
    # = Convert time =
    # ================
    chan.info.start = chan.fhead._ticks_to_seconds(
            chan.info.start, timeunits)
    chan.info.stop =  chan.fhead._ticks_to_seconds(
            chan.info.stop, timeunits)
    chan.info.timeunits = timeunits

    # =========================
    # = Scale and return data =
    # =========================
    if as_float and chan.info.kind == 1:     # Adc
        data = _adc_to_double(chan, data)
    if not as_float and chan.info.kind == 9: # RealWave
        data = _real_to_adc(data)
    return data