Example #1
0
def raw_spatial_spatial_attr(model, img, layer1, layer2, override=None):
    """Attribution between spatial positions in two different layers."""

    # Set up a graph for doing attribution...
    with tf.Graph().as_default(), tf.Session(), gradient_override_map(override
                                                                      or {}):
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)

        # Compute activations
        acts1 = T(layer1).eval()
        acts2 = T(layer2).eval({T(layer1): acts1})

        # Construct gradient tensor
        # Backprop from spatial position (n_x, n_y) in layer2 to layer1.
        n_x, n_y = tf.placeholder("int32", []), tf.placeholder("int32", [])
        layer2_mags = tf.sqrt(tf.reduce_sum(T(layer2)**2, -1))[0]
        score = layer2_mags[n_x, n_y]
        t_grad = tf.gradients([score], [T(layer1)])[0]

        # Compute attribution backwards from each positin in layer2
        attrs = []
        for i in range(acts2.shape[1]):
            attrs_ = []
            for j in range(acts2.shape[2]):
                grad = t_grad.eval({n_x: i, n_y: j, T(layer1): acts1})
                # linear approximation of imapct
                attr = np.sum(acts1 * grad, -1)[0]
                attrs_.append(attr)
            attrs.append(attrs_)
    return np.asarray(attrs)
Example #2
0
def raw_class_group_attr(img,
                         model,
                         layer,
                         label,
                         labels,
                         group_vecs,
                         override=None):
    """
  The method of Gradient * Activation maps
  """

    # Set up a graph for doing attribution...
    with tf.Graph().as_default(), tf.Session(), gradient_override_map(override
                                                                      or {}):
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)

        # Compute activations
        acts = T(layer).eval()

        if label is None:
            return np.zeros(acts.shape[1:-1])

        # Compute gradient
        score = T("softmax2_pre_activation")[0, labels.index(label)]
        t_grad = tf.gradients([score], [T(layer)])[0]
        grad = t_grad.eval({T(layer): acts})

        # Linear approximation of effect of spatial position
        return [np.sum(group_vec * grad) for group_vec in group_vecs]
def get_multi_path_attr(model,
                        layer_name,
                        prev_layer_name,
                        obses,
                        prev_nmf,
                        *,
                        act_dir=None,
                        act_poses=None,
                        score_fn=default_score_fn,
                        override=None,
                        max_paths=50,
                        integrate_steps=10):
    with tf.Graph().as_default(), tf.Session(), gradient_override_map(override
                                                                      or {}):
        t_obses = tf.placeholder_with_default(obses.astype(np.float32),
                                              (None, None, None, None))
        T = render.import_model(model, t_obses, t_obses)
        t_acts = T(layer_name)
        if prev_layer_name is None:
            t_acts_prev = t_obses
        else:
            t_acts_prev = T(prev_layer_name)
        if act_dir is not None:
            t_acts = act_dir[None, None, None] * t_acts
        if act_poses is not None:
            t_acts = tf.gather_nd(
                t_acts,
                tf.concat([tf.range(obses.shape[0])[..., None], act_poses],
                          axis=-1),
            )
        t_scores = score_fn(t_acts)
        assert len(
            t_scores.shape) >= 1, "score_fn should not reduce the batch dim"
        t_score = tf.reduce_sum(t_scores)
        t_grad = tf.gradients(t_score, [t_acts_prev])[0]
        acts_prev = t_acts_prev.eval()
        path_acts = get_paths(acts_prev,
                              prev_nmf,
                              max_paths=max_paths,
                              integrate_steps=integrate_steps)
        deltas_of_path = lambda path: np.array([
            b - a for a, b in zip([np.zeros_like(acts_prev)] + path[:-1], path)
        ])
        grads_of_path = lambda path: np.array(
            [t_grad.eval(feed_dict={t_acts_prev: acts}) for acts in path])
        path_attrs = map(
            lambda path:
            (deltas_of_path(path) * grads_of_path(path)).sum(axis=0),
            path_acts,
        )
        total_attr = 0
        num_paths = 0
        for attr in path_attrs:
            total_attr += attr
            num_paths += 1
        return total_attr / num_paths
Example #4
0
def test_gradient_override_relu6_directionality(nonl_name, nonl,
                                                nonl_grad_override, examples):
    for incoming_grad, input, grad in examples:
        with tf.Session().as_default() as sess:
            batched_shape = [1, 1]
            incoming_grad_t = tf.constant(incoming_grad, shape=batched_shape)
            input_t = tf.constant(input, shape=batched_shape)
            with gradient_override_map({nonl_name: nonl_grad_override}):
                nonl_t = nonl(input_t)
                grad_wrt_input = tf.gradients(nonl_t, input_t,
                                              [incoming_grad_t])[0]
            assert (grad_wrt_input.eval() == grad).all()
Example #5
0
def test_gradient_override_map():
    def gradient_override(op, grad):
        return tf.constant(42)

    with tf.Session().as_default() as sess:
        a = tf.constant(1.)
        standard_relu = tf.nn.relu(a)
        grad_wrt_a = tf.gradients(standard_relu, a, [1.])[0]
        with gradient_override_map({"Relu": gradient_override}):
            overriden_relu = tf.nn.relu(a)
            overriden_grad_wrt_a = tf.gradients(overriden_relu, a, [1.])[0]
        assert grad_wrt_a.eval() != overriden_grad_wrt_a.eval()
        assert overriden_grad_wrt_a.eval() == 42
