コード例 #1
0
ファイル: loader.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def __import_graph(cls, graph_path, session, out_nodes_names):
        """
        :type graph_path: str
        :type session: tensorflow.Session
        :type out_nodes_names: list[str]
        :rtype: tf.GraphDef
        """
        if not os.path.exists(graph_path):
            raise ConverterError(
                code_to_message.get_error_message(
                    'ERROR_TF_GRAPH_FILE_DOES_NOT_EXIST')(graph_path))

        graph_path = os.path.abspath(graph_path)
        if graph_path.endswith('.meta'):
            checkpoint = graph_path.split('.meta')[0]
            graph_def = cls.__import_from_meta_graph(graph_path, checkpoint,
                                                     out_nodes_names)
        else:
            graph_def = cls.__import_from_frozen_graph(graph_path)

        if len(graph_def.node) == 0:
            raise ConverterError(
                code_to_message.get_error_message(
                    'ERROR_TF_NODES_NOT_FOUND_IN_GRAPH'))

        with session.graph.as_default():
            tf.import_graph_def(graph_def, name="")
        return graph_def
コード例 #2
0
    def axes_to_spatial_first_order(self, node, graph):
        input_name = node.input_names[0]
        input_buf = graph.get_buffer(input_name)
        # force convergence if necessary
        # use the 'backwards' permute orders because they are self-inverses.
        if input_buf.axis_format == AxisTracker.AxisFormat.NSC:
            AxisTracker.inject_implicit_permute(
                graph, input_name, AxisTracker.AxisFormat.NCS,
                AxisTracker.AxisFormat.NSC_TO_NCS, [node.op.name])
        elif input_buf.axis_format == AxisTracker.AxisFormat.BTF:
            AxisTracker.inject_implicit_permute(
                graph, input_name, AxisTracker.AxisFormat.TBF,
                AxisTracker.AxisFormat.TBF_TO_BTF, [node.op.name])
        elif input_buf.axis_format == AxisTracker.AxisFormat.NONTRIVIAL:
            pass
        elif input_buf.axis_format == AxisTracker.AxisFormat.FEATURE:
            pass
        else:
            raise ValueError(
                code_to_message.get_error_message(
                    "ERROR_RESHAPE_UNEXPECTED_INPUT_ORDER")(
                        input_buf.axis_format))

        output_buf = graph.get_output_buffers(node)[0]
        if output_buf.rank() > 4:
            log_assert(
                self.product(output_buf.shape[:-4]) == 1,
                code_to_message.get_error_message(
                    "ERROR_RESHAPE_BATCH_UNSUPPORTED"))
            output_buf.shape = output_buf.shape[-4:]
        output_buf.axis_format = AxisTracker.AxisFormat.NONTRIVIAL
コード例 #3
0
ファイル: loader.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def __import_from_meta_graph(cls, meta_graph_path, graph_path,
                                 out_nodes_names):
        """
        :type meta_graph_path: str
        :type graph_path: str
        :type out_nodes_names: list[str]
        :rtype: tensorflow.GraphDef
        """
        session = tf.Session(graph=tf.Graph())
        with session.graph.as_default():
            try:
                saver = tf.train.import_meta_graph(meta_graph_path)
            except AssertionError as e:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_CANNOT_IMPORT_GRAPH_FROM_META')(e.message))

            if saver is None:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_GRAPH_META_EMPTY'))
            saver.restore(session, graph_path)

        graph_def = session.graph.as_graph_def(add_shapes=True)
        return cls.__freeze_graph(session, graph_def, out_nodes_names)
コード例 #4
0
ファイル: common.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def get_input_name(cls, converter_context, descriptor, input_descriptors):
        """
        :type converter_context: converters.tensorflow.converter.ConverterContext
        :type input_descriptors: [LayerDescriptor]
        :type descriptor: LayerDescriptor
        :rtype: str
        """
        if len(input_descriptors) > 1:
            raise ConverterError(
                code_to_message.get_error_message(
                    'ERROR_TF_LAYER_INPUT_COUNT_ERROR')(
                        input_descriptors[0].layer_type, 1,
                        len(input_descriptors)))

        input_names = cls.get_input_names(converter_context, descriptor,
                                          input_descriptors)
        if len(input_names) == 0:
            raise ConverterError(
                code_to_message.get_error_message(
                    'ERROR_TF_LAYER_NO_INPUT_FOUND')(descriptor.layer_type,
                                                     descriptor.layer_name))

        if len(input_names) > 1:
            raise ConverterError(
                code_to_message.get_error_message(
                    'ERROR_TF_LAYER_INPUT_COUNT_ERROR')(
                        input_descriptors[0].layer_type, 1,
                        len(input_descriptors)))

        return input_names[0]
