Ejemplo n.º 1
0
def test_hdf5():
    """Test HDF5 IO
    """
    test_file = op.join(tempdir, 'test.hdf5')
    x = dict(a=dict(b=np.zeros(3)), c=np.zeros(2, np.complex128),
             d=[dict(e=(1, -2., 'hello'))])
    write_hdf5(test_file, 1)
    assert_equal(read_hdf5(test_file), 1)
    assert_raises(IOError, write_hdf5, test_file, x)  # file exists
    write_hdf5(test_file, x, overwrite=True)
    assert_raises(IOError, read_hdf5, test_file + 'FOO')  # not found
    xx = read_hdf5(test_file)
    print(object_diff(x, xx))
    assert_true(object_diff(x, xx) == '')  # no assert_equal, ugly output
def generate_stimuli(num_trials=10,
                     num_freqs=4,
                     stim_dur=0.5,
                     min_freq=500.0,
                     max_freq=4000.0,
                     fs=24414.0625,
                     rms=0.01,
                     output_dir='.',
                     save_as='hdf5',
                     rand_seed=0):
    """Make some sine waves and save in various formats. Optimized for saving
    as MAT files, but can also save directly as WAV files, or can return a
    python dictionary with sinewave data as values.

    Parameters
    ----------
    num_trials : int
        Number of trials you want in your experiment. Ignored if save_as is
        not 'mat'.
    num_freqs : int
        Number of frequencies (equally-spaced on a log2-scale) at which to
        generate tones.
    stim_dur : float
        Duration of the tones in seconds.
    min_freq : float
        Frequency of the lowest tone in Hertz.
    max_freq : float
        Frequency of the highest tone in Hertz.
    fs : float | None
        Sampling frequency of resulting sinewaves.  Defaults to 24414.0625 (a
        standard rate for TDTs).
    rms : float
        RMS amplitude to which all sinwaves will be scaled.
    output_dir : str
        Directory to output the files into.
    save_as : str
        Format in which to return the sinewaves. 'dict' returns sinewave arrays
        as values in a python dictionary; 'wav' saves them as WAV files at
        sampling frequency 'fs'; 'mat' saves them as a MAT file along with
        related variables 'fs', 'freqs', 'trial_order', and 'rms'.
    rand_seed : int | None
        Seed for the random number generator.

    Returns
    -------
    wavs : dict | None
        The stimulus dictionary.
    """
    if rand_seed is None:
        rng = np.random.RandomState()
    else:
        rng = np.random.RandomState(rand_seed)

    # check input arguments
    if save_as not in ['dict', 'wav', 'hdf5']:
        raise ValueError('"save_as" must be "dict", "wav", or "hdf5"')

    fs = float(fs)
    t = np.arange(np.round(stim_dur * fs)) / fs

    # frequencies equally spaced on a log-2 scale
    freqs = min_freq * np.logspace(0,
                                   np.log2(max_freq / float(min_freq)),
                                   num_freqs,
                                   endpoint=True,
                                   base=2)

    # strings for the filenames / dictionary keys
    freq_names = [str(int(f)) for f in freqs]
    names = ['stim_%s_%s' % (n, f) for n, f in enumerate(freq_names)]

    # generate sinewaves & RMS normalize
    wavs = [np.sin(2 * np.pi * f * t) for f in freqs]
    wavs = [rms / np.sqrt(np.mean(w**2)) * w for w in wavs]

    # collect into dictionary & save
    wav_dict = {n: w for (n, w) in zip(names, wavs)}
    if save_as == 'hdf5':
        num_reps = num_trials // num_freqs + 1
        trials = np.tile(range(num_freqs), num_reps)
        trial_order = rng.permutation(trials[0:num_trials])
        wav_dict.update({
            'trial_order': trial_order,
            'freqs': freqs,
            'fs': fs,
            'rms': rms
        })
        write_hdf5(op.join(output_dir, 'equally_spaced_sinewaves.hdf5'),
                   wav_dict,
                   overwrite=True)
    elif save_as == 'wav':
        for n in names:
            write_wav(op.join(output_dir, n + '.wav'), wav_dict[n], int(fs))
    return wav_dict