def get_grad_or_attr(model,
                     layer_name,
                     prev_layer_name,
                     obses,
                     *,
                     act_dir=None,
                     act_poses=None,
                     score_fn=default_score_fn,
                     grad_or_attr,
                     override=None,
                     integrate_steps=1):
    with tf.Graph().as_default(), tf.Session(), gradient_override_map(override
                                                                      or {}):
        t_obses = tf.placeholder_with_default(obses.astype(np.float32),
                                              (None, None, None, None))
        T = render.import_model(model, t_obses, t_obses)
        t_acts = T(layer_name)
        if prev_layer_name is None:
            t_acts_prev = t_obses
        else:
            t_acts_prev = T(prev_layer_name)
        if act_dir is not None:
            t_acts = act_dir[None, None, None] * t_acts
        if act_poses is not None:
            t_acts = tf.gather_nd(
                t_acts,
                tf.concat([tf.range(obses.shape[0])[..., None], act_poses],
                          axis=-1),
            )
        t_scores = score_fn(t_acts)
        assert len(
            t_scores.shape) >= 1, "score_fn should not reduce the batch dim"
        t_score = tf.reduce_sum(t_scores)
        t_grad = tf.gradients(t_score, [t_acts_prev])[0]
        if integrate_steps > 1:
            acts_prev = t_acts_prev.eval()
            grad = (sum([
                t_grad.eval(feed_dict={t_acts_prev: acts_prev * alpha})
                for alpha in np.linspace(0, 1, integrate_steps + 1)[1:]
            ]) / integrate_steps)
        else:
            acts_prev = None
            grad = t_grad.eval()
        if grad_or_attr == "grad":
            return grad
        elif grad_or_attr == "attr":
            if acts_prev is None:
                acts_prev = t_acts_prev.eval()
            return acts_prev * grad
        else:
            raise NotImplementedError
Example #7
0
def raw_class_spatial_attr(img, layer, label, override=None):
    """How much did spatial positions at a given layer effect a output class?"""

    # Set up a graph for doing attribution...
    with tf.Graph().as_default(), tf.Session(), gradient_override_map(override or {}):
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)

        # Compute activations
        acts = T(layer).eval()

        if label is None: return np.zeros(acts.shape[1:-1])

        # Compute gradient
        score = T("softmax2_pre_activation")[0, labels.index(label)]
        t_grad = tf.gradients([score], [T(layer)])[0]
        grad = t_grad.eval({T(layer): acts})

        # Linear approximation of effect of spatial position
        return np.sum(acts * grad, -1)[0]
