def _check_onnx_export(net, group_outputs=False, shape_type=tuple, extra_params={}): net.initialize() data = nd.random.uniform(0, 1, (1, 1024)) output = _force_list(net(data)) # initialize weights net_sym = _optional_group(net(sym.Variable('data')), group_outputs) net_params = { name: param._reduce() for name, param in net.collect_params().items() } net_params.update(extra_params) with tempfile.TemporaryDirectory() as tmpdirname: onnx_file_path = os.path.join(tmpdirname, 'net.onnx') export_path = onnx_mxnet.export_model( sym=net_sym, params=net_params, input_shape=[shape_type(data.shape)], onnx_file_path=onnx_file_path) assert export_path == onnx_file_path # Try importing the model to symbol _assert_sym_equal(net_sym, onnx_mxnet.import_model(export_path)[0]) # Try importing the model to gluon imported_net = onnx_mxnet.import_to_gluon(export_path, ctx=None) _assert_sym_equal( net_sym, _optional_group(imported_net(sym.Variable('data')), group_outputs)) # Confirm network outputs are the same imported_net_output = _force_list(imported_net(data)) for out, imp_out in zip(output, imported_net_output): mx.test_utils.assert_almost_equal(out.asnumpy(), imp_out.asnumpy())
def _check_onnx_export(net, group_outputs=False, shape_type=tuple, extra_params={}): net.initialize() data = nd.random.uniform(0, 1, (1, 1024)) output = _force_list(net(data)) # initialize weights net_sym = _optional_group(net(sym.Variable('data')), group_outputs) net_params = {name:param._reduce() for name, param in net.collect_params().items()} net_params.update(extra_params) with tempfile.TemporaryDirectory() as tmpdirname: onnx_file_path = os.path.join(tmpdirname, 'net.onnx') export_path = onnx_mxnet.export_model( sym=net_sym, params=net_params, input_shape=[shape_type(data.shape)], onnx_file_path=onnx_file_path) assert export_path == onnx_file_path # Try importing the model to symbol _assert_sym_equal(net_sym, onnx_mxnet.import_model(export_path)[0]) # Try importing the model to gluon imported_net = onnx_mxnet.import_to_gluon(export_path, ctx=None) _assert_sym_equal(net_sym, _optional_group(imported_net(sym.Variable('data')), group_outputs)) # Confirm network outputs are the same imported_net_output = _force_list(imported_net(data)) for out, imp_out in zip(output, imported_net_output): mx.test_utils.assert_almost_equal(out.asnumpy(), imp_out.asnumpy())
def _run_model_on_fold( self, model: Any, task: 'OpenMLTask', X_train: Union[np.ndarray, scipy.sparse.spmatrix, pd.DataFrame], rep_no: int, fold_no: int, y_train: Optional[np.ndarray] = None, X_test: Optional[Union[np.ndarray, scipy.sparse.spmatrix, pd.DataFrame]] = None, ) -> Tuple[np.ndarray, np.ndarray, 'OrderedDict[str, float]', Optional[OpenMLRunTrace], Optional[Any]]: """Run a model on a repeat,fold,subsample triplet of the task and return prediction information. Furthermore, it will measure run time measures in case multi-core behaviour allows this. * exact user cpu time will be measured if the number of cores is set (recursive throughout the model) exactly to 1 * wall clock time will be measured if the number of cores is set (recursive throughout the model) to any given number (but not when it is set to -1) Returns the data that is necessary to construct the OpenML Run object. Is used by run_task_get_arff_content. Do not use this function unless you know what you are doing. Parameters ---------- model : Any The UNTRAINED model to run. The model instance will be copied and not altered. task : OpenMLTask The task to run the model on. X_train : array-like Training data for the given repetition and fold. rep_no : int The repeat of the experiment (0-based; in case of 1 time CV, always 0) fold_no : int The fold nr of the experiment (0-based; in case of holdout, always 0) y_train : Optional[np.ndarray] (default=None) Target attributes for supervised tasks. In case of classification, these are integer indices to the potential classes specified by dataset. X_test : Optional, array-like (default=None) Test attributes to test for generalization in supervised tasks. Returns ------- predictions : np.ndarray Model predictions. probabilities : Optional, np.ndarray Predicted probabilities (only applicable for supervised classification tasks). user_defined_measures : OrderedDict[str, float] User defined measures that were generated on this fold trace : Optional, OpenMLRunTrace Hyperparameter optimization trace (only applicable for supervised tasks with hyperparameter optimization). additional_information: Optional, Any Additional information provided by the extension to be converted into additional files. """ def _prediction_to_probabilities(y: np.ndarray, classes: List[Any]) -> np.ndarray: """Transforms predicted probabilities to match with OpenML class indices. Parameters ---------- y : np.ndarray Predicted probabilities (possibly omitting classes if they were not present in the training data). classes : list List of classes known_predicted by the model, ordered by their index. Returns ------- np.ndarray """ # y: list or numpy array of predictions # model_classes: keras classifier mapping from original array id to # prediction index id if not isinstance(classes, list): raise ValueError( 'please convert model classes to list prior to ' 'calling this fn') result = np.zeros((len(y), len(classes)), dtype=np.float32) for obs, prediction_idx in enumerate(y): result[obs][prediction_idx] = 1.0 return result if isinstance(task, OpenMLSupervisedTask): if y_train is None: raise TypeError('argument y_train must not be of type None') if X_test is None: raise TypeError('argument X_test must not be of type None') # Save model to file and import it as MXNet model onnx.save(model, ONNX_FILE_PATH) model_mx = onnx_mxnet.import_to_gluon(ONNX_FILE_PATH, ctx=context) # Remove the saved file if os.path.exists(ONNX_FILE_PATH): os.remove(ONNX_FILE_PATH) # Reinitialize weights and bias model_mx.initialize(init=mx.init.Uniform(), force_reinit=True) # Sanitize train and test data X_train[np.isnan(X_train)] = sanitize_value if X_test is not None: X_test[np.isnan(X_test)] = sanitize_value user_defined_measures = OrderedDict( ) # type: 'OrderedDict[str, float]' try: if isinstance(task, OpenMLSupervisedTask): # Obtain loss function from configuration loss_fn = criterion_gen(task) # Define trainer using optimizer from configuration trainer = gluon.Trainer(model_mx.collect_params(), optimizer) # Calculate the number of batches using batch size from configuration nr_of_batches = math.ceil(X_train.shape[0] / batch_size) for j in range(epoch_count): for i in range(nr_of_batches): # Take current batch of input data and labels input = nd.array(X_train[i * batch_size:(i + 1) * batch_size]) if y_train is not None: labels = nd.array(y_train[i * batch_size:(i + 1) * batch_size]) # Train the model with autograd.record(): output = model_mx(input) loss = loss_fn(output, labels) loss.backward() trainer.step(input.shape[0]) except AttributeError as e: # typically happens when training a regressor on classification task raise PyOpenMLError(str(e)) if isinstance(task, OpenMLClassificationTask): model_classes = mx.nd.argmax(nd.array(y_train), axis=-1) # In supervised learning this returns the predictions for Y if isinstance(task, OpenMLSupervisedTask): pred_y = model_mx(nd.array(X_test)) if isinstance(task, OpenMLClassificationTask): pred_y = mx.nd.argmax(pred_y, -1) pred_y = (pred_y.asnumpy()).astype(np.int64) if isinstance(task, OpenMLRegressionTask): pred_y = pred_y.asnumpy() pred_y = pred_y.reshape((-1)) else: raise ValueError(task) if isinstance(task, OpenMLClassificationTask): try: proba_y = model_mx(nd.array(X_test)).asnumpy() except AttributeError: if task.class_labels is not None: proba_y = _prediction_to_probabilities( pred_y, list(task.class_labels)) else: raise ValueError('The task has no class labels') if task.class_labels is not None: if proba_y.shape[1] != len(task.class_labels): # Remap the probabilities in case there was a class missing at training time # By default, the classification targets are mapped to be zero-based indices # to the actual classes. Therefore, the model_classes contain the correct # indices to the correct probability array. Example: # classes in the dataset: 0, 1, 2, 3, 4, 5 # classes in the training set: 0, 1, 2, 4, 5 # then we need to add a column full of zeros into the probabilities for class 3 # (because the rest of the library expects that the probabilities are ordered # the same way as the classes are ordered). proba_y_new = np.zeros( (proba_y.shape[0], len(task.class_labels))) for idx, model_class in enumerate(model_classes): proba_y_new[:, model_class] = proba_y[:, idx] proba_y = proba_y_new if proba_y.shape[1] != len(task.class_labels): message = "Estimator only predicted for {}/{} classes!".format( proba_y.shape[1], len(task.class_labels), ) warnings.warn(message) openml.config.logger.warn(message) elif isinstance(task, OpenMLRegressionTask): proba_y = None else: raise TypeError(type(task)) return pred_y, proba_y, user_defined_measures, None, None
def __init__(self, data_mean=None, data_std=None, mx_context=None, batch_size=None, **kwargs): super(Net_0, self).__init__(**kwargs) with self.name_scope(): self.save_specific_params_list = [] if data_mean: assert (data_std) self.input_normalization_data_ = ZScoreNormalization( data_mean=data_mean['data_'], data_std=data_std['data_']) else: self.input_normalization_data_ = NoNormalization() lastEpoch = 0 symbolFile = None weightFile = None onnxFile = None for file in os.listdir("pretrained"): if "network_name-" in file and ".json" in file: symbolFile = file if "network_name-" in file and ".param" in file: epochStr = file.replace(".params", "").replace("network_name-", "") epoch = int(epochStr) if epoch >= lastEpoch: lastEpoch = epoch weightFile = file if "network_name-" in file and ".onnx" in file: onnxFile = file inputNames = ["data"] zeroInputs = [nd.zeros((1, 128), ctx=mx_context[0])] with warnings.catch_warnings(): warnings.simplefilter("ignore") if symbolFile and weightFile: self.loadnetwork1_ = gluon.nn.SymbolBlock.imports( "pretrained/" + symbolFile, inputNames, "pretrained/" + weightFile, ctx=mx_context) elif onnxFile: from mxnet.contrib import onnx as onnx_mxnet self.loadnetwork1_ = onnx_mxnet.import_to_gluon( "pretrained/" + onnxFile, ctx=mx_context) else: raise FileNotFoundError( "Model files were not found in 'pretrained'.") self.loadnetwork1_out_shape = self.loadnetwork1_(*zeroInputs).shape if self.loadnetwork1_out_shape != (1, 1, 768): outputSize = 1 for x in ( 1, 768, ): outputSize = outputSize * x self.loadnetwork1_fc_ = gluon.nn.Dense(units=outputSize, use_bias=False, flatten=False) self.fc1_ = gluon.nn.Dense(units=33, use_bias=True, flatten=True) # fc1_, output shape: {[33,1,1]} pass