import tensorflow as tf
import numpy as np
import matplotlib.pyplot as plt
from tensorflow.keras.models import Model
from tensorflow.keras.preprocessing import image
def grad_cam(model, img_array, last_conv_layer_name, pred_index=None):
"""
Generate a Grad-CAM heatmap for a given image.
Args:
- model: The trained model
- img_array: The image to be processed (numpy array)
- last_conv_layer_name: Name of the last convolutional layer for Grad-CAM
- pred_index: Index of the predicted class (optional)
Returns:
- A heatmap that highlights important areas of the image
"""
# Ensure the model is in inference mode
model = model if isinstance(model, tf.keras.Model) else model.model
# Convert img_array to tensor if needed and add batch dimension
img_array = np.expand_dims(img_array, axis=0)
# Retrieve the last convolutional layer
last_conv_layer = model.get_layer('resnet50').get_layer(last_conv_layer_name)
# Create a model that outputs the last convolutional layer and the final predictions
grad_model = Model(
inputs=[model.get_layer('resnet50').input],
outputs=[last_conv_layer.output, model.get_layer('dense_out').output]
)
with tf.GradientTape() as tape:
# Record the forward pass
conv_outputs, predictions = grad_model(img_array)
# If pred_index is None, use the predicted class index
if pred_index is None:
pred_index = tf.argmax(predictions[0])
# Compute the gradient of the predicted class (class index) with respect to the last convolutional layer
loss = predictions[:, pred_index]
# Compute the gradient of the loss with respect to the convolutional layer outputs
grads = tape.gradient(loss, conv_outputs)
# Average the gradients across all the axes of the feature maps to get the importance of each channel
pooled_grads = tf.reduce_mean(grads, axis=(0, 1, 2))
# Multiply each channel in the feature map by the corresponding pooled gradient
conv_outputs = conv_outputs[0]
for i in range(conv_outputs.shape[-1]):
conv_outputs[:, :, i] *= pooled_grads[i]
# Average the feature maps along the channels axis to get a 2D heatmap
heatmap = np.mean(conv_outputs, axis=-1)
# Normalize the heatmap to a range [0, 1]
heatmap = np.maximum(heatmap, 0)
heatmap /= np.max(heatmap)
# Return the heatmap
return heatmap
def display_grad_cam(img_array, heatmap, alpha=0.4):
"""
Display the Grad-CAM heatmap overlaid on the original image.
Args:
- img_array: The original image (numpy array)
- heatmap: The Grad-CAM heatmap
- alpha: Transparency level for overlaying the heatmap
Returns:
- None, but displays the image with Grad-CAM overlay
"""
# Resize heatmap to match the size of the original image
heatmap = np.uint8(255 * heatmap)
heatmap = tf.image.resize(heatmap, (img_array.shape[0], img_array.shape[1]))
heatmap = np.array(heatmap)
# Load the image into a format that can be plotted
img = image.array_to_img(img_array[0])
# Display the image with the heatmap overlay
plt.imshow(img)
plt.imshow(heatmap, cmap='jet', alpha=alpha) # Jet colormap for better visibility
plt.axis('off')
plt.show()
# Usage example:
# Assuming `model` is your trained `CustomResNet` model and `x_test[0]` is an image from your dataset.
# Choose the last convolutional layer name from the ResNet50 model
last_conv_layer_name = "conv5_block3_out" # Change this if necessary based on your model
# Run Grad-CAM
heatmap = grad_cam(model=resnet50_geral_ft, img_array=x_test[0:1], last_conv_layer_name=last_conv_layer_name)
# Display the result
display_grad_cam(x_test[0:1], heatmap)
При запуске я получил ошибку.
ValueError: слой Density_out никогда не вызывался и, следовательно, нет определенного вывода.
Даже после использования фиктивного ввода и вызова сборки. Сводная информация моей модели запускается, но в столбце вывода отображается только ?
Инициализация моей модели следующая:
def call(self, inputs, training=None): x = self.resnet(inputs) print(f"Shape after ResNet: {x.shape}") x = self.flatten(x) print(f"Shape after Flatten: {x.shape}") x = self.drop1(x) x = self.bn1(x) x = self.dense1(x) print(f"Shape after dense1: {x.shape}") x = self.drop2(x) x = self.bn2(x) x = self.dense2(x) print(f"Shape after dense 2: {x.shape}") x = self.dense_out(x) print(f"Shape after dense_out: {x.shape}") return x
def get_config(self): # Include `num_classes` in the config config = super(CustomResNet, self).get_config() # Include base class config config['num_classes'] = self.num_classes return config
@classmethod def from_config(cls, config): # Evita passar o mesmo argumento mais de uma vez return cls(**config)
def build(self, input_shape): self.resnet.build(input_shape) super(CustomResNet, self).build(input_shape) self.built = True [/code] И следующая реализация grad-cam [code]import tensorflow as tf import numpy as np import matplotlib.pyplot as plt from tensorflow.keras.models import Model from tensorflow.keras.preprocessing import image
def grad_cam(model, img_array, last_conv_layer_name, pred_index=None): """ Generate a Grad-CAM heatmap for a given image.
Args: - model: The trained model - img_array: The image to be processed (numpy array) - last_conv_layer_name: Name of the last convolutional layer for Grad-CAM - pred_index: Index of the predicted class (optional)
Returns: - A heatmap that highlights important areas of the image """ # Ensure the model is in inference mode model = model if isinstance(model, tf.keras.Model) else model.model
# Convert img_array to tensor if needed and add batch dimension img_array = np.expand_dims(img_array, axis=0)
# Retrieve the last convolutional layer last_conv_layer = model.get_layer('resnet50').get_layer(last_conv_layer_name)
# Create a model that outputs the last convolutional layer and the final predictions grad_model = Model( inputs=[model.get_layer('resnet50').input], outputs=[last_conv_layer.output, model.get_layer('dense_out').output] )
with tf.GradientTape() as tape: # Record the forward pass conv_outputs, predictions = grad_model(img_array)
# If pred_index is None, use the predicted class index if pred_index is None: pred_index = tf.argmax(predictions[0])
# Compute the gradient of the predicted class (class index) with respect to the last convolutional layer loss = predictions[:, pred_index]
# Compute the gradient of the loss with respect to the convolutional layer outputs grads = tape.gradient(loss, conv_outputs)
# Average the gradients across all the axes of the feature maps to get the importance of each channel pooled_grads = tf.reduce_mean(grads, axis=(0, 1, 2))
# Multiply each channel in the feature map by the corresponding pooled gradient conv_outputs = conv_outputs[0] for i in range(conv_outputs.shape[-1]): conv_outputs[:, :, i] *= pooled_grads[i]
# Average the feature maps along the channels axis to get a 2D heatmap heatmap = np.mean(conv_outputs, axis=-1)
# Normalize the heatmap to a range [0, 1] heatmap = np.maximum(heatmap, 0) heatmap /= np.max(heatmap)
# Return the heatmap return heatmap
def display_grad_cam(img_array, heatmap, alpha=0.4): """ Display the Grad-CAM heatmap overlaid on the original image.
Args: - img_array: The original image (numpy array) - heatmap: The Grad-CAM heatmap - alpha: Transparency level for overlaying the heatmap
Returns: - None, but displays the image with Grad-CAM overlay """ # Resize heatmap to match the size of the original image heatmap = np.uint8(255 * heatmap) heatmap = tf.image.resize(heatmap, (img_array.shape[0], img_array.shape[1])) heatmap = np.array(heatmap)
# Load the image into a format that can be plotted img = image.array_to_img(img_array[0])
# Display the image with the heatmap overlay plt.imshow(img) plt.imshow(heatmap, cmap='jet', alpha=alpha) # Jet colormap for better visibility plt.axis('off') plt.show()
# Usage example: # Assuming `model` is your trained `CustomResNet` model and `x_test[0]` is an image from your dataset. # Choose the last convolutional layer name from the ResNet50 model last_conv_layer_name = "conv5_block3_out" # Change this if necessary based on your model
# Run Grad-CAM heatmap = grad_cam(model=resnet50_geral_ft, img_array=x_test[0:1], last_conv_layer_name=last_conv_layer_name)
# Display the result display_grad_cam(x_test[0:1], heatmap) [/code] При запуске я получил ошибку.
ValueError: слой Density_out никогда не вызывался и, следовательно, нет определенного вывода.
Даже после использования фиктивного ввода и вызова сборки. Сводная информация моей модели запускается, но в столбце вывода отображается только ? Инициализация моей модели следующая: [code]resnet50_geral_ft = CustomResNet(num_classes=14) resnet50_geral_ft.build(input_shape=(None, 100, 75, 3)) resnet50_geral_ft.compile(optimizer = optimizer,loss='categorical_crossentropy', metrics=default_metrics) resnet50_geral_ft = load_model( checkpoint_filepath + "resnet50_geral_ft.keras", custom_objects={'CustomResNet': CustomResNet} ) [/code] Я не могу понять, чего мне здесь не хватает.... кто-нибудь знает?
Я пытаюсь создать ИИ Flappy Bird, используя репозиторий flappy_bird_gym с использованием Tensorflow. Я создал среду, используя conda в WSL2, тензорный поток версии 2.17, с keras-rl2 и keras 3, python 3.10.14.
Но когда я пытаюсь построить свою ошибку...
Я запускаю этот код:
import numpy as np
import keras
import tensorflow as tf
tf.compat.v1.logging.set_verbosity(tf.compat.v1.logging.ERROR)
from keras.models import Sequential, Model
from keras.layers import Conv2D, Activation