コード例 #5
0
    def _convert_input_layers(self):
        """
        :rtype: None
        """
        for model_input in self._context.inputs:
            input_operation = self._context.graph.get_operation_by_name(
                model_input.name)
            shape = self._graph_helper.get_op_output_shape(input_operation)
            if None in shape:
                message = code_to_message.get_error_message(
                    'ERROR_TF_UNABLE_TO_RESOLVE_GRAPH_INPUT_DIMS')
                raise ConverterError(message(model_input.name))
            if model_input.shape != shape:
                message = code_to_message.get_error_message(
                    'ERROR_TF_UNEXPECTED_INPUT_SHAPE')
                raise ConverterError(message(model_input.shape, shape))

            self._logger.info(
                code_to_message.get_progress_message(
                    'INFO_TF_BUILDING_INPUT_LAYER')(input_operation.name,
                                                    shape))

            layer_name = str(input_operation.outputs[0].name)
            descriptor = InputLayerDescriptor(layer_name, [input_operation])
            self._input_descriptors.append(descriptor)
            self._ops.remove(input_operation)
            self._context.model.add_data_layer(descriptor.output_names[0],
                                               shape, 'rgb', 'rgb',
                                               model_input.type)
コード例 #6
0
    def resolve_layer(self, graph_matcher, graph_helper):
        matches = graph_matcher.match_sequence(self.sequence)
        if len(matches) == 0:
            return []
        descriptors = []
        for match in matches:
            variance_op = match['variance']
            epsilon_op = match['epsilon']
            if variance_op.type not in ['Identity', 'Const']:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_BATCHNORM_RESOLVE_VARIANCE'))
            variance = graph_helper.evaluate_tensor_output(
                variance_op.outputs[0])

            if epsilon_op.type not in ['Identity', 'Const']:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_BATCHNORM_RESOLVE_EPSILON'))
            epsilon = graph_helper.evaluate_tensor_output(
                epsilon_op.outputs[0])

            scale_op = match['scale']
            if scale_op.type not in ['Identity', 'Const', 'Fill']:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_BATCHNORM_RESOLVE_SCALE'))
            scale = graph_helper.evaluate_tensor_output(scale_op.outputs[0])

            mean_op = match['mean']
            if mean_op.type not in ['Identity', 'Const']:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_BATCHNORM_RESOLVE_MEAN'))
            mean = graph_helper.evaluate_tensor_output(mean_op.outputs[0])

            beta_op = match['beta']
            if beta_op.type not in ['Identity', 'Const']:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_BATCHNORM_RESOLVE_BETA'))
            beta = graph_helper.evaluate_tensor_output(beta_op.outputs[0])

            output_op_nodes_names = [
                str(match[node.identifier].outputs[0].name)
                for node in self.sequence.output_nodes
            ]
            descriptors.append(
                BatchNormLayerResolver.Descriptor(
                    str(match['d'].name),
                    match.consumed_nodes,
                    bn_mul_op=match['d'],
                    mean=mean,
                    variance=variance,
                    epsilon=epsilon,
                    scale=scale,
                    beta=beta,
                    output_names=output_op_nodes_names))
        return descriptors
コード例 #7
0
    def resolve_layer(self, graph_matcher, graph_helper):
        descriptors = []
        for match in graph_matcher.match_sequence(self.sequence):
            input_op = match['input']
            reshape_out_op = match['reshape_out']
            reshape_in_op = match['reshape_in']
            transpose_op = match['transpose']

            input_shape = graph_helper.get_op_output_shape(input_op)
            reshape_in_shape = graph_helper.get_op_output_shape(reshape_in_op)
            transpose_shape = graph_helper.get_op_output_shape(transpose_op)
            reshape_out_shape = graph_helper.get_op_output_shape(
                reshape_out_op)

            if len(reshape_in_shape) < 2:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_CHANNEL_SHUFFLE_RESHAPE'))

            num_channels = input_shape[-1]
            num_groups = reshape_in_shape[-2]
            num_channels_prime = num_channels / num_groups

            if num_channels % num_groups != 0:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_CHANNEL_SHUFFLE'))

            is_channel_shuffle = True
            # first reshape must divide the channel dimension to [num_groups, num_channels_prime]
            is_channel_shuffle &= reshape_in_shape == input_shape[:-1] + [
                num_groups, num_channels_prime
            ]
            # transpose must permute the last two dimensions only
            is_channel_shuffle &= transpose_shape == input_shape[:-1] + [
                num_channels_prime, num_groups
            ]
            # output shape must be equal to the input shape
            is_channel_shuffle &= reshape_out_shape == input_shape

            if not is_channel_shuffle:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_CHANNEL_SHUFFLE_OUTPUT'))

            consumed_nodes = match.consumed_nodes
            descriptors.append(
                ChannelShuffleLayerResolver.Descriptor(
                    str(reshape_out_op.name),
                    consumed_nodes,
                    num_groups,
                    output_names=[str(reshape_out_op.outputs[0].name)]))

        return descriptors