Example #8
0
def make_vis_T(
    model,
    objective_per_image,
    objective_additional_global,
    param_f=None,
    optimizer=None,
    transforms=None,
    relu_gradient_override=False,
):
    """Even more flexible optimization-base feature vis.

    This function is the inner core of render_vis(), and can be used
    when render_vis() isn't flexible enough. Unfortunately, it's a bit more
    tedious to use:

    >    with tf.Graph().as_default() as graph, tf.Session() as sess:
    >
    >        T = make_vis_T(model, "mixed4a_pre_relu:0")
    >        tf.initialize_all_variables().run()
    >
    >        for i in range(10):
    >            T("vis_op").run()
    >            showarray(T("input").eval()[0])

    This approach allows more control over how the visualizaiton is displayed
    as it renders. It also allows a lot more flexibility in constructing
    objectives / params because the session is already in scope.


    Args:
        model: The model to be visualized, from Alex' modelzoo.
        objective_f: The objective our visualization maximizes.
            See the objectives module for more details.
        param_f: Paramaterization of the image we're optimizing.
            See the paramaterization module for more details.
            Defaults to a naively paramaterized [1, 128, 128, 3] image.
        optimizer: Optimizer to optimize with. Either tf.train.Optimizer instance,
            or a function from (graph, sess) to such an instance.
            Defaults to Adam with lr .05.
        transforms: A list of stochastic transformations that get composed,
            which our visualization should robustly activate the network against.
            See the transform module for more details.
            Defaults to [transform.jitter(8)].

    Returns:
        A function T, which allows access to:
            * T("vis_op") -- the operation for to optimize the visualization
            * T("input") -- the visualization itself
            * T("loss") -- the loss for the visualization
            * T(layer) -- any layer inside the network
    """

    # pylint: disable=unused-variable
    t_image = make_t_image(param_f)
    objective_per_image = objectives.as_objective(objective_per_image)
    objective_additional_global = objectives.as_objective(
        objective_additional_global)
    transform_f = make_transform_f(transforms)
    optimizer = make_optimizer(optimizer, [])

    global_step = tf.train.get_or_create_global_step()
    init_global_step = tf.variables_initializer([global_step])
    init_global_step.run()

    if relu_gradient_override:
        with gradient_override_map({
                "Relu": redirected_relu_grad,
                "Relu6": redirected_relu6_grad
        }):
            T = import_model(model, transform_f(t_image), t_image)
    else:
        T = import_model(model, transform_f(t_image), t_image)
    loss_per_image = objective_per_image(T)
    loss_additional_global = objective_additional_global(T)
    loss = tf.reduce_mean(loss_per_image) + loss_additional_global

    vis_op = optimizer.minimize(-loss, global_step=global_step)

    local_vars = locals()

    # pylint: enable=unused-variable

    def T2(name):
        if name in local_vars:
            return local_vars[name]
        else:
            return T(name)

    return T2
    def _build_graph(self, graph):
        if graph is None:
            self.g = tf.Graph()
        else:
            self.g = graph

        # Set up graphs of VAE or GAN
        if self.painter_type == "GAN":
            self.painter = ConvGAN(reuse=False,
                                   gpu_mode=self.gpu_mode,
                                   graph=self.g)
        elif self.painter_type == "VAE":
            self.painter = ConvVAE2(reuse=False,
                                    gpu_mode=self.gpu_mode,
                                    graph=self.g)
        self.painter.close_sess()

        with self.g.as_default():
            print('GLOBAL VARS', tf.global_variables())

        with self.g.as_default():
            batch_size = 1
            self.actions = tf.get_variable(
                "action_vars",
                [batch_size, self.num_strokes, 12],
                #initializer=tf.initializers.random_normal()
                initializer=tf.initializers.random_uniform())
            if self.bw:
                actions2 = tf.concat([
                    self.actions[:, :, :6],
                    tf.zeros([1, self.num_strokes, 3]), self.actions[:, :, 9:]
                ],
                                     axis=2)
            else:
                actions2 = self.actions

            self.actions_assign_ph = tf.placeholder(dtype=tf.float32)
            self.actions_assign_op = tf.assign(self.actions,
                                               self.actions_assign_ph)

            # Prepare loop vars for rnn loop
            canvas_state = tf.ones(
                shape=[batch_size, self.full_size, self.full_size, 3],
                dtype=tf.float32)
            i = tf.constant(0)
            initial_canvas_ta = tf.TensorArray(dtype=tf.float32,
                                               size=self.num_strokes)
            loop_vars = (canvas_state, initial_canvas_ta, i)

            # condition for continuation
            def cond(cs, c_ta, i):
                return tf.less(i, self.num_strokes)

            # run one state of rnn cell
            def body(cs, c_ta, i):

                trimmed_actions = tf.sigmoid(actions2)

                print(trimmed_actions.get_shape())

                def use_whole_action():
                    return trimmed_actions[:, i, :12]

                def use_previous_entrypoint():
                    # start x and y are previous end x and y
                    # start pressure is previous pressure
                    return tf.concat([
                        trimmed_actions[:, i, :9], trimmed_actions[:, i - 1,
                                                                   4:6],
                        trimmed_actions[:, i - 1, 0:1]
                    ],
                                     axis=1)

                if self.connected:
                    inp = tf.cond(tf.equal(i, 0),
                                  true_fn=use_whole_action,
                                  false_fn=use_previous_entrypoint)
                else:
                    inp = use_whole_action()
                inp = tf.reshape(inp, [-1, 12])

                print(inp.get_shape())

                decoded_stroke = self.painter.generate_stroke_graph(inp)

                cases = []
                ctr = 0
                for a in range(self.repeat):
                    for b in range(self.repeat):
                        print([int(self.repeat**2), ctr])
                        print([[0, 0],
                               [(64 - self.overlap_px) * a,
                                (64 - self.overlap_px) * (self.repeat - 1 - a)
                                ],
                               [(64 - self.overlap_px) * b,
                                (64 - self.overlap_px) * (self.repeat - 1 - b)
                                ], [0, 0]])
                        cases.append(
                            (tf.equal(tf.floormod(i, int(self.repeat**2)), ctr)
                             if self.alternate else tf.less(
                                 i, self.unrepeated_num_strokes * (ctr + 1)),
                             lambda a=a, b=b: tf.pad(
                                 decoded_stroke, [[0, 0],
                                                  [(64 - self.overlap_px) * a,
                                                   (64 - self.overlap_px) *
                                                   (self.repeat - 1 - a)],
                                                  [(64 - self.overlap_px) * b,
                                                   (64 - self.overlap_px) *
                                                   (self.repeat - 1 - b)],
                                                  [0, 0]],
                                 constant_values=1)))
                        ctr += 1

                print(cases)
                decoded_stroke = tf.case(cases)

                darkness_mask = tf.reduce_mean(decoded_stroke, axis=3)
                darkness_mask = 1 - tf.reshape(
                    darkness_mask,
                    [batch_size, self.full_size, self.full_size, 1])
                darkness_mask = darkness_mask / tf.reduce_max(darkness_mask)

                color_action = trimmed_actions[:, i, 6:9]
                color_action = tf.reshape(color_action, [batch_size, 1, 1, 3])
                color_action = tf.tile(color_action,
                                       [1, self.full_size, self.full_size, 1])
                stroke_whitespace = tf.equal(decoded_stroke, 1.)
                maxed_stroke = tf.where(stroke_whitespace, decoded_stroke,
                                        color_action)

                cs = (darkness_mask) * maxed_stroke + (1 - darkness_mask) * cs
                c_ta = c_ta.write(i, cs)

                i = tf.add(i, 1)
                return (cs, c_ta, i)

            final_canvas_state, final_canvas_ta, _ = tf.while_loop(
                cond, body, loop_vars, swap_memory=True)
            self.intermediate_canvases = final_canvas_ta.stack()

            content_input = tf.image.resize_images(
                np.expand_dims(self.content, 0),
                [self.full_size, self.full_size])
            final_canvas_state = tf.stack(
                [final_canvas_state[0], content_input[0]])
            print(final_canvas_state.shape)
            self.final_canvas_state = final_canvas_state
            self.resized_final = tf.image.resize_images(
                final_canvas_state, [256, 256])

            #For visualization
            self.content_style_vis = final_canvas_state[1:]

            global_step = tf.train.get_or_create_global_step()

            with gradient_override_map({
                    'Relu': redirected_relu_grad,
                    'Relu6': redirected_relu6_grad
            }):
                self.T = render.import_model(
                    self.inception_v1, self.transform_f(final_canvas_state),
                    final_canvas_state)

            content_obj = 100 * activation_difference(
                content_layers, difference_to=CONTENT_INDEX)
            content_obj.description = "Content Loss"

            self.loss = content_obj(self.T)

            self.vis_op = self.optim.minimize(self.loss,
                                              global_step=global_step,
                                              var_list=[self.actions])

            # initialize vars
            self.init = tf.global_variables_initializer()

            print('TRAINABLE', tf.trainable_variables())
