Machine Learning Visual model with 95% accuracy predicts new data the same label

[confusion matrix (https://i.sstatic.net/WiTyUOew.png)]

model performance (validation and training testing acc) (https://i.sstatic.net/r8AK1wkZ.png)

here are all the dataset distributions (https://i.sstatic.net/LhBXJeTd.png)](https://i.sstatic.net/mLpB7vDs.png)(https://i.sstatic.net/IYvPpRzW.png)

Sorry I am relatively new to coding in general so I apologize if I misspeak.

So I attached the performance metrics of the model including validation and testing accuracy. It seemed to do pretty well. It reads Brain MRI scans and predicts among 3 different types of tumors or no tumor (healthy brain) — so 4 categories in total.

I got 24 new images (6 per category) and used the predict function…the model guessed them all to be the same label (pituatary tumor) leading to an accuracy of 25%.

My datasets are relatively balanced Ill post them as images.

What might be happening here and is there anything I can do to fix it?

I’ll paste the code below.

from google.colab import drive
import numpy as np
from PIL import Image
import os
import random
import tensorflow as tf
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Conv2D, MaxPooling2D, Flatten, Dense
from tensorflow.keras.utils import to_categorical
from tensorflow.keras.regularizers import l2
from tensorflow.keras.layers import Dropout
import matplotlib.pyplot as plt
#from tensorflow.keras.preprocessing.image import ImageDataGenerator
from tensorflow.keras.callbacks import EarlyStopping, ReduceLROnPlateau

# Mount Google Drive
drive.mount('/content/drive')

# Define the data folder path
data_folder = '/content/drive/My Drive/mldata/data'

from skimage.transform import resize

# Function to load images and labels with dynamic resizing and width filtering
def load_images_and_labels(data_folder, target_size, width_range):
images = []
labels = []
class_names = os.listdir(data_folder)  # Get class names from folder names
for label, class_name in enumerate(class_names):
    class_folder = os.path.join(data_folder, class_name)
    for filename in os.listdir(class_folder):
        img_path = os.path.join(class_folder, filename)
        img = Image.open(img_path)
        img = img.convert('L')  # Convert to grayscale if needed
        img_width, img_height = img.size
        if img_width >= width_range[0] and img_width <= width_range[1]:  # Filter by width range
            img_array = np.array(img)  # Convert PIL Image to NumPy array
            img_resized = resize(img_array, target_size, anti_aliasing=True)  # Dynamic resizing while preserving aspect ratio
            images.append(img_resized)
            labels.append(label)
return np.array(images), np.array(labels), class_names

# Define the target size for resizing
target_size = (512, 512)  # or (480, 480)

# Define the width range for filtering
width_range = (420, 540)

# Load images and labels with dynamic resizing and width filtering
images, labels, class_names = load_images_and_labels(data_folder, target_size, width_range)

# Normalize pixel values to [0, 1]
images = images / 255.0

# Add a channel dimension to the image arrays
images = np.expand_dims(images, axis=-1)

# Shuffle the dataset
indices = np.arange(images.shape[0])
np.random.shuffle(indices)
images = images[indices]
labels = labels[indices]

# Define the split sizes
train_size = int(len(images) * 0.7)
val_size = int(len(images) * 0.2)
test_size = len(images) - train_size - val_size

# Split the dataset
train_images = images[:train_size]
train_labels = labels[:train_size]
val_images = images[train_size:train_size+val_size]
val_labels = labels[train_size:train_size+val_size]
test_images = images[train_size+val_size:]
test_labels = labels[train_size+val_size:]

# Convert labels to one-hot encoding
train_labels = to_categorical(train_labels, num_classes=len(class_names))
val_labels = to_categorical(val_labels, num_classes=len(class_names))
test_labels = to_categorical(test_labels, num_classes=len(class_names))



from tensorflow.keras.layers import BatchNormalization

model = Sequential([
Conv2D(32, (3, 3), activation='relu', input_shape=(512, 512, 1), kernel_regularizer=l2(0.001)),
BatchNormalization(),
MaxPooling2D((2, 2)),
Conv2D(64, (3, 3), activation='relu', kernel_regularizer=l2(0.001)),
BatchNormalization(),
MaxPooling2D((2, 2)),
Conv2D(128, (3, 3), activation='relu', kernel_regularizer=l2(0.001)),
BatchNormalization(),
MaxPooling2D((2, 2)),
Flatten(),
Dense(128, activation='relu', kernel_regularizer=l2(0.001)),
BatchNormalization(),
Dropout(0.5),
Dense(len(class_names), activation='softmax')
])

# Compile the model
model.compile(optimizer='adam',
          loss='categorical_crossentropy',
          metrics=['accuracy'])

from tensorflow.keras.callbacks import ReduceLROnPlateau

lr_reduction = ReduceLROnPlateau(monitor='val_loss',
                             patience=3,
                             verbose=1,
                             factor=0.5,
                             min_lr=0.00001)

from tensorflow.keras.callbacks import EarlyStopping

# Early stopping callback
early_stopping = EarlyStopping(
monitor='val_accuracy',  # Monitor validation accuracy
patience=10,             # Number of epochs with no improvement after which training will be stopped
verbose=1,               # Verbosity mode
restore_best_weights=True  # Restore model weights from the epoch with the best value of the monitored quantity
)

from tensorflow.keras.callbacks import ModelCheckpoint

checkpoint = ModelCheckpoint('/content/drive/My Drive/RadiologyTumorModelUSF2_checkpoint.h5',         save_best_only=True, monitor='val_loss', mode='min')


# Update the model.fit() call to include the early stopping callback
history = model.fit(
train_images, train_labels,  # Pass training images and labels separately
batch_size=16,               # Specify batch_size separately
epochs=100,                  # Start with a high number and let early stopping decide
validation_data=(val_images, val_labels),
callbacks=[lr_reduction, early_stopping, checkpoint]  # Add callbacks
)

model_path = '/content/drive/My Drive/RadiologyTumorModelUSF2.h5'

# Save the model
model.save(model_path)

print("Model saved successfully at:", model_path)

# Evaluate the model on the validation set
val_loss, val_accuracy = model.evaluate(val_images, val_labels, verbose=2)
print(f"Validation Accuracy: {val_accuracy}")

# Evaluate the model on the test set
test_loss, test_accuracy = model.evaluate(test_images, test_labels, verbose=2)
print(f"Test Accuracy: {test_accuracy}")

I thought it was due to the discrepency between quality of pictures at first due to variations in pixel width and resizing so I tried revising and retraining my model using img_resized = resize(img_array, target_size, anti_aliasing=True) # Dynamic resizing while preserving aspect ratio

since most of my training data was between 420-540 px width and my new testing images were originally 512×512 or 630×630

New contributor

Alex Huang is a new contributor to this site. Take care in asking for clarification, commenting, and answering.
Check out our Code of Conduct.

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa
Thiết kế website Thiết kế website Thiết kế website Cách kháng tài khoản quảng cáo Mua bán Fanpage Facebook Dịch vụ SEO Tổ chức sinh nhật