コード例 #8
0
    def resolve_layer(self, graph_matcher, graph_helper):
        matches = graph_matcher.match_sequence(self.sequence)
        if len(matches) == 0:
            return []
        descriptors = []
        for match in matches:
            conv_trans_op = match['root']
            _, weights_tensor, input_tensor = GraphHelper.get_op_input_tensors(
                conv_trans_op, ('?', '?', '?'))
            if weights_tensor.op.type not in ['Identity', 'Const']:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_DECONV_CANT_FIND_WEIGHTS_NODE'))
            strides = conv_trans_op.get_attr('strides')
            padding = conv_trans_op.get_attr('padding')
            weights = graph_helper.evaluate_tensor_output(weights_tensor)
            consumed_nodes = match.consumed_nodes
            output_op_nodes_names = [
                str(match[node.identifier].outputs[0].name)
                for node in self.sequence.output_nodes
            ]
            bias_op = None
            try:
                output_ops = graph_helper.get_op_outputs(conv_trans_op)
                bias_op = GraphHelper.filter_single_op_by_type(
                    output_ops, 'BiasAdd')

                _, biases = GraphHelper.get_op_input_tensors(
                    bias_op, ('?', '?'))
                if biases.op.type not in ['Const', 'Identity']:
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_DECONV_CANT_FIND_BIAS_NODE'))
                biases = graph_helper.evaluate_tensor_output(biases)
                consumed_nodes.append(bias_op)
                output_op_nodes_names = [str(bias_op.outputs[0].name)]
            except OperationNotFoundError:
                biases = np.zeros(np.shape(weights)[-2], dtype=np.float32)

            descriptors.append(
                DeConvolutionOptimizedLayerResolver.Descriptor(
                    str(conv_trans_op.name),
                    consumed_nodes,
                    conv_trans_op,
                    bias_op,
                    weights,
                    strides,
                    padding,
                    biases,
                    input_tensor,
                    output_names=output_op_nodes_names))
        return descriptors
コード例 #9
0
    def resolve_layer(self, graph_matcher, graph_helper):
        descriptors = []
        for sequence in self.sequences:
            for match in graph_matcher.match_sequence(sequence):
                pad_op = None
                mode_values = modeltools.PADDING_CONSTANT
                if 'root' in match:
                    pad_op = match['root']
                if 'mirror_pad' in match:
                    pad_op = match['mirror_pad']
                    mode = pad_op.get_attr(self.TF_ATTRIBUTE_MODE)
                    if mode.decode() == "REFLECT":
                        mode_values = modeltools.PADDING_REFLECT

                input_op = match['input']
                paddings_op = match['paddings']

                paddings_tensor = graph_helper.evaluate_tensor_output(
                    paddings_op.outputs[0])
                paddings_shape = graph_helper.get_op_output_shape(paddings_op)

                input_rank = len(graph_helper.get_op_output_shape(input_op))
                if [input_rank, 2] != paddings_shape:
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_PAD_INVALUD_PADDINGS')(str(
                                [input_rank, 2]), str(paddings_shape)))

                if 'const_values' in match:
                    const_values_op = match['const_values']
                    const_values = graph_helper.evaluate_tensor_output(
                        const_values_op.outputs[0])
                else:
                    const_values = 0.0

                if not np.isscalar(const_values):
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_PAD_CONSTANT_NOT_SCALAR'))

                consumed_nodes = match.consumed_nodes
                pad_descriptor = PadLayerResolver.Descriptor(
                    str(pad_op.name),
                    consumed_nodes,
                    paddings_tensor,
                    mode_values,
                    const_values,
                    output_names=[str(pad_op.outputs[0].name)])
                descriptors.extend([pad_descriptor])

        return descriptors
コード例 #10
0
    def resolve_layer(self, graph_matcher, graph_helper):
        descriptors = []
        for sequence in self.sequences:
            matches = graph_matcher.match_sequence(sequence)
            for match in matches:
                matmul_op = match['matmul_op']
                weights_op = match['weights']
                biases_op = None
                bias_add_op = None
                if weights_op.type not in [
                        'Identity', 'Const', 'FakeQuantWithMinMaxVars'
                ]:
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_MATMUL_RESOLVE_WEIGHTS')(matmul_op.name))
                weights = graph_helper.evaluate_tensor_output(
                    weights_op.outputs[0])
                try:
                    bias_add_op = match['bias_op']
                    biases_op = match['biases']
                except KeyError:
                    pass
                if biases_op is not None and bias_add_op is not None:
                    if biases_op.type not in ['Identity', 'Const']:
                        # do we still need this check ?
                        raise ConverterError(
                            code_to_message.get_error_message(
                                'ERROR_TF_MATMUL_RESOLVE_BIAS')(
                                    bias_add_op.name))
                    biases = graph_helper.evaluate_tensor_output(
                        biases_op.outputs[0])
                else:
                    biases = np.zeros(weights.shape[-1], dtype=np.float32)

                consumed_nodes = match.consumed_nodes
                output_op_nodes_names = [
                    str(match[node.identifier].outputs[0].name)
                    for node in sequence.output_nodes
                ]
                descriptors.append(
                    FullyConnectedLayerResolver.Descriptor(
                        str(matmul_op.name),
                        consumed_nodes,
                        matmul_op,
                        bias_add_op,
                        weights,
                        biases,
                        output_names=output_op_nodes_names))
        return descriptors