Example #10
0
def compute_igsg(img,
                 model,
                 attr_class,
                 layers,
                 flag1,
                 flag_read_attr=True,
                 iter_num=100,
                 SG_path=False,
                 labels=None,
                 save_directory=None):
    with tf.Graph().as_default(), tf.Session() as sess, gradient_override_map(
        {}):
        # img = tf.image.resize_image_with_crop_or_pad(img, model.image_shape[0], model.image_shape[0])
        # imgnp = sess.run(img)
        # imgnp = imgnp.reshape(224, 224, 3)
        # plt.imsave("./doghead224.jpeg", imgnp)
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)
        # grads_cam_T = [T(layer) for layer in layers]
        # logit = T("softmax2_pre_activation")[0]

        logit_layer = "resnet_v1_50/predictions/Reshape"
        # writer = tf.summary.FileWriter('./graph_vis/', sess.graph)
        # writer.add_graph(tf.get_default_graph())
        # writer.close()

        # logit = T("output2")[0]
        # score = T("output2")[0, labels.index(attr_class)]
        logit = T(logit_layer)[0]
        logit4grad = T(logit_layer)[0, labels.index(attr_class)]

        AM_T = list(range(len(layers)))
        AM_T_reverse = list(range(len(layers)))

        channel_attr_list = list(range(len(layers)))

        kept_channel_list = list(range(len(layers)))
        kept_channel_list_reverse = list(range(len(layers)))

        for i_wanted_layer in range(len(layers)):
            layer = layers[i_wanted_layer]
            acts = T(layer).eval()
            attr = np.zeros(acts.shape[1:])
            t_grad = tf.gradients([logit4grad], [T(layer)])[0]

            if not flag_read_attr:
                for n in range(iter_num):
                    acts_ = acts * float(n) / iter_num
                    if SG_path:
                        acts_ *= (np.random.uniform(0, 1, [528]) +
                                  np.random.uniform(0, 1, [528])) / 1.5
                    grad = t_grad.eval({T(layer): acts_})
                    attr += grad[0]
                attr = attr * (1.0 / iter_num) * acts[0]
                attr = np.sum(np.sum(attr, 0), 0)
                layer_name = re.sub(r'/', "", layer)
                np.savetxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer_name, attr_class),
                    attr)
            else:
                layer_name = re.sub(r'/', "", layer)
                attr = np.loadtxt(save_directory + "/{}_{}_{}.txt".format(
                    flag1, layer_name, attr_class)).astype(np.float32)
            # AM_T[i_wanted_layer] = attr * (attr > 0)

            kept_channel_idx = np.squeeze(
                np.argwhere(
                    attr > np.nanmean(np.where(attr > 0, attr, np.nan))))
            acts_squeeze = np.squeeze(acts)
            attr_temp = np.squeeze(attr).astype(np.float32)
            # print(np.count_nonzero(clear_channel_idx))
            channel_attr_list[i_wanted_layer] = attr_temp
            AM_T[i_wanted_layer] = acts_squeeze[..., kept_channel_idx]
            kept_channel_list[i_wanted_layer] = kept_channel_idx

            # # alltests_Shap/test0_4
            # kept_channel_idx = np.squeeze(np.argwhere(attr < 0))
            # # alltests_Shap/test0_6
            kept_channel_idx = np.squeeze(
                np.argwhere(
                    attr < np.nanmean(np.where(attr < 0, attr, np.nan))))
            AM_T_reverse[i_wanted_layer] = acts_squeeze[..., kept_channel_idx]
            kept_channel_list_reverse[i_wanted_layer] = kept_channel_idx

        AM_list = AM_T
        logit_list = sess.run([logit])[0]
        return [AM_list, AM_T_reverse], logit_list, channel_attr_list, \
               [kept_channel_list, kept_channel_list_reverse]
def lbfgs_min(model,
              objective_f,
              param_f=None,
              optimizer=None,
              transforms=None,
              thresholds=(512, ),
              print_objectives=None,
              verbose=True,
              relu_gradient_override=True,
              use_fixed_seed=False):
    with tf.Graph().as_default() as graph, tf.Session() as sess:

        if use_fixed_seed:  # does not mean results are reproducible, see Args doc
            tf.set_random_seed(0)


