MilesCranmer commited on
Commit
4854265
1 Parent(s): 4ff119b

Add optional timeout

Browse files
Files changed (2) hide show
  1. eureqa.py +8 -1
  2. hyperparamopt.py +16 -10
eureqa.py CHANGED
@@ -23,6 +23,7 @@ def eureqa(X=None, y=None, threads=4, parsimony=1e-3, alpha=10,
23
  weightSimplify=0.05,
24
  weightRandomize=0.25,
25
  weightDoNothing=1.0,
 
26
  ):
27
  """ Runs symbolic regression in Julia, to fit y given X.
28
  Either provide a 2D numpy array for X, 1D array for y, or declare a test to run.
@@ -146,10 +147,16 @@ def eureqa(X=None, y=None, threads=4, parsimony=1e-3, alpha=10,
146
  '-e',
147
  f'\'include(".hyperparams_{rand_string}.jl"); include(".dataset_{rand_string}.jl"); include("eureqa.jl"); fullRun({niterations:d}, npop={npop:d}, annealing={"true" if annealing else "false"}, ncyclesperiteration={ncyclesperiteration:d}, fractionReplaced={fractionReplaced:f}f0, verbosity=round(Int32, 1e9), topn={topn:d})\'',
148
  ]
 
 
149
  cur_cmd = ' '.join(command)
150
  print("Running on", cur_cmd)
151
  os.system(cur_cmd)
152
- output = pd.read_csv(equation_file, sep="|")
 
 
 
 
153
  os.system(starting_path)
154
  return output
155
 
 
23
  weightSimplify=0.05,
24
  weightRandomize=0.25,
25
  weightDoNothing=1.0,
26
+ timeout=None,
27
  ):
28
  """ Runs symbolic regression in Julia, to fit y given X.
29
  Either provide a 2D numpy array for X, 1D array for y, or declare a test to run.
 
147
  '-e',
148
  f'\'include(".hyperparams_{rand_string}.jl"); include(".dataset_{rand_string}.jl"); include("eureqa.jl"); fullRun({niterations:d}, npop={npop:d}, annealing={"true" if annealing else "false"}, ncyclesperiteration={ncyclesperiteration:d}, fractionReplaced={fractionReplaced:f}f0, verbosity=round(Int32, 1e9), topn={topn:d})\'',
149
  ]
150
+ if timeout is not None:
151
+ command = [f'timeout {timeout}'] + command
152
  cur_cmd = ' '.join(command)
153
  print("Running on", cur_cmd)
154
  os.system(cur_cmd)
155
+ try:
156
+ output = pd.read_csv(equation_file, sep="|")
157
+ except FileNotFoundError:
158
+ print("Couldn't find equation file!")
159
+ output = pd.DataFrame()
160
  os.system(starting_path)
161
  return output
162
 
hyperparamopt.py CHANGED
@@ -4,7 +4,6 @@ import numpy as np
4
  import pickle as pkl
5
  import hyperopt
6
  from hyperopt import hp, fmin, tpe, Trials
7
- import signal
8
  import eureqa
9
 
10
 
@@ -21,29 +20,35 @@ def run_trial(args):
21
 
22
  """
23
 
 
24
  for key in 'niterations npop ncyclesperiteration topn'.split(' '):
25
  args[key] = int(args[key])
26
 
 
 
 
 
27
  def handler(signum, frame):
 
28
  raise ValueError("Takes too long")
29
 
30
- signal.signal(signal.SIGALRM, handler)
31
  maxTime = 60
32
  ntrials = 1 #3
33
  equation_file=f'hall_of_fame_{np.random.rand():f}.csv'
34
- signal.alarm(maxTime)
35
 
36
  try:
37
  trials = []
38
  for i in range(1, 2):
39
- trials.append([np.min(eureqa.eureqa(
40
  test=f"simple{i}",
41
- threads=20,
42
  binary_operators=["plus", "mult", "pow", "div"],
43
  unary_operators=["cos", "exp", "sin", "log"],
44
  equation_file=equation_file,
45
- **args)['MSE']) for _ in range(ntrials)])
46
- signal.alarm(0)
 
 
47
  except ValueError:
48
  return {
49
  'status': 'ok', # or 'fail' if nan loss
@@ -51,6 +56,7 @@ def run_trial(args):
51
  }
52
 
53
  loss = np.average(trials)
 
54
 
55
  return {
56
  'status': 'ok', # or 'fail' if nan loss
@@ -59,9 +65,9 @@ def run_trial(args):
59
 
60
 
61
  space = {
62
- 'niterations': hp.qloguniform('niterations', np.log(10), 0.5, 1),
63
- 'npop': hp.qloguniform('npop', np.log(100), 0.5, 1),
64
- 'ncyclesperiteration': hp.qloguniform('ncyclesperiteration', np.log(5000), 0.5, 1),
65
  'topn': hp.quniform('topn', 1, 30, 1),
66
  'annealing': hp.choice('annealing', [False, True]),
67
  'alpha': hp.lognormal('alpha', np.log(10.0), 0.5),
 
4
  import pickle as pkl
5
  import hyperopt
6
  from hyperopt import hp, fmin, tpe, Trials
 
7
  import eureqa
8
 
9
 
 
20
 
21
  """
22
 
23
+ print("Running on", args)
24
  for key in 'niterations npop ncyclesperiteration topn'.split(' '):
25
  args[key] = int(args[key])
26
 
27
+ if args['npop'] < 50 or args['ncyclesperiteration'] < 3:
28
+ print("Bad parameters")
29
+ return {'status': 'ok', 'loss': np.inf}
30
+
31
  def handler(signum, frame):
32
+ print("Took too long. Skipping.")
33
  raise ValueError("Takes too long")
34
 
 
35
  maxTime = 60
36
  ntrials = 1 #3
37
  equation_file=f'hall_of_fame_{np.random.rand():f}.csv'
 
38
 
39
  try:
40
  trials = []
41
  for i in range(1, 2):
42
+ trial = eureqa.eureqa(
43
  test=f"simple{i}",
44
+ threads=4,
45
  binary_operators=["plus", "mult", "pow", "div"],
46
  unary_operators=["cos", "exp", "sin", "log"],
47
  equation_file=equation_file,
48
+ timeout=maxTime,
49
+ **args)
50
+ if len(trial) == 0: raise ValueError
51
+ trials.append([np.min(trial['MSE'])])
52
  except ValueError:
53
  return {
54
  'status': 'ok', # or 'fail' if nan loss
 
56
  }
57
 
58
  loss = np.average(trials)
59
+ print(args, "got", loss)
60
 
61
  return {
62
  'status': 'ok', # or 'fail' if nan loss
 
65
 
66
 
67
  space = {
68
+ 'niterations': hp.qlognormal('niterations', np.log(10), 0.5, 1),
69
+ 'npop': hp.qlognormal('npop', np.log(100), 0.5, 1),
70
+ 'ncyclesperiteration': hp.qlognormal('ncyclesperiteration', np.log(5000), 0.5, 1),
71
  'topn': hp.quniform('topn', 1, 30, 1),
72
  'annealing': hp.choice('annealing', [False, True]),
73
  'alpha': hp.lognormal('alpha', np.log(10.0), 0.5),