UNPKG

@tensorflow/tfjs-converter

Version:

Tensorflow model converter for javascript

1,586 lines (1,575 loc) 1.32 MB
/** * @license * Copyright 2024 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ (function (global, factory) { typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('@tensorflow/tfjs-core')) : typeof define === 'function' && define.amd ? define(['exports', '@tensorflow/tfjs-core'], factory) : (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.tf = global.tf || {}, global.tf)); })(this, (function (exports, tfc) { 'use strict'; function _interopNamespaceDefault(e) { var n = Object.create(null); if (e) { Object.keys(e).forEach(function (k) { if (k !== 'default') { var d = Object.getOwnPropertyDescriptor(e, k); Object.defineProperty(n, k, d.get ? d : { enumerable: true, get: function () { return e[k]; } }); } }); } n.default = e; return n; } function _mergeNamespaces(n, m) { m.forEach(function (e) { e && typeof e !== 'string' && !Array.isArray(e) && Object.keys(e).forEach(function (k) { if (k !== 'default' && !(k in n)) { var d = Object.getOwnPropertyDescriptor(e, k); Object.defineProperty(n, k, d.get ? d : { enumerable: true, get: function () { return e[k]; } }); } }); }); return n; } var tfc__namespace = /*#__PURE__*/_interopNamespaceDefault(tfc); /** * @license * Copyright 2021 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ const ENV$1 = tfc.env(); /** Whether to keep intermediate tensors. */ ENV$1.registerFlag('KEEP_INTERMEDIATE_TENSORS', () => false, debugValue => { if (debugValue) { console.warn('Keep intermediate tensors is ON. This will print the values of all ' + 'intermediate tensors during model inference. Not all models ' + 'support this mode. For details, check e2e/benchmarks/ ' + 'model_config.js. This significantly impacts performance.'); } }); /** * @license * Copyright 2019 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * * ============================================================================= */ /** DataType enum. */ var DataType; (function (DataType) { // These properties must be quoted since they are used by parseDtypeParam // in tfjs-converter/src/operations/operation_mapper.ts to look up dtypes // by string name. If they are not quoted, Closure will mangle their names. // Not a legal value for DataType. Used to indicate a DataType field // has not been set. DataType[DataType["DT_INVALID"] = 0] = "DT_INVALID"; // Data types that all computation devices are expected to be // capable to support. DataType[DataType["DT_FLOAT"] = 1] = "DT_FLOAT"; DataType[DataType["DT_DOUBLE"] = 2] = "DT_DOUBLE"; DataType[DataType["DT_INT32"] = 3] = "DT_INT32"; DataType[DataType["DT_UINT8"] = 4] = "DT_UINT8"; DataType[DataType["DT_INT16"] = 5] = "DT_INT16"; DataType[DataType["DT_INT8"] = 6] = "DT_INT8"; DataType[DataType["DT_STRING"] = 7] = "DT_STRING"; DataType[DataType["DT_COMPLEX64"] = 8] = "DT_COMPLEX64"; DataType[DataType["DT_INT64"] = 9] = "DT_INT64"; DataType[DataType["DT_BOOL"] = 10] = "DT_BOOL"; DataType[DataType["DT_QINT8"] = 11] = "DT_QINT8"; DataType[DataType["DT_QUINT8"] = 12] = "DT_QUINT8"; DataType[DataType["DT_QINT32"] = 13] = "DT_QINT32"; DataType[DataType["DT_BFLOAT16"] = 14] = "DT_BFLOAT16"; DataType[DataType["DT_QINT16"] = 15] = "DT_QINT16"; DataType[DataType["DT_QUINT16"] = 16] = "DT_QUINT16"; DataType[DataType["DT_UINT16"] = 17] = "DT_UINT16"; DataType[DataType["DT_COMPLEX128"] = 18] = "DT_COMPLEX128"; DataType[DataType["DT_HALF"] = 19] = "DT_HALF"; DataType[DataType["DT_RESOURCE"] = 20] = "DT_RESOURCE"; DataType[DataType["DT_VARIANT"] = 21] = "DT_VARIANT"; DataType[DataType["DT_UINT32"] = 22] = "DT_UINT32"; DataType[DataType["DT_UINT64"] = 23] = "DT_UINT64"; // Do not use! These are only for parameters. Every enum above // should have a corresponding value below (verified by types_test). DataType[DataType["DT_FLOAT_REF"] = 101] = "DT_FLOAT_REF"; DataType[DataType["DT_DOUBLE_REF"] = 102] = "DT_DOUBLE_REF"; DataType[DataType["DT_INT32_REF"] = 103] = "DT_INT32_REF"; DataType[DataType["DT_UINT8_REF"] = 104] = "DT_UINT8_REF"; DataType[DataType["DT_INT16_REF"] = 105] = "DT_INT16_REF"; DataType[DataType["DT_INT8_REF"] = 106] = "DT_INT8_REF"; DataType[DataType["DT_STRING_REF"] = 107] = "DT_STRING_REF"; DataType[DataType["DT_COMPLEX64_REF"] = 108] = "DT_COMPLEX64_REF"; DataType[DataType["DT_INT64_REF"] = 109] = "DT_INT64_REF"; DataType[DataType["DT_BOOL_REF"] = 110] = "DT_BOOL_REF"; DataType[DataType["DT_QINT8_REF"] = 111] = "DT_QINT8_REF"; DataType[DataType["DT_QUINT8_REF"] = 112] = "DT_QUINT8_REF"; DataType[DataType["DT_QINT32_REF"] = 113] = "DT_QINT32_REF"; DataType[DataType["DT_BFLOAT16_REF"] = 114] = "DT_BFLOAT16_REF"; DataType[DataType["DT_QINT16_REF"] = 115] = "DT_QINT16_REF"; DataType[DataType["DT_QUINT16_REF"] = 116] = "DT_QUINT16_REF"; DataType[DataType["DT_UINT16_REF"] = 117] = "DT_UINT16_REF"; DataType[DataType["DT_COMPLEX128_REF"] = 118] = "DT_COMPLEX128_REF"; DataType[DataType["DT_HALF_REF"] = 119] = "DT_HALF_REF"; DataType[DataType["DT_RESOURCE_REF"] = 120] = "DT_RESOURCE_REF"; DataType[DataType["DT_VARIANT_REF"] = 121] = "DT_VARIANT_REF"; DataType[DataType["DT_UINT32_REF"] = 122] = "DT_UINT32_REF"; DataType[DataType["DT_UINT64_REF"] = 123] = "DT_UINT64_REF"; })(DataType || (DataType = {})); var SaverDef; (function (SaverDef) { (function (CheckpointFormatVersion) { CheckpointFormatVersion[CheckpointFormatVersion["LEGACY"] = 0] = "LEGACY"; CheckpointFormatVersion[CheckpointFormatVersion["V1"] = 1] = "V1"; CheckpointFormatVersion[CheckpointFormatVersion["V2"] = 2] = "V2"; })(SaverDef.CheckpointFormatVersion || (SaverDef.CheckpointFormatVersion = {})); })(SaverDef || (SaverDef = {})); /** * @license * Copyright 2019 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ const CUSTOM_OPS = {}; /** * Register an Op for graph model executor. This allows you to register * TensorFlow custom op or override existing op. * * Here is an example of registering a new MatMul Op. * ```js * const customMatmul = (node) => * tf.matMul( * node.inputs[0], node.inputs[1], * node.attrs['transpose_a'], node.attrs['transpose_b']); * * tf.registerOp('MatMul', customMatmul); * ``` * The inputs and attrs of the node object are based on the TensorFlow op * registry. * * @param name The Tensorflow Op name. * @param opFunc An op function which is called with the current graph node * during execution and needs to return a tensor or a list of tensors. The node * has the following attributes: * - attr: A map from attribute name to its value * - inputs: A list of input tensors * * @doc {heading: 'Models', subheading: 'Op Registry'} */ function registerOp(name, opFunc) { const opMapper = { tfOpName: name, category: 'custom', inputs: [], attrs: [], customExecutor: opFunc }; CUSTOM_OPS[name] = opMapper; } /** * Retrieve the OpMapper object for the registered op. * * @param name The Tensorflow Op name. * * @doc {heading: 'Models', subheading: 'Op Registry'} */ function getRegisteredOp(name) { return CUSTOM_OPS[name]; } /** * Deregister the Op for graph model executor. * * @param name The Tensorflow Op name. * * @doc {heading: 'Models', subheading: 'Op Registry'} */ function deregisterOp(name) { delete CUSTOM_OPS[name]; } /** * @license * Copyright 2018 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ function getParamValue(paramName, node, tensorMap, context, resourceManager) { const inputParam = node.inputParams[paramName]; if (inputParam && inputParam.inputIndexStart !== undefined) { const start = inputParam.inputIndexStart; const end = inputParam.inputIndexEnd === 0 ? undefined : (inputParam.inputIndexEnd === undefined ? start + 1 : inputParam.inputIndexEnd); const shiftedStart = start < 0 ? node.inputNames.length + start : start; if (inputParam.type === 'tensor') { return getTensor(node.inputNames[shiftedStart], tensorMap, context, resourceManager); } if (inputParam.type === 'tensors') { // TODO(mattSoulanille): This filters out NoOp nodes during execution, but // these should really never be in the execution graph in the first place. // They're necessary for ordering the graph, but should not be visible // during execution. Perhaps have different sets of children, one for // control dependencies and another for real dependencies. const inputs = node.inputs.slice(start, end); const inputNames = node.inputNames.slice(start, end) .filter((_name, index) => { var _a; return ((_a = inputs[index]) === null || _a === void 0 ? void 0 : _a.op) !== 'NoOp'; }); return inputNames.map(name => getTensor(name, tensorMap, context, resourceManager)); } const tensor = getTensor(node.inputNames[shiftedStart], tensorMap, context, resourceManager); const data = tensor.dataSync(); return inputParam.type === 'number' ? data[0] : tfc.util.toNestedArray(tensor.shape, data); } const attrParam = node.attrParams[paramName]; return attrParam && attrParam.value; } /** * Retrieve the tensor from tensorsMap based on input name. * @param name Node input name * @param tensorsMap Tensors map keyed by the node * @param context contains tensors and information for running the current node. * @param resourceManager Optional. Contains global resources of the model. */ function getTensor(name, tensorsMap, context, resourceManager) { const [nodeName, index] = parseNodeName(name, context); if (resourceManager != null) { const tensor = resourceManager.getHashTableHandleByName(nodeName); if (tensor != null) { return tensor; } } const contextId = context.currentContextIds.find(contextId => { return !!tensorsMap[getNodeNameWithContextId(nodeName, contextId)]; }); return contextId !== undefined ? tensorsMap[getNodeNameWithContextId(nodeName, contextId)][index] : undefined; } /** * Retrieve the tensors based on input name for current context. * @param name Node input name * @param tensorsMap Tensors map keyed by the node */ function getTensorsForCurrentContext(name, tensorsMap, context) { return tensorsMap[getNodeNameWithContextId(name, context.currentContextId)]; } /** * Returns the node name, outputName and index from the Node input name. * @param inputName The input name of the node, in format of * node_name:output_index, i.e. MatMul:0, if the output_index is not set, it is * default to 0. * If the input name contains output name i.e. StringSplit:indices:0, it will * return ['StringSplit', 0, 'indices']. */ function getNodeNameAndIndex(inputName, context) { const [nodeName, index, outputName] = parseNodeName(inputName, context); return [ getNodeNameWithContextId(nodeName, context && context.currentContextId), index, outputName ]; } function getNodeNameWithContextId(name, contextId) { return !!contextId ? `${name}-${contextId}` : name; } function parseNodeName(name, context) { if (name === '') { return ['', 0, undefined]; } const isCacheEnabled = context != null && context.parseNodeNameCache != null; if (isCacheEnabled) { const cachedResult = context.parseNodeNameCache.get(name); if (cachedResult != null) { return cachedResult; } } const parts = name.split(':'); let result; if (parts.length === 1) { result = [name, 0, undefined]; } else { const nodeName = parts[0]; const outputName = parts.length === 3 ? parts[1] : undefined; const index = Number(parts[parts.length - 1]); result = [nodeName, index, outputName]; } if (isCacheEnabled) { context.parseNodeNameCache.set(name, result); } return result; } function getPadding(node, tensorMap, context) { let pad = getParamValue('pad', node, tensorMap, context); if (pad === 'explicit') { // This is 1d array, we need to convert it to 2d array pad = getParamValue('explicitPaddings', node, tensorMap, context); const explicitPadding = [[0, 0], [0, 0], [0, 0], [0, 0]]; for (let i = 0; i < 4; i++) { explicitPadding[i][0] = pad[i * 2]; explicitPadding[i][1] = pad[i * 2 + 1]; } return explicitPadding; } return pad; } /** * Reuse the tensor if it is marked as keep, otherwise clone the tensor to * avoid disposal. This is important for TensorArray and TensorList ops, since * internally they use a tensor as the id for TensorArray and TensorList, and * to simplify lookup, they also use Tensor.id as the key to the internal map. * These id tensors have been marked as kept in the backend, we need avoid clone * them in order to create new Tensor.id. * @param tensor */ function cloneTensor(tensor) { return tensor.kept ? tensor : tfc.clone(tensor); } /** * @license * Copyright 2023 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ const json$i = [ { 'tfOpName': 'Add', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'AddV2', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'AddN', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'end': 0, 'name': 'tensors', 'type': 'tensors' } ] }, { 'tfOpName': 'BiasAdd', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true }, { 'tfName': 'data_format', 'name': 'dataFormat', 'type': 'string', 'notSupported': true } ] }, { 'tfOpName': 'Sub', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'RealDiv', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Div', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'DivNoNan', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'FloorDiv', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Mul', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Maximum', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Minimum', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Pow', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'SquaredDifference', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Mod', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'FloorMod', 'category': 'arithmetic', 'inputs': [ { 'start': 0, 'name': 'a', 'type': 'tensor' }, { 'start': 1, 'name': 'b', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] } ]; var arithmetic = { __proto__: null, json: json$i }; /** * @license * Copyright 2023 Google LLC. All Rights Reserved. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ============================================================================= */ const json$h = [ { 'tfOpName': 'Abs', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Acos', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Asin', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Atan', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Atan2', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' }, { 'start': 1, 'name': 'y', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Ceil', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'ClipByValue', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' }, { 'start': 1, 'name': 'clipValueMin', 'type': 'number' }, { 'start': 2, 'name': 'clipValueMax', 'type': 'number' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Complex', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'real', 'type': 'tensor' }, { 'start': 1, 'name': 'imag', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'ComplexAbs', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Cos', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Cosh', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Elu', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Exp', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Floor', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Log', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Imag', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true }, { 'tfName': 'Tout', 'name': 'outputType', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Neg', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Real', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true }, { 'tfName': 'Tout', 'name': 'outputType', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Prelu', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' }, { 'start': 1, 'name': 'alpha', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Relu', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Relu6', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Selu', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Sigmoid', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Sin', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Sinh', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Sqrt', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Rsqrt', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Square', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Tan', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Tanh', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Sign', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Round', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Expm1', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Log1p', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Reciprocal', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Softplus', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Asinh', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Acosh', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype', 'notSupported': true } ] }, { 'tfOpName': 'Atanh', 'category': 'basic_math', 'inputs': [ { 'start': 0, 'name': 'x', 'type': 'tensor' } ], 'attrs': [ { 'tfName': 'T', 'name': 'dtype', 'type': 'dtype',