#        T = render.make_vis_T(model, objective_f, param_f, optimizer, transforms,
#                       relu_gradient_override)

        t_image = param_f()
        #        placeholder = tf.placeholder(tf.float32, shape=init_img.shape)
        #        placeholder_clip = tf.placeholder(tf.float32, shape=init_img.shape)
        #
        #        assign_op = net['input'].assign(placeholder)
        #assert(isinstance(t_image, tf.Tensor))
        objective_f = objectives.as_objective(objective_f)
        transform_f = render.make_transform_f(transforms)
        #optimizer = make_optimizer(optimizer, [])

        #global_step = tf.train.get_or_create_global_step()
        #init_global_step = tf.variables_initializer([global_step])
        #init_global_step.run()

        if relu_gradient_override:
            with gradient_override_map({
                    'Relu': redirected_relu_grad,
                    'Relu6': redirected_relu6_grad
            }):
                T = render.import_model(model, transform_f(t_image), t_image)
        else:
            T = render.import_model(model, transform_f(t_image), t_image)
        loss = objective_f(T)
        t_image = T("input")

        #print_objective_func = render.make_print_objective_func(print_objectives, T)
        #loss, vis_op, t_image = T("loss"), T("vis_op"), T("input")

        gradient = tf.gradients(loss, t_image)

        i = 0

        def callback(loss, var, grad):
            nonlocal i
            print('Loss evaluation #', i, ', loss:', loss, 'var max',
                  np.max(var), 'grad max', np.max(grad))
            i += 1

        maxcor = 30
        print_disp = 1
        optimizer_kwargs = {'maxiter':max(thresholds),'maxcor': maxcor, \
                    'disp': print_disp}
        #bnds = get_lbfgs_bnds(init_img,clip_value_min,clip_value_max,BGR)
        trainable_variables = tf.trainable_variables()[0]
        print(trainable_variables)
        #        var_eval = trainable_variables.eval()
        #        print('initialization before variable init',np.max(var_eval),np.min(var_eval))
        #var_to_bounds = {trainable_variables: bnds}
        #        optimizer = tf.contrib.opt.ScipyOptimizerInterface(loss_total,var_to_bounds=var_to_bounds,
        #                        method='L-BFGS-B',options=optimizer_kwargs)
        optimizer = tf.contrib.opt.ScipyOptimizerInterface(
            -loss, method='L-BFGS-B', options=optimizer_kwargs)

        tf.global_variables_initializer().run()

        var_eval = trainable_variables.eval()
        print('initialization after variable init', np.max(var_eval),
              np.min(var_eval))
        var_eval = t_image.eval()
        print('initialization', np.max(var_eval), np.min(var_eval))
        images = []
        loss_ = sess.run([loss])
        print("beginning loss :", loss_)
        optimizer.minimize(sess,
                           fetches=[loss, t_image, gradient],
                           loss_callback=callback)
        vis = t_image.eval()
        images.append(vis)
        loss_ = sess.run([loss])
        print("End loss :", loss_)
        #        try:
        #          #sess.run(assign_op, {placeholder: init_img})
        #          optimizer.minimize(sess,step_callback=callback)
        #          for i in range(max(thresholds)+1):
        #            loss_, _ = sess.run([loss, vis_op])
        #            if i in thresholds:
        #              vis = t_image.eval()
        #              images.append(vis)
        #              if verbose:
        #                print(i, loss_)
        #                print_objective_func(sess)
        #                show(np.hstack(vis))
        #        except KeyboardInterrupt:
        #          log.warning("Interrupted optimization at step {:d}.".format(i+1))
        #          vis = t_image.eval()
        #          show(np.hstack(vis))

        return images
def test_autocorr_render_Inception_v1():

    tf.reset_default_graph()
    K.set_learning_phase(0)
    if not (os.path.isfile("model/tf_inception_v1.pb")):
        with K.get_session().as_default():
            model = inception_v1_oldTF(
                weights='imagenet',
                include_top=True)  #include_top=True, weights='imagenet')
            print(model.input)
            os.makedirs('./model', exist_ok=True)

            frozen_graph = freeze_session(
                K.get_session(),
                output_names=[out.op.name for out in model.outputs],
                clear_devices=True)
            # Save the pb model
            tf.io.write_graph(frozen_graph,
                              logdir="model",
                              name="tf_inception_v1.pb",
                              as_text=False)
            nodes_tab = [
                n.name for n in tf.get_default_graph().as_graph_def().node
            ]
            print(nodes_tab)

    #with tf.Graph().as_default() as graph, tf.Session() as sess:
    with gradient_override_map({
            'Relu': redirected_relu_grad,
            'ReLU': redirected_relu_grad
    }):
        lucid_inception_v1 = Lucid_InceptionV1()
        lucid_inception_v1.load_graphdef()


    out = render.render_vis(lucid_inception_v1, 'mixed4a_1x1_pre_relu/Conv2D:0',\
                            relu_gradient_override=True,use_fixed_seed=True)
    plt.figure()
    plt.imshow(out[0][0])


    out = render.render_vis(lucid_inception_v1, 'mixed4b_pre_relu/concat:452',\
                            relu_gradient_override=True,use_fixed_seed=True)
    plt.figure()
    plt.imshow(out[0][0])

    JITTER = 1
    ROTATE = 5
    SCALE = 1.1

    transforms = [
        transform.pad(2 * JITTER),
        transform.jitter(JITTER),
        transform.random_scale([SCALE**(n / 10.) for n in range(-10, 11)]),
        transform.random_rotate(range(-ROTATE, ROTATE + 1))
    ]

    imgs = render.render_vis(lucid_inception_v1,
                             'mixed4b_pre_relu/concat:452',
                             transforms=transforms,
                             param_f=lambda: param.image(64),
                             thresholds=[2048],
                             verbose=False,
                             relu_gradient_override=True,
                             use_fixed_seed=True)
    plt.figure()
    plt.imshow(imgs[0][0])
