Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
raise RuntimeError(
"'{}': unexpected number of inputs {} != {}.".format(
node.op_type, len(node.input), len(inps)))
if len(node.output) < len(outs):
raise RuntimeError(
"'{}': unexpected number of inputs {} != {}.".format(
node.op_type, len(node.output), len(outs)))
# See file onnx-ml.proto.
if inps[0].data_type in (onnx_proto.TensorProto.FLOAT16, ):
# not supported
return (node.op_type, False,
"Unsupported type {}".format(inps[0].data_type))
expected_data_type = (onnx_proto.TensorProto.UINT8,
onnx_proto.TensorProto.INT32,
onnx_proto.TensorProto.INT64,
onnx_proto.TensorProto.FLOAT,
onnx_proto.TensorProto.DOUBLE,
onnx_proto.TensorProto.BOOL,
onnx_proto.TensorProto.STRING)
if inps[0].data_type not in expected_data_type:
if node.op_type in untested:
return (node.op_type, False,
"unexpected data_type {} not in {}".format(
inps[0].data_type, expected_data_type))
raise NotImplementedError(
"Unexpected data_type {}: {}\n---\n{}\n---".format(
inps[0].data_type, node.op_type, inps[0]))
# prepare the inputs
inp_arrays = [numpy_helper.to_array(inp) for inp in inps]
out_arrays = [numpy_helper.to_array(out) for out in outs]
input_name = operator.input_full_names
if type(operator.inputs[0].type) == Int64TensorType:
cast_input_name = scope.get_unique_variable_name('cast_input')
apply_cast(scope, operator.input_full_names, cast_input_name,
container, to=onnx_proto.TensorProto.FLOAT)
input_name = cast_input_name
svm_out = operator.output_full_names[1]
container.add_node(op_type, input_name, svm_out,
op_domain='ai.onnx.ml', **svm_attrs)
pred = scope.get_unique_variable_name('float_prediction')
container.add_node('Sign', svm_out, pred, op_version=9)
apply_cast(scope, pred, operator.output_full_names[0],
container, to=onnx_proto.TensorProto.INT64)
else:
raise ValueError("Unknown support vector machine model type found "
"'{0}'.".format(operator.type))
def convert_sklearn_array_feature_extractor(scope, operator, container):
"""
Extracts a subset of columns. This is used by *ColumnTransformer*.
"""
column_indices_name = scope.get_unique_variable_name('column_indices')
for i, ind in enumerate(operator.column_indices):
if not isinstance(ind, int):
raise RuntimeError(("Column {0}:'{1}' indices must be specified "
"as integers. This error may happen when "
"column names are used to define a "
"ColumnTransformer. Column name in input data "
"do not necessarily match input variables "
"defined for the ONNX model.").format(i, ind))
container.add_initializer(column_indices_name,
onnx_proto.TensorProto.INT64,
[len(operator.column_indices)],
operator.column_indices)
container.add_node(
'ArrayFeatureExtractor',
[operator.inputs[0].full_name, column_indices_name],
operator.outputs[0].full_name,
name=scope.get_unique_operator_name('ArrayFeatureExtractor'),
op_domain='ai.onnx.ml')
label_name = operator.outputs[0].full_name
if use_raw_scores:
container.add_node(classifier_type, operator.inputs[0].full_name,
[label_name, operator.outputs[1].full_name],
op_domain='ai.onnx.ml', **classifier_attrs)
elif (isinstance(op, (LinearSVC, RidgeClassifier, RidgeClassifierCV))
and op.classes_.shape[0] <= 2):
raw_scores_tensor_name = scope.get_unique_variable_name(
'raw_scores_tensor')
positive_class_index_name = scope.get_unique_variable_name(
'positive_class_index')
container.add_initializer(positive_class_index_name,
onnx_proto.TensorProto.INT64, [], [1])
if (hasattr(op, '_label_binarizer') and
op._label_binarizer.y_type_ == 'multilabel-indicator'):
y_pred_name = scope.get_unique_variable_name('y_pred')
binarised_label_name = scope.get_unique_variable_name(
'binarised_label')
container.add_node(classifier_type, operator.inputs[0].full_name,
[y_pred_name, raw_scores_tensor_name],
op_domain='ai.onnx.ml', **classifier_attrs)
container.add_node(
'Binarizer', raw_scores_tensor_name, binarised_label_name,
op_domain='ai.onnx.ml')
apply_cast(
scope, binarised_label_name, label_name,
container, to=onnx_proto.TensorProto.INT64)
apply_exp(scope, log_prob_name, operator.outputs[1].full_name, container)
container.add_node(
'ArrayFeatureExtractor', [classes_name, argmax_output_name],
array_feature_extractor_result_name, op_domain='ai.onnx.ml',
name=scope.get_unique_operator_name('ArrayFeatureExtractor'))
# Reshape op does not seem to handle INT64 tensor even though it is
# listed as one of the supported types in the doc, so Cast was
# required here.
if class_type == onnx_proto.TensorProto.INT32:
apply_cast(scope, array_feature_extractor_result_name,
cast2_result_name, container,
to=proto_type)
apply_reshape(scope, cast2_result_name, reshaped_result_name,
container, desired_shape=output_shape)
apply_cast(scope, reshaped_result_name, operator.outputs[0].full_name,
container, to=onnx_proto.TensorProto.INT64)
else: # string labels
apply_reshape(scope, array_feature_extractor_result_name,
operator.outputs[0].full_name, container,
desired_shape=output_shape)
probas = OnnxDiv(all_together, sum_prob, op_version=opv)
res_name = OnnxArrayFeatureExtractor(
cur_class, res, op_version=opv)
reshaped_labels = OnnxReshape(
res_name, np.array([-1, 1], dtype=np.int64), op_version=opv)
reshaped_probas = OnnxReshape(
probas, np.array([1, -1, len(cur_class)], dtype=np.int64),
op_version=opv)
out_labels.append(reshaped_labels)
out_probas.append(reshaped_probas)
concatenated_labels = OnnxConcat(
*out_labels, axis=1, op_version=opv)
final_proba = OnnxConcat(
*out_probas, axis=0, output_names=out[1:], op_version=opv)
final_label = OnnxCast(
concatenated_labels, to=onnx_proto.TensorProto.INT64,
output_names=out[:1], op_version=opv)
final_label.add_to(scope, container)
final_proba.add_to(scope, container)
else:
all_together, sum_prob, res = get_proba_and_label(
container, nb_classes, reshaped, wei, axis, opv)
probas = OnnxDiv(all_together, sum_prob, op_version=opv,
output_names=out[1:])
res_name = OnnxArrayFeatureExtractor(classes, res, op_version=opv)
out_labels = OnnxReshape(res_name, np.array([-1], dtype=np.int64),
output_names=out[:1], op_version=opv)
out_labels.add_to(scope, container)
probas.add_to(scope, container)
highest probability obtained for each class over all estimators.
*scikit-learn* enables both modes, transformer and predictor
for the voting classifier. *ONNX* does not make this
distinction and always creates two outputs, labels
and probabilities.
"""
if scope.get_options(operator.raw_operator, dict(nocl=False))['nocl']:
raise RuntimeError(
"Option 'nocl' is not implemented for operator '{}'.".format(
operator.raw_operator.__class__.__name__))
op = operator.raw_operator
n_classes = len(op.classes_)
classes_ind_name = scope.get_unique_variable_name('classes_ind')
container.add_initializer(classes_ind_name, onnx_proto.TensorProto.INT64,
(1, n_classes), list(range(n_classes)))
probs_names = []
one_name = None
for i, estimator in enumerate(op.estimators_):
if estimator is None:
continue
op_type = sklearn_operator_name_map[type(estimator)]
this_operator = scope.declare_local_operator(op_type)
this_operator.raw_operator = estimator
this_operator.inputs = operator.inputs
label_name = scope.declare_local_variable('label_%d' % i)
prob_name = scope.declare_local_variable('proba_%d' % i,
def _apply_gather_elements(scope, container, inputs, output, axis,
dim, zero_type, suffix):
if container.target_opset >= 11:
container.add_node(
'GatherElements', inputs, output, op_version=11, axis=axis,
name=scope.get_unique_operator_name('GatEls' + suffix))
else:
classes_ind_name = scope.get_unique_variable_name('classes_ind2')
container.add_initializer(
classes_ind_name, onnx_proto.TensorProto.INT64,
(1, dim), list(range(dim)))
shape_name = scope.get_unique_variable_name('shape')
container.add_node(
'Shape', inputs[0], shape_name,
name=scope.get_unique_operator_name('Shape'))
zero_name = scope.get_unique_variable_name('zero')
zero_val = (0 if zero_type == onnx_proto.TensorProto.INT64
else 0.)
container.add_node(
'ConstantOfShape', shape_name, zero_name,
name=scope.get_unique_operator_name('CoSA'),
value=make_tensor("value", zero_type,
(1, ), [zero_val]), op_version=9)
equal_name = scope.get_unique_variable_name('equal')
operator.outputs[1].full_name, container, broadcast=1)
class_prob_name = operator.outputs[1].full_name
container.add_node('ArgMax', class_prob_name,
argmax_output_name,
name=scope.get_unique_operator_name('ArgMax'), axis=1)
container.add_node(
'ArrayFeatureExtractor', [classes_name, argmax_output_name],
array_feature_extractor_result_name, op_domain='ai.onnx.ml',
name=scope.get_unique_operator_name('ArrayFeatureExtractor'))
if class_type == onnx_proto.TensorProto.INT32:
apply_reshape(scope, array_feature_extractor_result_name,
reshaped_result_name, container,
desired_shape=output_shape)
apply_cast(scope, reshaped_result_name, operator.outputs[0].full_name,
container, to=onnx_proto.TensorProto.INT64)
else:
apply_reshape(scope, array_feature_extractor_result_name,
operator.outputs[0].full_name, container,
desired_shape=output_shape)
name=scope.get_unique_operator_name('ArgMax'), axis=1)
container.add_node(
'ArrayFeatureExtractor', [classes_name, argmax_output_name],
array_feature_extractor_result_name, op_domain='ai.onnx.ml',
name=scope.get_unique_operator_name('ArrayFeatureExtractor'))
if class_type == onnx_proto.TensorProto.INT32:
cast_result_name = scope.get_unique_variable_name('cast_result')
reshaped_result_name = scope.get_unique_variable_name(
'reshaped_result')
apply_cast(scope, array_feature_extractor_result_name,
cast_result_name, container,
to=onnx_proto.TensorProto.INT64)
apply_reshape(scope, cast_result_name, reshaped_result_name,
container, desired_shape=output_shape)
apply_cast(scope, reshaped_result_name, operator.outputs[0].full_name,
container, to=onnx_proto.TensorProto.INT64)
else: # string labels
apply_reshape(scope, array_feature_extractor_result_name,
operator.outputs[0].full_name, container,
desired_shape=output_shape)