コード例 #11
0
    def resolve_layer(self, graph_matcher, graph_helper):
        potential_descriptors = []
        for sequence in self.sequences:
            matches = graph_matcher.match_sequence(sequence)
            for match in matches:
                extract_glimpse = match['extract_glimpse']

                size = match['size']
                size_value = graph_helper.evaluate_tensor_output(
                    size.outputs[0])
                if size_value.size != 2:
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_RESOLVE_EXTRACT_GLIMPSE_SIZE'))

                output_op_nodes_names = [str(extract_glimpse.outputs[0].name)]
                consumed_nodes = match.consumed_nodes

                centered = bool(extract_glimpse.get_attr('centered'))
                normalized = bool(extract_glimpse.get_attr('normalized'))
                uniform_noise = bool(extract_glimpse.get_attr('uniform_noise'))

                potential_descriptors.append(
                    ExtractGlimpseLayerResolver.Descriptor(
                        str(extract_glimpse.name),
                        consumed_nodes,
                        size_value[1],
                        size_value[0],
                        centered,
                        normalized,
                        uniform_noise,
                        output_names=output_op_nodes_names))
        return potential_descriptors
コード例 #12
0
    def resolve_layer(self, graph_matcher, graph_helper):
        potential_descriptors = []
        matches = graph_matcher.match_sequence(self.sequence)
        for match in matches:
            image_proj_transform = match['root']

            output_op_nodes_names = [str(image_proj_transform.outputs[0].name)]
            consumed_nodes = match.consumed_nodes

            interpolation = str(
                image_proj_transform.get_attr('interpolation').decode('utf-8'))
            if interpolation == "BILINEAR":
                interpolation_mode = 0
            elif interpolation == "NEAREST":
                interpolation_mode = 1
            else:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_RESOLVE_IMAGE_TRANSFORM_INTERPOLATION'))

            potential_descriptors.append(
                ImageProjectiveTransformLayerResolver.Descriptor(
                    str(image_proj_transform.name),
                    consumed_nodes,
                    interpolation_mode,
                    output_names=output_op_nodes_names))
        return potential_descriptors
コード例 #13
0
ファイル: ssd.py プロジェクト: Weizhuo-Zhang/ML_coursera
 def build_layer(self, converter_context, descriptor, input_descriptors,
                 output_descriptors):
     """
     :type input_descriptors: [converters.tensorflow.common.LayerDescriptor]
     :type output_descriptors: [converters.tensorflow.common.LayerDescriptor]
     :type converter_context: converters.tensorflow.converter.ConverterContext
     :type descriptor: ConcatLayerResolver.Descriptor
     :rtype: int
     """
     output_name = descriptor.output_names[0]
     anchor_input = [
         d for d in input_descriptors
         if isinstance(d, ConstantLayerResolver.Descriptor)
     ]
     boxes_input = [
         d for d in input_descriptors
         if not isinstance(d, ConstantLayerResolver.Descriptor)
     ]
     if len(anchor_input) != 1:
         raise ConverterError(
             get_error_message('ERROR_TF_SSD_ANCHOR_INPUT_MISSING'))
     anchors_layer_name = anchor_input[0].output_names[0]
     boxes_layer_name = boxes_input[0].output_names[0]
     return converter_context.model.add_box_decoder_layer(
         output_name, [boxes_layer_name, anchors_layer_name], [output_name],
         scale_y=descriptor.scale_y,
         scale_x=descriptor.scale_y,
         scale_h=descriptor.scale_h,
         scale_w=descriptor.scale_w)
コード例 #14
0
 def _get_input_layer_output_op_for(self, operation):
     """
     :type operation: tensorflow.Operation
     :rtype: tensorflow.Operation
     """
     input_tensors = self._get_input_layers_output_tensors_for(operation)
     ops = uniques([t.op for t in input_tensors])
     if len(ops) == 0:
         raise ConverterError(
             code_to_message.get_error_message(
                 'ERROR_TF_INPUT_OPERATION_NOT_FOUND')(operation.name))
     if len(ops) != 1:
         raise ConverterError(
             code_to_message.get_error_message(
                 'ERROR_TF_EXPECTED_SINGLE_OUTPUT_FROM_PREVIOUS_LAYER'))
     return ops[0]