def test_render_Inception_v1_slim():

    K.set_learning_phase(0)
    model_path = 'model/tf_inception_v1_slim.pb'
    if not (os.path.exists(model_path)):
        with K.get_session().as_default():
            model = InceptionV1_slim(include_top=True, weights='imagenet')
            os.makedirs('./model', exist_ok=True)

            #model.save('./model/inception_v1_keras_model.h5')
            frozen_graph = freeze_session(
                K.get_session(),
                output_names=[out.op.name for out in model.outputs],
                clear_devices=True)
            # Save the pb model
            tf.io.write_graph(frozen_graph,
                              logdir="model",
                              name="tf_inception_v1_slim.pb",
                              as_text=False)

    with tf.Graph().as_default() as graph, tf.Session() as sess:

        # f = gfile.FastGFile("/model/tf_inception_v1.pb", 'rb')
        # graph_def = tf.GraphDef()
        # # Parses a serialized binary message into the current message.
        # graph_def.ParseFromString(f.read())
        # f.close()

        # sess.graph.as_default()
        # # Import a serialized TensorFlow `GraphDef` protocol buffer
        # # and place into the current default `Graph`.
        # tf.import_graph_def(graph_def)

        # nodes_tab = [n.name for n in tf.get_default_graph().as_graph_def().node]
        #print(nodes_tab)
        with gradient_override_map({
                'Relu': redirected_relu_grad,
                'ReLU': redirected_relu_grad
        }):
            # cela ne semble pas apporter quoique ce soit de particulier
            lucid_inception_v1 = Lucid_Inception_v1_slim()
            lucid_inception_v1.load_graphdef()

        neuron1 = ('mixed4b_pre_relu', 111)  # large fluffy
        C = lambda neuron: objectives.channel(*neuron)
        out = render.render_vis(lucid_inception_v1, 'Mixed_4b_Concatenated/concat:452',\
                                relu_gradient_override=True,use_fixed_seed=True)
        plt.imshow(out[0][0])

        JITTER = 1
        ROTATE = 5
        SCALE = 1.1

        transforms = [
            transform.pad(2 * JITTER),
            transform.jitter(JITTER),
            transform.random_scale([SCALE**(n / 10.) for n in range(-10, 11)]),
            transform.random_rotate(range(-ROTATE, ROTATE + 1))
        ]
        # https://github.com/tensorflow/lucid/issues/82
        with gradient_override_map({
                'Relu': redirected_relu_grad,
                'ReLU': redirected_relu_grad
        }):
            out = render.render_vis(lucid_inception_v1, "Mixed_4b_Concatenated/concat:452", transforms=transforms,
                                     param_f=lambda: param.image(64),
                                     thresholds=[2048], verbose=False,\
                                     relu_gradient_override=True,use_fixed_seed=True)
        # out = render.render_vis(lucid_inception_v1, "Mixed_4d_Branch_2_b_3x3_act/Relu:452", transforms=transforms,
        #                          param_f=lambda: param.image(64),
        #                          thresholds=[2048], verbose=False) # Cela ne marche pas !
        plt.imshow(out[0][0])

        out = render.render_vis(lucid_inception_v1, "Mixed_3c_Concatenated/concat:479", transforms=transforms,
                                 param_f=lambda: param.image(64),
                                 thresholds=[2048], verbose=False,\
                                 relu_gradient_override=True,use_fixed_seed=True)
        plt.imshow(out[0][0])
def compute_all_am_igsg(img,
                        model,
                        attr_class,
                        layers,
                        flag1,
                        flag_read_attr=True,
                        iter_num=2**8,
                        SG_path=False,
                        labels=None,
                        save_directory=None):
    """
  Using Aumann Shapley values as feature attributions
  Return all attributions and AM not just positive or negative ones
  """
    with tf.Graph().as_default(), tf.Session() as sess, gradient_override_map(
        {}):
        # img = tf.image.resize_image_with_crop_or_pad(img, model.image_shape[0], model.image_shape[0])
        # imgnp = sess.run(img)
        # imgnp = imgnp.reshape(224, 224, 3)
        # plt.imsave("./doghead224.jpeg", imgnp)
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)
        # grads_cam_T = [T(layer) for layer in layers]
        # logit = T("softmax2_pre_activation")[0]

        # score = T("output2")[0, labels.index(attr_class)]
        logit = T("softmax2_pre_activation")[0]
        logit4grad = T("softmax2_pre_activation")[0, labels.index(attr_class)]
        AM_T = list(range(len(layers)))
        channel_attr_list = list(range(len(layers)))

        ori_logit = logit.eval()
        ori_single_logit = logit4grad.eval()

        y_label = np.zeros_like(ori_logit)
        y_label[labels.index(attr_class)] = 1

        # index_class_logit = ori_logit[labels.index(attr_class)]
        # detected_label_index = ori_logit.argmax()
        # print("detected label index: {}, real label index: {}, label name: {}"
        #       .format(detected_label_index, labels.index(attr_class), attr_class))
        for i_wanted_layer in range(len(layers)):
            layer = layers[i_wanted_layer]
            acts = T(layer).eval()

            attr = np.zeros(acts.shape[1:])
            t_grad = tf.gradients([logit4grad], [T(layer)])[0]

            if not flag_read_attr:
                for n in range(iter_num):
                    acts_ = acts * float(n) / iter_num
                    if SG_path:
                        acts_ *= (np.random.uniform(0, 1, [528]) +
                                  np.random.uniform(0, 1, [528])) / 1.5
                    grad = t_grad.eval({T(layer): acts_})
                    attr += grad[0]
                attr = attr * (1.0 / iter_num) * acts[0]
                attr = np.sum(np.sum(attr, 0), 0)

                # normalize IG result for degub differences
                attr = attr * ori_single_logit / np.sum(attr)
                np.savetxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer, attr_class), attr)
            else:
                attr = np.loadtxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer, attr_class)).astype(
                        np.float32)

            attr_temp = np.squeeze(attr).astype(np.float32)
            channel_attr_list[i_wanted_layer] = attr_temp

            acts_squeeze = np.squeeze(acts)
            AM_T[i_wanted_layer] = acts_squeeze

        AM_list = AM_T
        logit_list = sess.run([logit])[0]
        return AM_list, logit_list, channel_attr_list