Ejemplo n.º 3
0
    plt.figure()
    for p in percent_correct[i]:
        per_mean = p.mean(-1)
        plt.plot(snrs, per_mean*100)
    plt.xlabel('SNR (db)')
    plt.ylabel('Percent Correct')
    plt.title(sub)
    plt.legend(('0', '90', '180', 'Static'))

    
percent_condition_subject = percent_correct.mean(-1)
mean_across_subjects = percent_condition_subject.mean(0)
sem = percent_condition_subject.std(axis=0)/np.sqrt(len(subjects))

write_hdf5('matrix1.hdf5', dict(data=percent_condition_subject), overwrite=True)

percent_across_snrs = percent_condition_subject.mean(2)
mean_across_subjects2 = percent_across_snrs.mean(0) 
sem2 = percent_across_snrs.std(axis=0)/np.sqrt(len(subjects))
    #plt.plot(snrs, mean_sub*100, 'o')

width = 8
height = 5
fname = 'Average Percent Correct Across SNR'

plt.figure(figsize=(width, height))
plt.errorbar(x=[0, 1, 2, 3], y=mean_across_subjects2*100, yerr=sem2*100, fmt='o')
plt.xticks([0, 1, 2, 3], [0, 1, 2, 3])
plt.gca().set_xticklabels(['0', '90', '180', 'Static'])
plt.xlabel('Angle (deg)')
    for n in np.arange(10000):
        sub_ind = np.random.choice(np.arange(23), (n_sub, ))
        disagree_tvm_resamp = disagree_tvm.mean(1)[sub_ind]
        t, p_tvm = scipy.stats.ttest_1samp(disagree_tvm_resamp, 0, axis=0)
        disagree_inv_resamp = disagree_up_vs_inv[sub_ind]
        t, p_inv = scipy.stats.ttest_1samp(disagree_inv_resamp, 0, axis=0)

        pval_tvm.append(p_tvm)
        pval_inv.append(p_inv)
    percent_sig_tvm.append(100 * sum(np.array(pval_tvm) < 0.05) /
                           len(pval_tvm))
    percent_sig_inv.append(100 * sum(np.array(pval_inv) < 0.05) /
                           len(pval_inv))
from expyfun.io import write_hdf5
write_hdf5(
    'power_analysis_sim.hdf5',
    dict(percent_sig_inv=percent_sig_inv, percent_sig_tvm=percent_sig_tvm))
plt.figure()
plt.plot(np.arange(2, 1000), percent_sig_tvm)
plt.plot(np.arange(2, 1000), percent_sig_inv)
plt.plot([2, 1000], [80, 80], 'k')
plt.legend(('Target vs. Masker', 'Upright vs. Inverted'))
plt.xlabel('Number of simulated subjects')
plt.ylabel('% of 1000 observations significant')

import scipy.stats
import statsmodels.stats.power as smp
import matplotlib.pyplot as plt

power_analysis = smp.TTestIndPower()
sample_size = power_analysis.solve_power(effect_size=0.064,
Ejemplo n.º 5
0
             (ti + 1, attns[ai], spatials[si], idents[ii],
              int(1e3 * gap_durs[gi]), ''.join(t), ''.join(m)))
    write_wav(op.join(stim_dir, fname), stim, fs, verbose=False)
    print('  Writing %s (%s/%s)' % (fname, ti + 1, n_trials))
    stim_names.append(fname)

##############################################################################
# Write out result

params = dict(gap_durs=gap_durs,
              spatials=spatials,
              idents=idents,
              attns=attns,
              inter_trial_dur=inter_trial_dur,
              targ_pos=targ_pos,
              cond_mat=cond_mat,
              cond_readme=cond_readme,
              blocks=blocks,
              block_trials=block_trials,
              stim_names=stim_names,
              stim_dir=stim_dir_end,
              n_targ_let=n_targ_let,
              n_cue_let=n_cue_let,
              trial_durs=trial_durs,
              stim_times=ts,
              n_blocks=n_blocks,
              letter_mat=letter_mat,
              letters=letters,
              gap_after=gap_after)