コード例 #15
0
ファイル: permute.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def resolve_layer(self, graph_matcher, graph_helper):
        descriptors = []
        for sequence in self.sequences:
            for match in graph_matcher.match_sequence(sequence):
                transpose_op = match['root']
                input_op = match['input']
                order_op = match['order']

                order_tensor = graph_helper.evaluate_tensor_output(
                    order_op.outputs[0])

                input_shape = graph_helper.get_op_output_shape(input_op)
                order_shape = graph_helper.get_op_output_shape(order_op)

                input_rank = len(input_shape)
                order_rank = len(order_shape)
                try:
                    assert order_rank == 1
                    for d in range(input_rank):
                        assert d in order_tensor
                except AssertionError:
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_PERMUTE_INVALID_ORDER_TENSOR')(
                                str(order_tensor)))

                consumed_nodes = match.consumed_nodes
                permute_descriptor = PermuteLayerResolver.Descriptor(
                    str(transpose_op.name),
                    consumed_nodes,
                    order_tensor,
                    output_names=[str(transpose_op.outputs[0].name)])
                descriptors.extend([permute_descriptor])

        return descriptors
コード例 #16
0
 def resolve_layer(self, graph_matcher, graph_helper):
     matches = graph_matcher.match_sequence(self.sequence)
     potential_descriptors = []
     for match in matches:
         bn_op = match['root']
         parameter_tensors = self._get_parameter_tensors(
             graph_helper, bn_op)
         if len(parameter_tensors) < 4:
             raise ConverterError(
                 code_to_message.get_error_message(
                     'ERROR_TF_BATCHNORM_GLOBALNORMALIZATION_INPUT'))
         epsilon = bn_op.get_attr('epsilon')
         scale = parameter_tensors[0]
         beta = parameter_tensors[1]
         mean = parameter_tensors[2]
         variance = parameter_tensors[3]
         consumed_nodes = match.consumed_nodes
         potential_descriptors.append(
             FusedBatchNormNormLayerResolver.Descriptor(str(bn_op.name),
                                                        consumed_nodes,
                                                        bn_mul_op=bn_op,
                                                        mean=mean,
                                                        variance=variance,
                                                        epsilon=epsilon,
                                                        scale=scale,
                                                        beta=beta))
     return potential_descriptors
コード例 #17
0
 def _create_layer_builder(cls, descriptor):
     builder_class = layers.layer_builders.get(type(descriptor), None)
     if builder_class is None:
         raise ConverterError(
             code_to_message.get_error_message(
                 'ERROR_TF_NO_INPUT_TO_CREATE_LAYER')(type(descriptor)))
     return builder_class()
コード例 #18
0
    def resolve_layer(self, graph_matcher, graph_helper):
        potential_descriptors = []
        for sequence in self.sequences:
            matches = graph_matcher.match_sequence(sequence)
            for match in matches:
                coefficients = match['alphas']
                add_op = match['f']
                if coefficients.type not in ['Identity', 'Const']:
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_RESOLVE_PRELU_COEFF'))

                output_op_nodes_names = [
                    str(match[node.identifier].outputs[0].name)
                    for node in sequence.output_nodes
                ]
                consumed_nodes = match.consumed_nodes
                potential_descriptors.append(
                    PReLuLayerResolver.Descriptor(
                        str(add_op.name),
                        consumed_nodes,
                        graph_helper.evaluate_tensor_output(
                            coefficients.outputs[0]),
                        output_names=output_op_nodes_names))
        return potential_descriptors
コード例 #19
0
ファイル: pow.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def resolve_layer(self, graph_matcher, graph_helper):
        descriptors = []
        for sequence in self.sequences:
            for match in graph_matcher.match_sequence(sequence):
                pow_op = match['pow']
                const_values_op = match['const']
                const_values = graph_helper.evaluate_tensor_output(
                    const_values_op.outputs[0])

                # only scalar power op is supported
                if not np.isscalar(const_values):
                    raise ConverterError(
                        code_to_message.get_error_message(
                            'ERROR_TF_POW_CONSTANT_NOT_SCALAR'))

                consumed_nodes = match.consumed_nodes
                pow_descriptor = PowLayerResolver.Descriptor(
                    str(pow_op.name),
                    consumed_nodes,
                    1,
                    0,
                    const_values,
                    output_names=[str(pow_op.outputs[0].name)])
                descriptors.extend([pow_descriptor])

        return descriptors