def compute_all_am_shap(img,
                        model,
                        attr_class,
                        layers,
                        flag1,
                        flag_read_attr=True,
                        iter_num=2**8,
                        labels=None,
                        save_directory=None):
    """
  Using sampling based Shapley method to compute feature attributions
  Return all attributions and AM not just positive or negative ones
  """
    with tf.Graph().as_default(), tf.Session() as sess, gradient_override_map(
        {}):
        # img = tf.image.resize_image_with_crop_or_pad(img, model.image_shape[0], model.image_shape[0])
        # imgnp = sess.run(img)
        # imgnp = imgnp.reshape(224, 224, 3)
        # plt.imsave("./doghead224.jpeg", imgnp)
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)
        # grads_cam_T = [T(layer) for layer in layers]
        # logit = T("softmax2_pre_activation")[0]

        # score = T("output2")[0, labels.index(attr_class)]
        logit = T("softmax2_pre_activation")[0]
        AM_T = list(range(len(layers)))
        channel_attr_list = list(range(len(layers)))
        ori_logit = logit.eval()

        y_label = np.zeros_like(ori_logit)
        y_label[labels.index(attr_class)] = 1

        # index_class_logit = ori_logit[labels.index(attr_class)]
        # detected_label_index = ori_logit.argmax()
        # print("detected label index: {}, real label index: {}, label name: {}"
        #       .format(detected_label_index, labels.index(attr_class), attr_class))
        for i_wanted_layer in range(len(layers)):
            layer = layers[i_wanted_layer]
            acts = T(layer).eval()
            acts_shape = list(acts.shape)
            # part_name = "import/{}:0".format(layer)
            # t_part_input = tf.placeholder(acts.dtype, acts_shape)
            # T_part = import_part_model(model, t_part_input, part_name)
            # part_logit = T_part("softmax2_pre_activation")[0]

            n_features = acts.shape[-1]

            if not flag_read_attr:
                result = np.zeros((1, n_features))
                run_shape = acts_shape.copy()
                # run_shape = np.delete(run_shape, -1).tolist()
                # run_shape.insert(-1, -1)
                reconstruction_shape = [1, acts_shape[-1]]

                for r in range(iter_num):
                    p = np.random.permutation(n_features)
                    x = acts.copy().reshape(run_shape)

                    y = None
                    for i in p:
                        if y is None:
                            y = logit.eval({T(layer): x})
                            # y = model.predict(x.reshape(acts_shape))
                        x[..., i] = 0
                        y0 = logit.eval({T(layer): x})
                        # print("Ori logit score: {}, new logit score: {}"
                        #       .format(index_class_logit, y0[labels.index(attr_class)]))
                        # y0 = model.predict(x.reshape(acts_shape))
                        assert y0.shape == y_label.shape, y0.shape
                        prediction_delta = np.sum((y - y0) * y_label)
                        result[:, i] += prediction_delta
                        y = y0
                attr = np.squeeze(
                    (result.copy() /
                     iter_num).reshape(reconstruction_shape).astype(
                         np.float32))
                np.savetxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer, attr_class), attr)
            else:
                attr = np.loadtxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer, attr_class)).astype(
                        np.float32)

            acts_squeeze = np.squeeze(acts)
            attr_temp = np.squeeze(attr).astype(np.float32)
            channel_attr_list[i_wanted_layer] = attr_temp
            AM_T[i_wanted_layer] = acts_squeeze

        AM_list = AM_T
        logit_list = sess.run([logit])[0]
        return AM_list, logit_list, channel_attr_list
