coco-experiment 2.8.3__tar.gz → 2.8.4__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/PKG-INFO +1 -1
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/_version.py +1 -1
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/coco.c +1 -1
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/interface.pyx +8 -1
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/noiser.py +48 -23
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/utilities.py +13 -4
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/.gitignore +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/LICENSE +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/README.md +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/meson.build +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/pyproject.toml +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/scripts/run-doctest.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/__init__.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/bare_problem.pyx +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/coco.h +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/download_example.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/exceptions.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/src/cocoex/solvers.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/tests/bbob2009_testcases.txt +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/tests/bbob2009_testcases2.txt +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/tests/test_bare_problem.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/tests/test_regression.py +0 -0
- {coco_experiment-2.8.3 → coco_experiment-2.8.4}/tests/test_suite.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.5
|
|
2
2
|
Name: coco-experiment
|
|
3
|
-
Version: 2.8.
|
|
3
|
+
Version: 2.8.4
|
|
4
4
|
Summary: Benchmarking framework for all types of black-box optimization algorithms.
|
|
5
5
|
Project-URL: Homepage, https://github.com/numbbo/coco-experiment
|
|
6
6
|
Project-URL: Documentation, https://numbbo.github.io/coco-doc/apidocs/cocoex/
|
|
@@ -31553,7 +31553,7 @@ void coco_archive_free(coco_archive_t *archive) {
|
|
|
31553
31553
|
* don't change, don't track in version control!
|
|
31554
31554
|
*/
|
|
31555
31555
|
|
|
31556
|
-
const char *coco_version = "2.8.
|
|
31556
|
+
const char *coco_version = "2.8.4";
|
|
31557
31557
|
#line 1 "coco_runtime_c.c"
|
|
31558
31558
|
/**
|
|
31559
31559
|
* @file coco_runtime_c.c
|
|
@@ -83,6 +83,7 @@ cdef extern from "coco.h":
|
|
|
83
83
|
void bbob_problem_best_parameter_print(const coco_problem_t *problem)
|
|
84
84
|
void bbob_biobj_problem_best_parameter_print(const coco_problem_t *problem)
|
|
85
85
|
|
|
86
|
+
cdef extern double coco_problem_get_best_value(coco_problem_t *p) # copied from bare_problem.pyx
|
|
86
87
|
|
|
87
88
|
cdef bytes _bstring(s):
|
|
88
89
|
if type(s) is bytes:
|
|
@@ -556,7 +557,7 @@ cdef class Problem:
|
|
|
556
557
|
raise RuntimeError("Problem already initialized")
|
|
557
558
|
if problem == NULL:
|
|
558
559
|
raise ValueError("in Problem._initialize(problem,...): problem is NULL")
|
|
559
|
-
self.problem = problem
|
|
560
|
+
self.problem = problem # should probably be private ._problem?
|
|
560
561
|
self._problem_index = coco_problem_get_suite_dep_index(self.problem)
|
|
561
562
|
self._do_free = free
|
|
562
563
|
self._list_of_observers = []
|
|
@@ -783,6 +784,12 @@ cdef class Problem:
|
|
|
783
784
|
"""
|
|
784
785
|
assert(self.problem)
|
|
785
786
|
return bool(coco_problem_final_target_hit(self.problem))
|
|
787
|
+
@property
|
|
788
|
+
def _best_value(self):
|
|
789
|
+
"""return best f-value
|
|
790
|
+
"""
|
|
791
|
+
assert(self.problem)
|
|
792
|
+
return coco_problem_get_best_value(self.problem)
|
|
786
793
|
#@property
|
|
787
794
|
#def final_target_fvalue1(self):
|
|
788
795
|
# assert(self.problem)
|
|
@@ -8,8 +8,12 @@ import json
|
|
|
8
8
|
import numpy as np # for checking finite values
|
|
9
9
|
|
|
10
10
|
_frozen_noise = True
|
|
11
|
-
math_floor = int
|
|
12
11
|
parameters_file = 'noiser_parameters.json'
|
|
12
|
+
'''default file name where to save current parameters of `Noisifier`'''
|
|
13
|
+
save_parameters = False
|
|
14
|
+
'''flag whether `Noisifier.__init__` saves noise parameters in file'''
|
|
15
|
+
|
|
16
|
+
math_floor = int
|
|
13
17
|
|
|
14
18
|
def rand(x, i=0):
|
|
15
19
|
"""return a uniform random value seeded with ``x[:2]`` and `i`"""
|
|
@@ -20,7 +24,7 @@ def randn(x, i=0):
|
|
|
20
24
|
def randc(x, i=0):
|
|
21
25
|
"""return a Cauchy random value seeded with ``x[:2]`` and `i`.
|
|
22
26
|
|
|
23
|
-
We observe that median
|
|
27
|
+
We observe that ``median(|Z|) == 1`` and ``p(pi x Z / 2 > a) == 1/a``.
|
|
24
28
|
"""
|
|
25
29
|
return _cauchy(1, _seed(x, i))[0]
|
|
26
30
|
|
|
@@ -71,6 +75,10 @@ class Noisifier:
|
|
|
71
75
|
noise generator and the numbers scaled by pi/2 such that P(number > k)
|
|
72
76
|
equals about 1/k when k >= 5.
|
|
73
77
|
|
|
78
|
+
Parameter settings are by default saved to the file indicated by the module
|
|
79
|
+
global variable `cocoex.noiser.parameters_file` if
|
|
80
|
+
``bool(cocoex.noiser.save_parameters) is True``.
|
|
81
|
+
|
|
74
82
|
A minimal regression test:
|
|
75
83
|
|
|
76
84
|
>>> import cocoex
|
|
@@ -95,7 +103,7 @@ class Noisifier:
|
|
|
95
103
|
"""
|
|
96
104
|
p_add_single_default = 0.2
|
|
97
105
|
def __init__(self, p_add=None, p_subtract=0.0, p_epsilon=0.0, epsilon=1e-4,
|
|
98
|
-
rands=(rand, randn, randc)):
|
|
106
|
+
rands=(rand, randn, randc), filename=None):
|
|
99
107
|
"""constructor with 4 optional parameters for the noise model,
|
|
100
108
|
|
|
101
109
|
`p_add`: probability for adding a positive heavy tail random value
|
|
@@ -108,6 +116,11 @@ class Noisifier:
|
|
|
108
116
|
`p_epsilon`: probability for adding a Gaussian random value
|
|
109
117
|
|
|
110
118
|
`epsilon`: standard deviation of the Gaussian random value
|
|
119
|
+
|
|
120
|
+
`filename`: for saving parameter setting, if not given use module global
|
|
121
|
+
variable `cocoex.noiser.parameters_file`, saving depends on the module
|
|
122
|
+
variable `save_parameters`.
|
|
123
|
+
|
|
111
124
|
"""
|
|
112
125
|
if p_add is None:
|
|
113
126
|
if p_subtract == p_epsilon == 0:
|
|
@@ -116,15 +129,17 @@ class Noisifier:
|
|
|
116
129
|
p_add = 0.0
|
|
117
130
|
self._params = {k: v for k, v in locals().items() if k != 'self'}
|
|
118
131
|
if sum(self._params[p] for p in ('p_subtract', 'p_add')) > 1:
|
|
119
|
-
warnings.warn("p_subtract={0} + p_add={1} > 1, hence p_add
|
|
120
|
-
" as ``1-p_subtract``"
|
|
132
|
+
warnings.warn("p_subtract={0} + p_add={1} > 1, hence p_add" # noqa: UP030
|
|
133
|
+
" is interpreted as ``1-p_subtract``"
|
|
121
134
|
.format(self._params['p_subtract'], self._params['p_add']))
|
|
122
135
|
if p_add < 0 or p_subtract < 0 or p_epsilon < 0 or epsilon < 0:
|
|
123
|
-
raise ValueError("parameters cannot be negative
|
|
124
|
-
.format(self._params))
|
|
136
|
+
raise ValueError("parameters cannot be negative" # noqa: UP030, UP032
|
|
137
|
+
" but were {0}".format(self._params))
|
|
125
138
|
if p_epsilon > 0 and epsilon == 0:
|
|
126
|
-
warnings.warn("p_epsilon = {0} > 0 is not effective
|
|
127
|
-
.format(p_epsilon))
|
|
139
|
+
warnings.warn("p_epsilon = {0} > 0 is not effective" # noqa: UP030, UP032
|
|
140
|
+
" because epsilon = 0".format(p_epsilon))
|
|
141
|
+
if save_parameters:
|
|
142
|
+
self.save_parameters()
|
|
128
143
|
|
|
129
144
|
def noisify(self, problem):
|
|
130
145
|
"""wrap `problem` with frozen noise"""
|
|
@@ -135,23 +150,19 @@ class Noisifier:
|
|
|
135
150
|
def parameters(self):
|
|
136
151
|
return {k: v for (k, v) in self._params.items() if k.startswith(('p_', 'eps'))}
|
|
137
152
|
|
|
138
|
-
def
|
|
139
|
-
|
|
153
|
+
def save_parameters(self, filename=None):
|
|
154
|
+
"""save parameter `dict` to a `json` file"""
|
|
155
|
+
with open(filename or self._params.get('filename')
|
|
156
|
+
or parameters_file, 'wt') as fp:
|
|
140
157
|
json.dump(self.parameters, fp)
|
|
141
158
|
|
|
142
|
-
def
|
|
143
|
-
|
|
144
|
-
with open(parameters_file, 'rt') as fp:
|
|
145
|
-
return json.load(fp)
|
|
146
|
-
except warn_errors as e:
|
|
147
|
-
warnings.warn('NoisifyProblem._load_params raised the exception "{0}"'.format(e))
|
|
148
|
-
except ignore_errors:
|
|
149
|
-
pass
|
|
150
|
-
return {}
|
|
159
|
+
def _set_params(self, filename=None, **kwargs):
|
|
160
|
+
"""set parameters from file `filename` or filename passed at
|
|
151
161
|
|
|
152
|
-
|
|
153
|
-
"""
|
|
154
|
-
self._params.update(self.
|
|
162
|
+
instantiation or `cocoex.noiser.parameters_file`.
|
|
163
|
+
"""
|
|
164
|
+
self._params.update(_read_params(filename or self._params.get('filename')
|
|
165
|
+
or parameters_file), **kwargs)
|
|
155
166
|
|
|
156
167
|
def __getattr__(self, name):
|
|
157
168
|
"""pretend to be a COCO `problem` as passed in `noisify`"""
|
|
@@ -211,6 +222,20 @@ class Noisifier:
|
|
|
211
222
|
assert np.isfinite(n)
|
|
212
223
|
return n
|
|
213
224
|
|
|
225
|
+
|
|
226
|
+
def _read_params(filename=None,
|
|
227
|
+
warn_errors=(FileNotFoundError,), ignore_errors=()):
|
|
228
|
+
"""read parameters from a json file and return a parameters `dict`"""
|
|
229
|
+
try:
|
|
230
|
+
with open(filename or parameters_file, 'rt') as fp:
|
|
231
|
+
return json.load(fp)
|
|
232
|
+
except warn_errors as e:
|
|
233
|
+
warnings.warn('noiser._read_params raised the exception: ' + str(e))
|
|
234
|
+
except ignore_errors:
|
|
235
|
+
pass
|
|
236
|
+
return {}
|
|
237
|
+
|
|
238
|
+
|
|
214
239
|
_seed_weights = [1.23468, 2.34579] # otherwise, coordinate search would be noisefree
|
|
215
240
|
_seeds = collections.deque(maxlen=99) # for the record only
|
|
216
241
|
def _seed(x, i=0):
|
|
@@ -600,6 +600,9 @@ class ExperimentRepeater:
|
|
|
600
600
|
sweeps until some given budget is exhaused, namely, ``budget_multiplier
|
|
601
601
|
* dimension``.
|
|
602
602
|
|
|
603
|
+
CAVEAT: this works as desired only when all instances of the same problem
|
|
604
|
+
are run in the same batch, as it is the case with `BatchScheduler`.
|
|
605
|
+
|
|
603
606
|
Example code snippet::
|
|
604
607
|
|
|
605
608
|
[...]
|
|
@@ -934,6 +937,9 @@ class ExperimentRepeater:
|
|
|
934
937
|
class BatchScheduler:
|
|
935
938
|
"""Facilitate to run a benchmarking experiment in independent batches.
|
|
936
939
|
|
|
940
|
+
All instances of the same ``(function, dimension)`` belong to the same
|
|
941
|
+
batch, in order to allow for uniform instance repetitions.
|
|
942
|
+
|
|
937
943
|
The batch scheduler crucially assumes that in each batch the same
|
|
938
944
|
problems are given *in the same order* when calling `is_in_batch`.
|
|
939
945
|
|
|
@@ -953,10 +959,13 @@ class BatchScheduler:
|
|
|
953
959
|
``batch_to_execute in (0,1,2,3)`` to generate the full experimental
|
|
954
960
|
data.
|
|
955
961
|
|
|
956
|
-
Details:
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
962
|
+
Details: while making the number of functions not divisible by the number of
|
|
963
|
+
batches may sometimes achieve a more even time distribution over all
|
|
964
|
+
batches, in practice, it is advisable to keep each function in a single or a
|
|
965
|
+
few batches as it is enforced by the `BatchScheduler`. Hence, for the 24
|
|
966
|
+
functions of the `'bbob'` testbed, having 48 or 24 or 12 or 8 or 6 or 4
|
|
967
|
+
batches is advisable. Additionally, it can be useful to run the largest
|
|
968
|
+
dimension in a separate launch (with at most 24 batches in this case).
|
|
960
969
|
"""
|
|
961
970
|
def __init__(self, number_of_batches, batch_to_execute):
|
|
962
971
|
"""distribute over `number_of_batches` batches and execute
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|