コード例 #20
0
    def _convert_layers(self):
        """
        :rtype: None
        """
        graph_ops = list(self._ops)
        descriptors = self._resolve_descriptors_from_nodes(graph_ops)
        descriptors = self._resolve_hierarchical_resolution_conflicts(
            descriptors)
        original_descriptors = descriptors

        self._topology_resolver.resolve_topology(self._input_descriptors +
                                                 descriptors)
        descriptors = self._topology_resolver.sort_descriptors_in_execution_order(
            descriptors, self._input_descriptors)
        descriptors = self._filter_disconnected_descriptors(descriptors)

        if self._strict_node_resolution:
            self._assert_all_ops_supported(original_descriptors, graph_ops)
            self._assert_all_descriptors_consumed(descriptors,
                                                  original_descriptors)
            if self._all_ops_consumed is False:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_OPERATION_NOT_MAPPED_TO_LAYER'))

        self._transform_descriptors(descriptors)
        self._topology_resolver.resolve_topology(self._input_descriptors +
                                                 descriptors)
        descriptors = [d for d in descriptors if not d.is_ignored]

        self._create_layers(descriptors)
コード例 #21
0
    def axes_to_spatial_first_order(self, node, graph):
        AxisTracker.log_axes_to_spatial_first_order(node, graph)
        input_buf = graph.get_input_buffers(node)[0]
        if input_buf.rank() == 4:
            AxisTracker.enforce_input_format(graph, input_buf.name,
                                             AxisTracker.AxisFormat.NSC,
                                             AxisTracker.AxisFormat.NCS_TO_NSC)
            # weights expect NCHW order, need to permute
            input_buf = graph.get_input_buffers(node)[0]
            batch, height, width, depth = input_buf.shape
            weights = node.op.weights_list[0]

            # TODO: this optimization was added based on onnx framework. Verify(Modify) if
            #       change is needed for other frameworks
            # ONNX defines FC as W^Tx + b,
            # so the weights have shape (batch, input_size, output_size)
            input_size = weights.shape[0]
            output_size = weights.shape[1]
            log_assert(
                input_size == depth * height * width,
                code_to_message.get_error_message("ERROR_FC_WRONG_INPUT_SIZE")(
                    node.op.name, input_size, (depth, height, width)))
            weights.shape = (depth, height, width, output_size)
            weights = numpy.transpose(weights, (3, 1, 2, 0))
            weights = numpy.ascontiguousarray(weights, dtype=numpy.float32)
            weights.shape = (output_size, input_size)
            node.op.weights_list[0] = weights
        elif input_buf.rank() == 2:
            # again, need to transpose weights for spatial_first order
            weights = node.op.weights_list[0]
            weights = numpy.ascontiguousarray(numpy.transpose(weights, (1, 0)))
            node.op.weights_list[0] = weights

        output_buf = graph.get_output_buffers(node)[0]
        output_buf.axis_format = AxisTracker.AxisFormat.FEATURE
コード例 #22
0
ファイル: argmax.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def resolve_layer(self, graph_matcher, graph_helper):
        descriptors = []
        for match in graph_matcher.match_sequence(self.sequence):
            argmax_op = match['root']
            input_op = match['input']
            axis_op = match['axis']

            input_shape = graph_helper.get_op_output_shape(input_op)
            input_rank = len(input_shape)

            axis = int(graph_helper.evaluate_tensor_output(axis_op.outputs[0]))
            if axis < 0:
                axis += input_rank

            if axis < 0 or axis >= input_rank:
                raise ConverterError(
                    code_to_message.get_error_message(
                        'ERROR_TF_ARGMAX_INVALID_AXIS')(axis, input_rank))

            consumed_nodes = match.consumed_nodes
            argmax_descriptor = ArgMaxLayerResolver.Descriptor(
                str(argmax_op.name),
                consumed_nodes,
                axis,
                output_names=[str(argmax_op.outputs[0].name)])
            descriptors.extend([argmax_descriptor])

        return descriptors
コード例 #23
0
ファイル: util.py プロジェクト: Weizhuo-Zhang/ML_coursera
 def fetch(self, *keys, **kwargs):
     ret = []
     # Prunable indicates whether the weights have been consumed in such a way as to
     # allow pruning of the node (eg Const ops that contain weights are consumed by
     # Conv/FC/etc and thus can be pruned from the network. Const ops that are inputs
     # to a node cannot
     consumed = kwargs.get('prunable', True)
     for key in keys:
         key = str(key)
         log_debug(
             code_to_message.get_debugging_message(
                 "DEBUG_RETRIEVE_WEIGHTS, key"))
         if key not in self.weight_map:
             raise KeyError(
                 code_to_message.get_error_message(
                     "ERROR_WEIGHTS_MISSING_KEY")(key))
         self.weight_map[key].consumed = consumed
         # Explicitly copy the data so if later ops modify it, the original data remains intact
         ret.append(
             numpy.require(self.weight_map[key].weights.copy(),
                           dtype=numpy.float32))
     if len(ret) == 1:
         return ret[0]
     else:
         return ret