def compute_shap(img,
                 model,
                 attr_class,
                 layers,
                 flag1,
                 flag_read_attr=True,
                 iter_num=2**8,
                 labels=None,
                 save_directory=None):
    """
  Using sampling based Shapley method to compute feature attributions
  """
    with tf.Graph().as_default(), tf.Session() as sess, gradient_override_map(
        {}):
        # img = tf.image.resize_image_with_crop_or_pad(img, model.image_shape[0], model.image_shape[0])
        # imgnp = sess.run(img)
        # imgnp = imgnp.reshape(224, 224, 3)
        # plt.imsave("./doghead224.jpeg", imgnp)
        t_input = tf.placeholder_with_default(img, [None, None, 3])
        T = render.import_model(model, t_input, t_input)
        # grads_cam_T = [T(layer) for layer in layers]
        # logit = T("softmax2_pre_activation")[0]

        # score = T("output2")[0, labels.index(attr_class)]
        logit = T("softmax2_pre_activation")[0]
        AM_T = list(range(len(layers)))
        AM_T_reverse = list(range(len(layers)))

        channel_attr_list = list(range(len(layers)))

        kept_channel_list = list(range(len(layers)))
        kept_channel_list_reverse = list(range(len(layers)))
        ori_logit = logit.eval()

        y_label = np.zeros_like(ori_logit)
        y_label[labels.index(attr_class)] = 1

        # index_class_logit = ori_logit[labels.index(attr_class)]
        # detected_label_index = ori_logit.argmax()
        # print("detected label index: {}, real label index: {}, label name: {}"
        #       .format(detected_label_index, labels.index(attr_class), attr_class))
        for i_wanted_layer in range(len(layers)):
            layer = layers[i_wanted_layer]
            acts = T(layer).eval()
            acts_shape = list(acts.shape)
            # part_name = "import/{}:0".format(layer)
            # t_part_input = tf.placeholder(acts.dtype, acts_shape)
            # T_part = import_part_model(model, t_part_input, part_name)
            # part_logit = T_part("softmax2_pre_activation")[0]

            n_features = acts.shape[-1]

            if not flag_read_attr:
                result = np.zeros((1, n_features))
                run_shape = acts_shape.copy()
                # run_shape = np.delete(run_shape, -1).tolist()
                # run_shape.insert(-1, -1)
                reconstruction_shape = [1, acts_shape[-1]]

                for r in range(iter_num):
                    p = np.random.permutation(n_features)
                    x = acts.copy().reshape(run_shape)

                    y = None
                    for i in p:
                        if y is None:
                            y = logit.eval({T(layer): x})
                            # y = model.predict(x.reshape(acts_shape))
                        x[..., i] = 0
                        y0 = logit.eval({T(layer): x})
                        # print("Ori logit score: {}, new logit score: {}"
                        #       .format(index_class_logit, y0[labels.index(attr_class)]))
                        # y0 = model.predict(x.reshape(acts_shape))
                        assert y0.shape == y_label.shape, y0.shape
                        prediction_delta = np.sum((y - y0) * y_label)
                        # if i == 139:
                        #   print("AM 139: attr is {}".format(prediction_delta))
                        result[:, i] += prediction_delta
                        y = y0
                attr = np.squeeze(
                    (result.copy() /
                     iter_num).reshape(reconstruction_shape).astype(
                         np.float32))
                np.savetxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer, attr_class), attr)
            else:
                attr = np.loadtxt(
                    save_directory +
                    "/{}_{}_{}.txt".format(flag1, layer, attr_class)).astype(
                        np.float32)

            # arg_attr = attr.argsort()[::-1][:]
            # shap_attr_trans = np.transpose(shap_attr, (2, 0, 1))
            # acts_squeeze_trans = np.transpose(acts_squeeze, (2, 0, 1))
            '''
      # # Use it for debug the attribution maps
      # sort_AMs_idx_b2s = np.argsort(-attr)
      # sort_AMs_idx_s2b = np.argsort(attr)
      # for i_sort_AMs in range(20):
      #   if i_sort_AMs < 10:
      #     AM_backup_idx = sort_AMs_idx_b2s[i_sort_AMs]
      #     print("big shap value: {:+.3f} in channel {} of all {}"
      #           .format(attr[AM_backup_idx], AM_backup_idx, acts.shape[-1]))
      #     print("    for class: {}, image No:{}"
      #           .format(attr_class, i_sort_AMs))
      #   else:
      #     AM_backup_idx = sort_AMs_idx_s2b[i_sort_AMs-10]
      #     print("small shap value: {:+.3f} in channel {} of all {}"
      #           .format(attr[AM_backup_idx], AM_backup_idx, acts.shape[-1]))
      #     print("    for class: {}, image No:{}"
      #           .format(attr_class, i_sort_AMs-10))
      #   AM_backup = acts[..., AM_backup_idx]
      #   AM_backup = AM_backup.reshape([AM_backup.shape[-1], AM_backup.shape[-1]])
      #   AM_backup = resize(AM_backup, (model.image_shape[0], model.image_shape[1]), order=1,
      #                            mode='constant', anti_aliasing=False)
      #   AM_backup = AM_backup / AM_backup.max() * 255
      #   resize_show(AM_backup, xi=img)
      # kept_channel_idx = np.squeeze(np.argwhere(attr > 0))
      '''

            kept_channel_idx = np.squeeze(
                np.argwhere(
                    attr > np.nanmean(np.where(attr > 0, attr, np.nan))))
            acts_squeeze = np.squeeze(acts)
            attr_temp = np.squeeze(attr).astype(np.float32)
            # print(np.count_nonzero(clear_channel_idx))
            channel_attr_list[i_wanted_layer] = attr_temp
            AM_T[i_wanted_layer] = acts_squeeze[..., kept_channel_idx]
            kept_channel_list[i_wanted_layer] = kept_channel_idx

            kept_channel_idx = np.squeeze(
                np.argwhere(
                    attr < np.nanmean(np.where(attr < 0, attr, np.nan))))
            AM_T_reverse[i_wanted_layer] = acts_squeeze[..., kept_channel_idx]
            kept_channel_list_reverse[i_wanted_layer] = kept_channel_idx
            # test_AM = acts_squeeze * clear_channel_idx * attr_temp
            # test_AM = np.sum(np.transpose(test_AM, (2, 0, 1)), axis=0)
            # acts_squeeze_trans = np.transpose(AM_T[i_wanted_layer], (2, 0, 1))
            # acts_squeeze_trans_sum = np.sum(acts_squeeze_trans, axis=0)

        AM_list = AM_T
        logit_list = sess.run([logit])[0]
        return [AM_list, AM_T_reverse], logit_list, channel_attr_list, \
               [kept_channel_list, kept_channel_list_reverse]