write_hdf5(op.join(work_dir, 'params.hdf5'), params, overwrite=True)
        if w:
            print(':\'(')
    thresholds = np.array([np.power(10, m / 20) for m in [params[0][0], params[1][0]]])
    thresholds = np.array([-1. / ok[1] * np.log((ok[2] - .5) / (.75 - .5) - 1) + p[0] for p in params])
    thresholds = np.power(10, thresholds / 20)
    perform_imp = (sigmoid(20 * np.log10(thresholds[0]), lower=.5, upper=ok[2], midpt=params[1][0], slope=ok[1]) - .75) * 100

    # %% save the data
    data = dict(responses=responses[-1],
                thresholds=thresholds,
                ok = ok,
                params=params,
                percent=percent,
                perform_imp = perform_imp)

    write_hdf5((path + 'percent_' + subject), data, overwrite=True)

    # %% plot an example
    if subject=='016':
        from collections import OrderedDict
        from matplotlib.transforms import blended_transform_factory
        from matplotlib import rc
        from matplotlib import rcParams
        
        rcParams['font.sans-serif'] = "Arial"
    
        linestyles = OrderedDict(
            [('densely dotted',      (0, (1, 1))),
             ('densely dashed',      (0, (5, 1))),
        
             ('loosely dashdotted',  (0, (3, 10, 1, 10))),
Ejemplo n.º 7
0
def generate_stimuli(num_trials=10, num_freqs=4, stim_dur=0.5, min_freq=500.0,
                     max_freq=4000.0, fs=24414.0625, rms=0.01, output_dir='.',
                     save_as='hdf5', rand_seed=0):
    """Make some sine waves and save in various formats. Optimized for saving
    as MAT files, but can also save directly as WAV files, or can return a
    python dictionary with sinewave data as values.

    Parameters
    ----------
    num_trials : int
        Number of trials you want in your experiment. Ignored if save_as is
        not 'mat'.
    num_freqs : int
        Number of frequencies (equally-spaced on a log2-scale) at which to
        generate tones.
    stim_dur : float
        Duration of the tones in seconds.
    min_freq : float
        Frequency of the lowest tone in Hertz.
    max_freq : float
        Frequency of the highest tone in Hertz.
    fs : float | None
        Sampling frequency of resulting sinewaves.  Defaults to 24414.0625 (a
        standard rate for TDTs).
    rms : float
        RMS amplitude to which all sinwaves will be scaled.
    output_dir : str
        Directory to output the files into.
    save_as : str | None
        Format in which to return the sinewaves. 'dict' returns sinewave arrays
        as values in a python dictionary; 'wav' saves them as WAV files at
        sampling frequency 'fs'; 'mat' saves them as a MAT file along with
        related variables 'fs', 'freqs', 'trial_order', and 'rms'.
        None will not save any data.
    rand_seed : int | None
        Seed for the random number generator.

    Returns
    -------
    wavs : dict | None
        The stimulus dictionary.
    """
    if rand_seed is None:
        rng = np.random.RandomState()
    else:
        rng = np.random.RandomState(rand_seed)

    # check input arguments
    if save_as is not None and save_as not in ['dict', 'wav', 'hdf5']:
        raise ValueError('"save_as" must be "dict", "wav", or "hdf5"')

    fs = float(fs)
    t = np.arange(np.round(stim_dur * fs)) / fs

    # frequencies equally spaced on a log-2 scale
    freqs = min_freq * np.logspace(0, np.log2(max_freq / float(min_freq)),
                                   num_freqs, endpoint=True, base=2)

    # strings for the filenames / dictionary keys
    freq_names = [str(int(f)) for f in freqs]
    names = ['stim_%s_%s' % (n, f) for n, f in enumerate(freq_names)]

    # generate sinewaves & RMS normalize
    wavs = [np.sin(2 * np.pi * f * t) for f in freqs]
    wavs = [rms / np.sqrt(np.mean(w ** 2)) * w for w in wavs]

    # collect into dictionary & save
    wav_dict = {n: w for (n, w) in zip(names, wavs)}
    if save_as == 'hdf5':
        num_reps = num_trials // num_freqs + 1
        trials = np.tile(range(num_freqs), num_reps)
        trial_order = rng.permutation(trials[0:num_trials])
        wav_dict.update({'trial_order': trial_order, 'freqs': freqs, 'fs': fs,
                         'rms': rms})
        write_hdf5(op.join(output_dir, 'equally_spaced_sinewaves.hdf5'),
                   wav_dict, overwrite=True)
    elif save_as == 'wav':
        for n in names:
            write_wav(op.join(output_dir, n + '.wav'), wav_dict[n], int(fs))
    return wav_dict
c_flash_locs = np.tile(c_flash_locations, 5)
condition_stamp_controls = np.array((range(1, 49)))
c_stamp_controls = np.tile(condition_stamp, 5)
cc = np.vstack(([control_stim], [cflashes], [c_flash_locs], [control_C],
                [c_stamp_controls])).T

############################################################################
# create and store the blocks (should be 15)
blocks = {}
bn = ['Block1', 'Block2', 'Block3', 'Block4', 'Block5', 'Block6', 'Block7',
      'Block8', 'Block9', 'Block10', 'Block11', 'Block12', 'Block13',
      'Block14', 'Block15']
blocks.fromkeys(bn)
n_blocks = total_trials / trials_per_block
for bi in range(1, 16):
    d = c[0:96]    # iter over this to stack into blocks
    stack = cc[:12]
    dd = np.append(d, stack, 0)
    blocks["Block{0}".format(bi)] = rng.permutation(dd)
    np.delete(c, np.s_[:96], 0)
    np.delete(cc, np.s_[:12], 0)


# write out result:
print('Saving stimuli variables')
Stim_vars = dict(space_conditions=space_conditions,
                 nocomp_stim_name=nocomp_stim_name, taud_stim=taud_stim,
                 blocks=blocks, flashes=flashes)
np.savez('stim', **Stim_vars)
write_hdf5(op.join(work_dir, 'Stim_vars.hdf5'), Stim_vars, overwrite=True)
plt.gca().spines['right'].set_visible(False)
plt.xlim([0,21.25])
plt.xlabel(u'Central threshold (°)')
plt.ylabel('Performance improvement \n (% correct)')
plt.subplots_adjust(left=0.4, right=.97, top=0.95, bottom=0.2)
plt.savefig(path + 'stem_correct.pdf', dpi=600)

improvements = -np.diff(thresholds, 1, -1)


# %% some stats

ax = plt.figure(figsize=(4.2, 2.8))
dist = np.mean(np.diff(per_cor, 1, -2), -1).squeeze()
inds = np.argsort(dist)
write_hdf5('effectsize.hdf5', dist, overwrite=True)


plt.plot(np.arange(20) + 1, dist[inds], '^', c='C2', ms=7)

plt.plot(np.arange(20) + 1, perform_imp[inds], 'd', mec='C2', mfc='w', ms=7)

plt.errorbar(23.6, dist.mean(), dist.std() / np.sqrt(20), fmt='^', color='C2', 
             ms=10, lw=1.5, capsize=3)
plt.errorbar(24.4, perform_imp.mean(), perform_imp.std() / np.sqrt(20), 
             fmt='d', mec='C2', mfc='w', color='C2', ms=10, lw=1.5, capsize=3)

plt.plot([0, 28], [0,0], 'k--', zorder=-5)
plt.xlim([0, 25])
plt.xlabel('Subjects')
plt.ylabel('Improvement \n (percent correct)')