コード例 #24
0
    def apply_method_to_all_ops(self, method_name, graph, *args, **kwargs):
        """
        Runs the requested method on all ops in the given graph. i.e loops through the nodes in graph, gets the
        corresponding translation class for node and runs the given method with node and graph as args
        :param method_name: name of the method to call
        :param graph: the IR Opgraph to traverse
        :param args: required positional arguments that will be passed to method
        :param kwargs: keywords arguments to be used to pass fail_if_no_method to this function

        raises KeyError if method no found for an op_type translation unless fail_if_no_method is set to False
                        in the kwargs argument
        """
        for node in graph.list_nodes():
            if node in graph.list_nodes(
            ):  # this extra check is needed since an optimization applied to op below
                # can remove next node(s), so doing a dynamic check is needed
                translation = self.__get_translation(node.op.type)
                if translation.has_indexed_method(method_name):
                    self.apply_method_to_op(node.op.type, method_name, node,
                                            graph, *args)
                else:
                    fail_if_no_method = kwargs.get('fail_if_no_method', True)
                    if fail_if_no_method:
                        raise KeyError(
                            code_to_message.get_error_message(
                                "ERROR_METHOD_NOT_FOUND_FOR_OP_TYPE")(
                                    method_name, node.op.type))
コード例 #25
0
ファイル: slice.py プロジェクト: Weizhuo-Zhang/ML_coursera
 def get_split_positions(cls, input_shape, split_count, split_sizes, split_axis):
     split_points = []
     if len(split_sizes) > 0:
         if sum(split_sizes) != input_shape[split_axis]:
             raise ConverterError(code_to_message.get_error_message('ERROR_TF_SLICE_SIZE_MISMATCH'))
         split_index = split_sizes[0]
         for size in split_sizes[1:]:
             split_points.append(int(split_index))
             split_index += size
     else:
         split_axis_dim = input_shape[split_axis]
         split_size = split_axis_dim // split_count
         if split_axis_dim % split_count:
             raise ConverterError(code_to_message.get_error_message('ERROR_TF_SLICE_UNEVEN_SPLIT'))
         for index in range(1, split_count):
             split_points.append(int(index * split_size))
     return split_points
コード例 #26
0
    def build_layer(self, converter_context, descriptor, input_descriptors, output_descriptors):
        """
        :type input_descriptors: [converters.tensorflow.common.LayerDescriptor]
        :type output_descriptors: [converters.tensorflow.common.LayerDescriptor]
        :type converter_context: converters.tensorflow.converter.ConverterContext
        :type descriptor: StridedSliceLayerResolver.Descriptor
        :rtype: int
        """
        input_name = self.get_input_name(converter_context, descriptor, input_descriptors)
        output_name = descriptor.output_names[0]

        if descriptor.ellipsis_mask != 0 or descriptor.new_axis_mask != 0:
            raise ConverterError(code_to_message.get_error_message('ERROR_TF_STRIDED_SLICE_UNSUPPORTED_MASKS'))

        input_rank = len(descriptor.input_shape)
        strides_rank = descriptor.strides.shape[0]

        # Extend to match input rank
        begin = np.append(descriptor.begin, np.zeros(input_rank - strides_rank, dtype=np.int32)).tolist()
        strides = np.append(descriptor.strides, np.ones(input_rank - strides_rank, dtype=np.int32)).tolist()
        end = np.append(descriptor.end, descriptor.input_shape[strides_rank:]).astype(np.int32).tolist()

        # Apply the binary masks
        for i in range(len(strides)):
            begin_mask_bit = self.get_bit(descriptor.begin_mask, i)
            end_mask_bit = self.get_bit(descriptor.end_mask, i)
            shrink_mask_bit = self.get_bit(descriptor.shrink_axis_mask, i)

            # Convert negative indices
            if begin[i] < 0:
                begin[i] += descriptor.input_shape[i]
            if end[i] < 0:
                end[i] += descriptor.input_shape[i]

            # Apply mask bits
            if strides[i] > 0:
                if begin_mask_bit:
                    begin[i] = 0
                if end_mask_bit:
                    end[i] = descriptor.input_shape[i]
            else:
                if begin_mask_bit:
                    begin[i] = descriptor.input_shape[i] - 1
                if end_mask_bit:
                    end[i] = -1

            # Apply shrink_axis_mask
            if shrink_mask_bit:
                strides[i] = 1
                end[i] = begin[i] + strides[i]

        return converter_context.model.add_strided_slice_layer(name=descriptor.layer_name,
                                                               input_name=input_name,
                                                               output_name=output_name,
                                                               begin=begin,
                                                               end=end,
                                                               strides=strides,
                                                               shrink_axis_mask=descriptor.shrink_axis_mask)
