Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/structured specs #271

Merged
merged 14 commits into from
Oct 31, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 2 additions & 2 deletions libensemble/alloc_funcs/fast_alloc.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
to evaluate in the simulation function. The fields in ``sim_specs['in']``
are given. If all entries in `H` have been given a be evaluated, a worker
is told to call the generator function, provided this wouldn't result in
more than ``gen_specs['num_active_gen']`` active generators.
more than ``gen_specs['user']['num_active_gen']`` active generators.

:See:
``/libensemble/tests/regression_tests/test_fast_alloc.py``
Expand All @@ -23,7 +23,7 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
sim_work(Work, i, sim_specs['in'], [persis_info['next_to_give']], [])
persis_info['next_to_give'] += 1

elif gen_count < gen_specs.get('num_active_gens', gen_count+1):
elif gen_count < gen_specs['user'].get('num_active_gens', gen_count+1):

# Give gen work
persis_info['total_gen_calls'] += 1
Expand Down
20 changes: 10 additions & 10 deletions libensemble/alloc_funcs/fast_alloc_and_pausing.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,16 +9,16 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
to evaluate in the simulation function. The fields in ``sim_specs['in']``
are given. If all entries in `H` have been given a be evaluated, a worker
is told to call the generator function, provided this wouldn't result in
more than ``gen_specs['num_active_gen']`` active generators. Also allows
more than ``gen_specs['user']['num_active_gen']`` active generators. Also allows
for a 'batch_mode'.

When there are multiple objective components, this allocation function
does not evaluate further components for some point in the following
scenarios:

alloc_specs['stop_on_NaNs']: True --- after a NaN has been found in returned in some
alloc_specs['user']['stop_on_NaNs']: True --- after a NaN has been found in returned in some
objective component
allocated['stop_partial_fvec_eval']: True --- after the value returned from
alloc_specs['user']['stop_partial_fvec_eval']: True --- after the value returned from
combine_component_func is larger than a known upper bound on the objective.

:See:
Expand Down Expand Up @@ -46,14 +46,14 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
if len(persis_info['need_to_give']):
# If 'stop_on_NaN' is true and any f_i is a NaN, then pause
# evaluations of other f_i, corresponding to the same pt_id
if 'stop_on_NaNs' in alloc_specs and alloc_specs['stop_on_NaNs']:
if alloc_specs['user'].get('stop_on_NaNs'):
pt_ids_to_pause.update(H['pt_id'][np.isnan(H['f_i'])])

# If 'stop_partial_fvec_eval' is true, pause entries in H if a
# partial combine_component_func evaluation is # worse than the
# best, known, complete evaluation (and the point is not a
# local_pt).
if 'stop_partial_fvec_eval' in alloc_specs and alloc_specs['stop_partial_fvec_eval']:
if alloc_specs['user'].get('stop_partial_fvec_eval'):
pt_ids = set(persis_info['pt_ids']) - persis_info['has_nan'] - persis_info['complete']
pt_ids = np.array(list(pt_ids))
partial_fvals = np.zeros(len(pt_ids))
Expand All @@ -71,11 +71,11 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):

if np.all(H['returned'][a1]):
persis_info['complete'].add(pt_id)
persis_info['best_complete_val'] = min(persis_info['best_complete_val'], gen_specs['combine_component_func'](H['f_i'][a1]))
persis_info['best_complete_val'] = min(persis_info['best_complete_val'], gen_specs['user']['combine_component_func'](H['f_i'][a1]))
else:
# Ensure combine_component_func calculates partial fevals correctly
# with H['f_i'] = 0 for non-returned point
partial_fvals[j] = gen_specs['combine_component_func'](H['f_i'][a1])
partial_fvals[j] = gen_specs['user']['combine_component_func'](H['f_i'][a1])

if len(persis_info['complete']) and len(pt_ids) > 1:

Expand All @@ -102,13 +102,13 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
i, idle_workers = idle_workers[0], idle_workers[1:]
sim_work(Work, i, sim_specs['in'], [next_row], [])

elif gen_count < gen_specs.get('num_active_gens', gen_count+1):
elif gen_count < gen_specs['user'].get('num_active_gens', gen_count+1):
lw = persis_info['last_worker']

last_size = persis_info.get('last_size')
if len(H):
# Don't give gen instances in batch mode if points are unfinished
if (gen_specs.get('batch_mode')
if (gen_specs['user'].get('batch_mode')
and not all(np.logical_or(H['returned'][last_size:],
H['paused'][last_size:]))):
break
Expand All @@ -131,7 +131,7 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):

persis_info['last_worker'] = i

elif gen_count >= gen_specs.get('num_active_gens', gen_count+1):
elif gen_count >= gen_specs['user'].get('num_active_gens', gen_count+1):
idle_workers = []

