From 566de690725e8a44ff1f2a653ae728b9cbf99095 Mon Sep 17 00:00:00 2001 From: "W. Trevor King" Date: Fri, 17 Aug 2012 14:51:30 -0400 Subject: [PATCH] Add --num-* arguments to calibcant-calibrate.py. This allows you to adjust the number of surface bumps, temperature measurements, and thermal vibration measurements from the command line, which is much more convenient than editing the calibcant.config file directly. You can also skip a troublesome phase. For example, if you want to look at the vibration data without running surface bumps, you can try: $ calibcant-calibrate.py --num-bumps 0 $ calibcant-plot.py *.h5 I adjusted analyze_all() so it can keep working even with one of the num-* configs set to zero, although you won't be able to get a valid calibration without at least one of each type of measurement. --- bin/calibcant-calibrate.py | 47 ++++++++++++++++++++++++++++++++++--- calibcant/analyze.py | 48 ++++++++++++++++++++++---------------- 2 files changed, 72 insertions(+), 23 deletions(-) diff --git a/bin/calibcant-calibrate.py b/bin/calibcant-calibrate.py index 3d20ab3..5cf5a92 100755 --- a/bin/calibcant-calibrate.py +++ b/bin/calibcant-calibrate.py @@ -7,7 +7,7 @@ (``pyafm.storage.load_afm()``). """ -import os +import argparse as _argparse import time as _time from calibcant.calibrate import Calibrator as _Calibrator @@ -15,7 +15,22 @@ from pyafm.storage import load_afm as _load_afm import calibcant.config as _config +_module_doc = __doc__ + def main(args): + parser = _argparse.ArgumentParser(description=_module_doc) + parser.add_argument( + '--num-bumps', type=int, + help='Number of surface bumps') + parser.add_argument( + '--num-temperatures', type=int, + help='Number of temperature measurements') + parser.add_argument( + '--num-vibrations', type=int, + help='Number of thermal vibration measurements') + + args = parser.parse_args(args) + timestamp = '{0}-{1:02d}-{2:02d}T{3:02d}-{4:02d}-{5:02d}'.format( *_time.localtime()) filename = '{}-calibcant-data.h5'.format(timestamp) @@ -25,6 +40,20 @@ def main(args): {'model':_config.Linear, 'initial-position':-150e-9}) config['temperature'] = _config.TemperatureConfig() config['vibration'] = _config.VibrationConfig() + if args.num_bumps is None: + args.num_bumps = config['num-bumps'] + else: + config['num-bumps'] = args.num_bumps + if args.num_temperatures is None: + args.num_temperatures = config['num-temperatures'] + else: + config['num-temperatures'] = args.num_temperatures + if args.num_vibrations is None: + args.num_vibrations = config['num-vibrations'] + else: + config['num-vibrations'] = args.num_vibrations + insufficient_calibration_data = 0 in [ + args.num_bumps, args.num_temperatures, args.num_vibrations] devices = [] try: afm = _load_afm() @@ -34,7 +63,10 @@ def main(args): deflection = afm.piezo.read_deflection() try: afm.stepper_approach(target_deflection=deflection + 1e3) - k,k_s,data = calibrator.calibrate(filename=filename) + if insufficient_calibration_data: + data = calibrator.acquire(filename=filename) + else: + k,k_s,data = calibrator.calibrate(filename=filename) except: afm.move_away_from_surface() afm.piezo.zero() @@ -42,7 +74,16 @@ def main(args): finally: for device in devices: device.close() - print 'k: {:g} +/- {:g}'.format(k, k_s) + if insufficient_calibration_data: + for count,field,label in [ + (args.num_bumps, 'bump', 'photodiode sensitivity (V/m)'), + (args.num_temperatures, 'temperature', 'temperature (K)'), + (args.num_vibrations, 'vibration', 'variance (V**2)')]: + if count: + d = data[field] + print('{}: {:g} +/- {:g}'.format(label, d.mean(), d.std())) + else: + print('k: {:g} +/- {:g}'.format(k, k_s)) return 0 if __name__ == '__main__': diff --git a/calibcant/analyze.py b/calibcant/analyze.py index f8d1bdd..ec33d56 100644 --- a/calibcant/analyze.py +++ b/calibcant/analyze.py @@ -224,13 +224,22 @@ def analyze_all(config, data, raw_data, maximum_relative_error=1e-5, if not data.get('vibrations', None): data['vibration'] = _numpy.zeros( (config['num-vibrations'],), dtype=float) + if 'raw' not in data: + data['raw'] = {} + if 'bump' not in data['raw']: + data['raw']['bump'] = _numpy.zeros((config['num-bumps'],), dtype=float) + if 'temperature' not in data['raw']: + data['raw']['temperature'] = _numpy.zeros( + (config['num-temperatures'],), dtype=float) + if 'vibration' not in data['raw']: + data['raw']['vibration'] = _numpy.zeros( + (config['num-vibrations'],), dtype=float) axis_config = config['afm']['piezo'].select_config( setting_name='axes', attribute_value=config['afm']['main-axis'], get_attribute=_get_axis_name) input_config = config['afm']['piezo'].select_config( setting_name='inputs', attribute_value='deflection') - bumps_changed = temperatures_changed = vibrations_changed = False calibration_group = None if not isinstance(group, _h5py.Group) and not dry_run: f = _h5py.File(filename, mode='a') @@ -238,9 +247,8 @@ def analyze_all(config, data, raw_data, maximum_relative_error=1e-5, else: f = None try: - if len(data.get('raw', {}).get('bump', [])) != len(data['bump']): - bumps_changed = True - for i,bump in enumerate(raw_data['bump']): + bumps_changed = len(data['raw']['bump']) != len(data['bump']) + for i,bump in enumerate(raw_data.get('bump', [])): # compare values data['bump'][i],changed = check_bump( index=i, bump=bump, config=config, z_axis_config=axis_config, deflection_channel_config=input_config, plot=plot, @@ -249,10 +257,9 @@ def analyze_all(config, data, raw_data, maximum_relative_error=1e-5, bumps_changed = True bump_group = _h5_create_group(group, 'bump/{}'.format(i)) _bump_save(group=bump_group, processed=data['bump'][i]) - if len(data.get('raw', {}).get('temperature', []) - ) != len(data['temperature']): - temperatures_changed = True - for i,temperature in enumerate(raw_data['temperature']): + temperatures_changed = len(data['raw']['temperature']) != len( + data['temperature']) + for i,temperature in enumerate(raw_data.get('temperature', [])): data['temperature'][i],changed = check_temperature( index=i, temperature=temperature, config=config, maximum_relative_error=maximum_relative_error) @@ -262,10 +269,9 @@ def analyze_all(config, data, raw_data, maximum_relative_error=1e-5, group, 'temperature/{}'.format(i)) _temperature_save( group=temperature_group, processed=data['temperature'][i]) - if len(data.get('raw', {}).get('vibration', []) - ) != len(data['vibration']): - vibrations_changed = True - for i,vibration in enumerate(raw_data['vibration']): + vibrations_changed = len(data['raw']['vibration']) != len( + data['vibration']) + for i,vibration in enumerate(raw_data.get('vibration', [])): data['vibration'][i],changed = check_vibration( index=i, vibration=vibration, config=config, deflection_channel_config=input_config, plot=plot, @@ -288,18 +294,20 @@ def analyze_all(config, data, raw_data, maximum_relative_error=1e-5, if vibrations_changed: save_results( group=calibration_group, vibration=data['vibration']) - if len(raw_data['bump']) != len(data['bump']): + if len(raw_data.get('bump', [])) != len(data['bump']): raise ValueError( 'not enough raw bump data: {} of {}'.format( - len(raw_data['bump']), len(data['bump']))) - if len(raw_data['temperature']) != len(data['temperature']): + len(raw_data.get('bump', [])), len(data['bump']))) + if len(raw_data.get('temperature', [])) != len(data['temperature']): raise ValueError( 'not enough raw temperature data: {} of {}'.format( - len(raw_data['temperature']), len(data['temperature']))) + len(raw_data.get('temperature', [])), + len(data['temperature']))) if len(raw_data['vibration']) != len(data['vibration']): raise ValueError( 'not enough raw vibration data: {} of {}'.format( - len(raw_data['vibration']), len(data['vibration']))) + len(raw_data.get('vibration', [])), + len(data['vibration']))) k,k_s,changed = check_calibration( k=data.get('processed', {}).get('spring_constant', None), k_s=data.get('processed', {}).get( @@ -317,9 +325,9 @@ def analyze_all(config, data, raw_data, maximum_relative_error=1e-5, if f: f.close() if plot: - _plot(bumps=data['raw']['bump'], - temperatures=data['raw']['temperature'], - vibrations=data['raw']['vibration']) + _plot(bumps=data['bump'], + temperatures=data['temperature'], + vibrations=data['vibration']) return (k, k_s) def check_bump(index, bump, config=None, maximum_relative_error=0, **kwargs): -- 2.26.2