コード例 #27
0
ファイル: ssd.py プロジェクト: Weizhuo-Zhang/ML_coursera
    def build_layer(self, converter_context, descriptor, input_descriptors,
                    output_descriptors):
        """
        :type input_descriptors: [converters.tensorflow.common.LayerDescriptor]
        :type output_descriptors: [converters.tensorflow.common.LayerDescriptor]
        :type converter_context: converters.tensorflow.converter.ConverterContext
        :type descriptor: ConcatLayerResolver.Descriptor
        :rtype: int
        """
        if len(input_descriptors) != 2:
            raise ConverterError(
                get_error_message('ERROR_TF_SSD_NMS_REQUIRES_2_INPUTS'))

        input_names = []
        input_shapes = []
        for i in input_descriptors:
            tensors = converter_context.get_output_tensors_between(
                i, descriptor)
            if len(tensors) != 1:
                raise ConverterError(
                    get_error_message(
                        'ERROR_TF_SSD_NMS_REQUIRES_SINGLE_INPUT_TENSOR'))

            input_shapes.append(
                converter_context.graph_helper.get_op_output_shape(
                    tensors[0].op))

        for index, shape in enumerate(input_shapes):
            output_names = input_descriptors[index].output_names
            if len(shape) == 3 and shape[-1] == 4:
                input_names = output_names + input_names
            else:
                input_names.extend(output_names)

        classes_shape = converter_context.graph_helper.get_op_output_shape(
            descriptor.classes_output_op)

        return converter_context.model.add_multi_class_nms_layer(
            name=descriptor.layer_name,
            input_names=input_names,
            output_names=descriptor.output_names,
            scoreThreshold=descriptor.score_threshold,
            iouThreshold=descriptor.iou_threshold,
            maxDetectionPerClass=classes_shape[-1],
            maxTotalDetections=classes_shape[-1])
コード例 #28
0
 def get_biases(self, graph_helper, conv_op, bias_op):
     _, biases_tensor = GraphHelper.get_op_input_tensors(
         bias_op, ('?', '?'))
     if biases_tensor.op.type not in ['Identity', 'Const'] and \
             not graph_helper.check_tensor_const_origin(biases_tensor):
         raise ConverterError(
             code_to_message.get_error_message('ERROR_TF_CONV_RESOLVE_BIAS')
             (conv_op.name))
     biases = graph_helper.evaluate_tensor_output(biases_tensor)
     return biases
コード例 #29
0
 def axes_to_spatial_first_order(self, node, graph):
     input_name = node.input_names[0]
     input_buf = graph.get_input_buffers(node)[0]
     output_buf = graph.get_output_buffers(node)[0]
     # check for trivial cases first, which will end up
     # in removal. Otherwise, just set output order to nontrivial
     if input_buf.axis_format == AxisTracker.AxisFormat.NSC:
         # special case: transforming to NSC, will become noop
         if node.op.order == [0, 2, 3, 1]:
             node.op.order = [0, 1, 2, 3]
             output_buf.axis_format = AxisTracker.AxisFormat.NSC
             return
         else:
             # going to nontrivial
             AxisTracker.inject_implicit_permute(
                 graph, input_name, AxisTracker.AxisFormat.NCS,
                 AxisTracker.AxisFormat.NSC_TO_NCS, [node.op.name])
             output_buf.axis_format = AxisTracker.AxisFormat.NONTRIVIAL
     elif input_buf.axis_format == AxisTracker.AxisFormat.BTF:
         if node.op.order == [0, 2, 3, 1]:
             node.op.order = [0, 1, 2, 3]
             output_buf.axis_format = AxisTracker.AxisFormat.BTF
         else:
             AxisTracker.inject_implicit_permute(
                 graph, input_name, AxisTracker.AxisFormat.TBF,
                 AxisTracker.AxisFormat.TBF_TO_BTF, [node.op.name])
             output_buf.axis_format = AxisTracker.AxisFormat.NONTRIVIAL
     elif input_buf.axis_format == AxisTracker.AxisFormat.NONTRIVIAL:
         if len(node.op.order) == 4:
             output_buf.axis_format = AxisTracker.AxisFormat.NONTRIVIAL
         elif len(node.op.order) > 4:
             raise ValueError(
                 code_to_message.get_error_message(
                     "ERROR_PERMUTE_TOO_MANY_DIMENSIONS")(node.op.order))
         else:
             # nothing to be done
             output_buf.axis_format = AxisTracker.AxisFormat.NONTRIVIAL
     else:
         raise ValueError(
             code_to_message.get_error_message(
                 "ERROR_PERMUTE_UNEXPECTED_INPUT_ORDER")(
                     input_buf.axis_format))
コード例 #30
0
 def enforce_input_format(cls, graph, input_name, target_format,
                          permute_order):
     input_buf = graph.get_buffer(input_name)
     if input_buf.axis_format == cls.AxisFormat.NONTRIVIAL:
         cls.inject_implicit_permute(graph, input_name, target_format,
                                     permute_order)
     elif input_buf.axis_format != target_format:
         raise ValueError(
             code_to_message.get_error_message(
                 'ERROR_INPUT_DATA_ORDER_UNEXPECTED')(
                     input_name, target_format, input_buf.axis_format))