return Work, persis_info
6 changes: 3 additions & 3 deletions libensemble/alloc_funcs/fast_alloc_to_aposmm.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
to evaluate in the simulation function. The fields in ``sim_specs['in']``
are given. If all entries in `H` have been given a be evaluated, a worker
is told to call the generator function, provided this wouldn't result in
more than ``gen_specs['num_active_gen']`` active generators. Also allows
more than ``gen_specs['user']['num_active_gen']`` active generators. Also allows
for a 'batch_mode'.

:See:
Expand All @@ -27,13 +27,13 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
sim_work(Work, i, sim_specs['in'], [persis_info['next_to_give']], [])
persis_info['next_to_give'] += 1

elif gen_count < gen_specs.get('num_active_gens', gen_count+1):
elif gen_count < gen_specs['user'].get('num_active_gens', gen_count+1):
lw = persis_info['last_worker']

last_size = persis_info.get('last_size')
if len(H):
# Don't give gen instances in batch mode if points are unfinished
if (gen_specs.get('batch_mode')
if (gen_specs['user'].get('batch_mode')
and not all(np.logical_or(H['returned'][last_size:],
H['paused'][last_size:]))):
break
Expand Down
10 changes: 5 additions & 5 deletions libensemble/alloc_funcs/give_sim_work_first.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,10 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
"""
Decide what should be given to workers. This allocation function gives any
available simulation work first, and only when all simulations are
completed or running does it start (at most ``gen_specs['num_active_gens']``)
completed or running does it start (at most ``gen_specs['user']['num_active_gens']``)
generator instances.

Allows for a ``gen_specs['batch_mode']`` where no generation
Allows for a ``gen_specs['user']['batch_mode']`` where no generation
work is given out unless all entries in ``H`` are returned.

Allows for ``blocking`` of workers that are not active, for example, so
Expand Down Expand Up @@ -39,7 +39,7 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
# Pick all high priority, oldest high priority, or just oldest point
if 'priority' in H.dtype.fields:
priorities = H['priority'][~H['allocated']]
if gen_specs.get('give_all_with_same_priority'):
if gen_specs['user'].get('give_all_with_same_priority'):
q_inds = (priorities == np.max(priorities))
else:
q_inds = np.argmax(priorities)
Expand Down Expand Up @@ -68,12 +68,12 @@ def give_sim_work_first(W, H, sim_specs, gen_specs, alloc_specs, persis_info):
else:

# Allow at most num_active_gens active generator instances
if gen_count >= gen_specs.get('num_active_gens', gen_count+1):
if gen_count >= gen_specs['user'].get('num_active_gens', gen_count+1):
break

# No gen instances in batch mode if workers still working
still_working = ~H['returned']
if gen_specs.get('batch_mode') and np.any(still_working):
if gen_specs['user'].get('batch_mode') and np.any(still_working):
break

# Give gen work
Expand Down
2 changes: 1 addition & 1 deletion libensemble/alloc_funcs/inverse_bayes_allocf.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ def only_persistent_gens_for_inverse_bayes(W, H, sim_specs, gen_specs, alloc_spe
inds_to_send_back = np.where(np.logical_and(inds_generated_by_i,
last_batch_inds))[0]
if H['batch'][-1] > 0:
n = gen_specs['subbatch_size']*gen_specs['num_subbatches']
n = gen_specs['user']['subbatch_size']*gen_specs['user']['num_subbatches']
k = H['batch'][-1]
H['weight'][(n*(k-1)):(n*k)] = H['weight'][(n*k):(n*(k+1))]

Expand Down
2 changes: 1 addition & 1 deletion libensemble/alloc_funcs/persistent_aposmm_alloc.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ def persistent_aposmm_alloc(W, H, sim_specs, gen_specs, alloc_specs, persis_info

# If any persistent worker's calculated values have returned, give them back.
for i in avail_worker_ids(W, persistent=True):
if persis_info.get('sample_done') or sum(H['returned']) >= gen_specs['initial_sample_size']:
if persis_info.get('sample_done') or sum(H['returned']) >= gen_specs['user']['initial_sample_size']:
# Don't return if the initial sample is not complete
persis_info['sample_done'] = True

Expand Down
2 changes: 1 addition & 1 deletion libensemble/alloc_funcs/start_persistent_local_opt_gens.py
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ def start_persistent_local_opt_gens(W, H, sim_specs, gen_specs, alloc_specs, per
# Find candidates to start local opt runs if a sample has been evaluated
if np.any(np.logical_and(~H['local_pt'], H['returned'])):
n, _, _, _, r_k, mu, nu = initialize_APOSMM(H, gen_specs)
update_history_dist(H, n, gen_specs, c_flag=False)
update_history_dist(H, n, gen_specs['user'], c_flag=False)
starting_inds = decide_where_to_start_localopt(H, r_k, mu, nu)
else:
starting_inds = []
Expand Down