def predict_ensemble(): """Predicts and saves the predictions from the ensemble""" # Import models ENSEMBLE_SAVE_NAME = 'small_net' # Name that the ensemble models will be saved with DATASET_NAME = 'spiral' # Name of dataset models were trained with AUX_DATASET_NAME = "spiral_aux" ensemble_model_names = saveload.get_ensemble_model_names() model_names = ensemble_model_names[ENSEMBLE_SAVE_NAME][DATASET_NAME] wrapped_models = [ models.ensemble.KerasLoadsWhole(name) for name in model_names ] # Build ensemble ensemble = models.ensemble.Ensemble(wrapped_models) print(ensemble) # Load data (x_train, y_train), (x_test, y_test) = datasets.get_dataset(DATASET_NAME) (x_aux, y_aux), (_, _) = datasets.get_dataset(AUX_DATASET_NAME) x_train_aux = np.concatenate((x_train, x_aux), axis=0) y_train_aux = np.concatenate((y_train, y_aux), axis=0) x_train_aux_20 = np.concatenate((x_train, x_aux[:20]), axis=0) y_train_aux_20 = np.concatenate((y_train, y_aux[:20]), axis=0) grid = get_grid(size=2000, steps=1000) # Predict with ensemble ensemble_logits_train_aux = ensemble.predict(x_train_aux) ensemble_logits_train_aux_20 = ensemble.predict(x_train_aux_20) ensemble_logits_train = ensemble.predict(x_train) ensemble_logits_test = ensemble.predict(x_test) ensemble_logits_grid = ensemble.predict(grid) # Save to file with open('train_aux_small_net_spiral.pkl', 'wb') as file: pickle.dump((x_train_aux, y_train_aux, ensemble_logits_train_aux), file) with open('train_aux_20_small_net_spiral.pkl', 'wb') as file: pickle.dump( (x_train_aux_20, y_train_aux_20, ensemble_logits_train_aux_20), file) with open('train_small_net_spiral.pkl', 'wb') as file: pickle.dump((x_train, y_train, ensemble_logits_train), file) with open('test_small_net_spiral.pkl', 'wb') as file: pickle.dump((x_test, y_test, ensemble_logits_test), file) with open('grid_small_net_spiral_1000.pkl', 'wb') as file: pickle.dump((grid, 0, ensemble_logits_grid), file, protocol=4)
def generate_figure_2(): ''' Reproduces the Figure 2 in Malinin (2020)''' (x_train, y_train), _ = datasets.get_dataset("spiral") (x_aux, y_aux), (_, _) = datasets.get_dataset("spiral_aux") x_train_aux = np.concatenate((x_train, x_aux), axis=0) y_train_aux = np.concatenate((y_train, y_aux), axis=0) plot_dataset(x_train, y_train, aux=False, filename="plots/" + str(i) + "/2a.png") plot_dataset(x_train_aux, y_train_aux, aux=True, filename="plots/" + str(i) + "/2b.png")
def plot_decision_boundary(): """Plots a decision boundary using the grid.""" # Load data with open('grid_small_net_spiral_1000.pkl', 'rb') as file: x_grid, _, ensemble_logits_grid = pickle.load(file) grid_size = int(np.sqrt(x_grid.shape[0])) (x_train, y_train), _ = datasets.get_dataset("spiral") # For ensemble prediction_grid = np.reshape( np.argmax(np.mean(ensemble_logits_grid, axis=0), axis=1), (grid_size, grid_size)) # Without ensemble #prediction_grid = np.reshape(np.argmax(ensemble_logits_grid, axis = 1), (grid_size, grid_size)) # Plot decision boundary fig, ax = plt.subplots(figsize=(5, 5)) im = ax.imshow(prediction_grid, extent=(-2000, 2000, -2000, 2000), origin='lower') fig.colorbar(im) colors = { 0: (245 / 255, 113 / 255, 137 / 255), 1: (80 / 255, 174 / 255, 50 / 255), 2: (59 / 255, 161 / 255, 234 / 255), -1: (254 / 255, 203 / 255, 82 / 255) } for i in range(3): idx = np.where(y_train == i) sns.scatterplot(x_train[idx, 0].flatten(), x_train[idx, 1].flatten(), marker="s", s=20, alpha=0.35, color=colors[i], ax=ax) ax.set_xlim((-500, 500)) ax.set_ylim((-500, 500)) plt.show()
def train_models(): '''Trains an ensemble of models on the spiral dataset.''' MODEL_TYPE = "small_net" ENSEMBLE_SAVE_NAME = "small_net" DATASET_NAME = "spiral" NAME_START_NUMBER = 0 N_MODELS = 100 N_EPOCHS = 85 # Import data (x_train, y_train), (x_test, y_test) = datasets.get_dataset(DATASET_NAME) y_train_one_hot = tf.one_hot(y_train.reshape((-1, )), settings.DATASET_N_CLASSES[DATASET_NAME]) y_test_one_hot = tf.one_hot(y_test.reshape((-1, )), settings.DATASET_N_CLASSES[DATASET_NAME]) # Train models model_module = settings.MODEL_MODULES[MODEL_TYPE] saved_model_names = [] try: for i in range(N_MODELS): # Get model model = model_module.get_model(dataset_name=DATASET_NAME, compile=True) # Train model model.fit(x_train, y_train_one_hot, validation_data=(x_test, y_test_one_hot), epochs=N_EPOCHS, verbose=2) print("Model {} finished training.".format(i)) # Save model model_name = "{}_{}_{}".format(ENSEMBLE_SAVE_NAME, DATASET_NAME, i) saveload.save_tf_model(model, model_name) saved_model_names.append(model_name) finally: append_model_names = NAME_START_NUMBER > 0 saveload.update_ensemble_names(ENSEMBLE_SAVE_NAME, DATASET_NAME, saved_model_names, append=append_model_names)
def get_dataset(dataset_name, normalization): # Load dataset (train_images, train_labels), (test_images, test_labels) = datasets.get_dataset(dataset_name) # Normalize data if normalization == "-1to1": train_images, min, max = preprocessing.normalize_minus_one_to_one( train_images) test_images = preprocessing.normalize_minus_one_to_one( test_images, min, max) elif normalization == 'gaussian': train_images, mean, std = preprocessing.normalize_gaussian( train_images) test_images = preprocessing.normalize_gaussian(test_images, mean, std) return (train_images, train_labels), (test_images, test_labels)
def train_end(): """Trains an END and and END_AUX model on the ensemble predictions""" # Name ENSEMBLE_SAVE_NAME = 'small_net' # Name that the ensemble models will be saved with DATASET_NAME = 'spiral' # Name of dataset models were trained with MODEL_SAVE_NAME = "end_small_net_spiral" MODEL_SAVE_NAME_AUX = "end_AUX_small_net_spiral" # Load data with open('train_small_net_spiral.pkl', 'rb') as file: x_train, y_train, ensemble_logits_train = pickle.load(file) with open('train_aux_small_net_spiral.pkl', 'rb') as file: x_train_aux, y_train_aux, ensemble_logits_train_aux = pickle.load(file) # Build ENDD model base_model = get_model(DATASET_NAME, compile=False) end_model = end.get_model(base_model, init_temp=1) base_model_AUX = get_model(DATASET_NAME, compile=False) end_model_AUX = end.get_model(base_model_AUX, init_temp=1) # Train model end_model.fit(x_train, np.transpose(ensemble_logits_train, (1, 0, 2)), epochs=150) end_model_AUX.fit(x_train_aux, np.transpose(ensemble_logits_train_aux, (1, 0, 2)), epochs=500) # Save model saveload.save_tf_model(end_model, MODEL_SAVE_NAME) saveload.save_tf_model(end_model_AUX, MODEL_SAVE_NAME_AUX) # Evaluate model _, (x_test, y_test) = datasets.get_dataset("spiral") logits = end_model.predict(x_test) logits_aux = end_model_AUX.predict(x_test) print(np.argmax(logits, axis=1)) print(np.argmax(logits_aux, axis=1)) print(y_test) print(sklearn.metrics.accuracy_score(y_test, np.argmax(logits, axis=1))) print(sklearn.metrics.accuracy_score(y_test, np.argmax(logits_aux, axis=1)))
def predict_endd(): """Predicts and saves the predictions of the ENDD-models to file""" # Load model MODEL_SAVE_NAMES = [ "endd_small_net_spiral", "endd_AUX_small_net_spiral", "endd_AUX_20_small_net_spiral", "endd_AUX_ANN_small_net_spiral", "endd_AUX_T25_small_net_spiral" ] PREDICT_SAVE_NAMES = [ "endd", "endd_AUX", "endd_AUX_20", "endd_AUX_ANN", "endd_AUX_T25" ] # Loop for aux or no aux for i in range(len(MODEL_SAVE_NAMES)): print(i) MODEL_SAVE_NAME = MODEL_SAVE_NAMES[i] PREDICT_SAVE_NAME = PREDICT_SAVE_NAMES[i] endd_model = saveload.load_tf_model(MODEL_SAVE_NAME, compile=False) endd_model = endd.get_model(endd_model, init_temp=1, teacher_epsilon=1e-4) # Load data (x_train, y_train), (x_test, y_test) = datasets.get_dataset("spiral") grid = get_grid(size=2000, steps=1000) # Predict endd_logits_train = endd_model.predict(x_train) endd_logits_test = endd_model.predict(x_test) endd_logits_grid = endd_model.predict(grid) with open('train_small_net_spiral_{}.pkl'.format(PREDICT_SAVE_NAME), 'wb') as file: pickle.dump((x_train, y_train, endd_logits_train), file) with open('test_small_net_spiral_{}.pkl'.format(PREDICT_SAVE_NAME), 'wb') as file: pickle.dump((x_test, y_test, endd_logits_test), file) with open('grid_small_net_spiral_{}.pkl'.format(PREDICT_SAVE_NAME), 'wb') as file: pickle.dump((grid, 0, endd_logits_grid), file)
def fetch_dataset(self): (self.x_train, self.x_test) = get_dataset(self.dataset_key)
ENSEMBLE_NAME = 'basic_cnn' DATASET_NAME = 'cifar10' # Load ensemble model ensemble_model_names = saveload.get_ensemble_model_names() model_names = ensemble_model_names[ENSEMBLE_NAME][DATASET_NAME][:3] models = [ensemble.KerasLoadsWhole(name) for name in model_names] ensm = ensemble.Ensemble(models) ensm_wrapper_type = 'ensemble' # Load individual model ind = saveload.load_tf_model(model_names[0]) ind_wrapper_type = 'individual' # Load data _, (test_images, test_labels) = datasets.get_dataset(DATASET_NAME) # Preprocess data test_labels = test_labels.reshape(-1) # Calculate measures ensm_measures = evaluation.calc_classification_measures( ensm, test_images, test_labels, wrapper_type=ensm_wrapper_type) ind_measures = evaluation.calc_classification_measures( ind, test_images, test_labels, wrapper_type=ind_wrapper_type) # Format and print results summary = evaluation.format_results(['ENSM', 'IND'], [ensm_measures, ind_measures]) print(summary)
plt.subplot(gs1[i]) plot_img(img) ensm_prediction = ensm_predictions[:, index, :] plt.subplot(gs1[i + n_cols]) plot_points(ensm_prediction) endd_prediction = endd_predictions[index, :] plt.subplot(gs1[i + 2 * n_cols]) plot_pdf(endd_prediction) # ======== PREPARE IMAGES ========= # Load test images (_, _), (test_images, test_labels) = datasets.get_dataset(DATASET_NAME) raw_test_images = test_images test_images = preprocessing.normalize_minus_one_to_one(test_images, min=0, max=255) (aux_images, _), (_, _) = datasets.get_dataset('cifar100') aux_images = preprocessing.normalize_minus_one_to_one(aux_images, min=0, max=255) noise_img = np.random.randn(1, 32, 32, 3) # ======== PREDICTIONS ========= if LOAD_PREVIOUS_ENSM_PREDS:
from torch.utils.data import Dataset from utils.datasets import get_dataset import torch from utils.calibration import calibrate from torch.nn import functional as F from ignite.engine import Engine from utils.model import Model, Model2 from utils.draw_picture import draw_loss, draw_two from utils.ECE import ece_score import xlsxwriter workbook = xlsxwriter.Workbook('data.xlsx') worksheet = workbook.add_worksheet() train_dataset, test_dataset, val_dataset = get_dataset() # get dataset num_classes = 10 epoch = 300 def train_model(learning_rate, scale, bins, la): model = Model() model2 = Model2() sf = torch.nn.Softmax(dim=1) device = torch.device("cuda:3" if torch.cuda.is_available() else "cpu") model.to(device) model2.to(device) optimizer = torch.optim.Adam( model.parameters(), lr=learning_rate, weight_decay=1e-4 )
TEMP_ANNEALING = True ONE_CYCLE_LR_POLICY = True CYCLE_LENGTH = 60 # (90) INIT_LR = 0.001 # (0.001) DROPOUT_RATE = 0.3 # (0.3) INIT_TEMP = 10 # (10) SAMPLE_ENSEMBLE_MODELS = False if SAMPLE_ENSEMBLE_MODELS: MODEL_BASE_SAVE_NAME += "_sampled" for nr_repetition in range(3, repetitions): # Load dataset (train_images, train_labels), (test_images, test_labels) = datasets.get_dataset(DATASET_NAME) if AUX_DATASET_NAME: (aux_images, _), _ = datasets.get_dataset(AUX_DATASET_NAME) train_images = np.concatenate((train_images, aux_images), axis=0) # Normalize data if NORMALIZATION == "-1to1": train_images, min, max = preprocessing.normalize_minus_one_to_one( train_images) test_images = preprocessing.normalize_minus_one_to_one( test_images, min, max) elif NORMALIZATION == 'gaussian': train_images, mean, std = preprocessing.normalize_gaussian( train_images) test_images = preprocessing.normalize_gaussian(test_images, mean, std)
def train_endd(): """Trains an ENDD and and ENDD_AUX model on the ensemble predictions""" # Name ENSEMBLE_SAVE_NAME = 'small_net' # Name that the ensemble models will be saved with DATASET_NAME = 'spiral' # Name of dataset models were trained with MODEL_SAVE_NAME = "endd_small_net_spiral" MODEL_SAVE_NAME_AUX = "endd_AUX_small_net_spiral" MODEL_SAVE_NAME_AUX_20 = "endd_AUX_20_small_net_spiral" MODEL_SAVE_NAME_AUX_ANN = "endd_AUX_ANN_small_net_spiral" MODEL_SAVE_NAME_AUX_T25 = "endd_AUX_T25_small_net_spiral" # Load data with open('train_small_net_spiral.pkl', 'rb') as file: x_train, y_train, ensemble_logits_train = pickle.load(file) with open('train_aux_small_net_spiral.pkl', 'rb') as file: x_train_aux, y_train_aux, ensemble_logits_train_aux = pickle.load(file) with open('train_aux_20_small_net_spiral.pkl', 'rb') as file: x_train_aux_20, y_train_aux_20, ensemble_logits_train_aux_20 = pickle.load( file) # Build ENDD model base_model = get_model(DATASET_NAME, compile=False) endd_model = endd.get_model(base_model, init_temp=1, teacher_epsilon=1e-4) base_model_AUX = get_model(DATASET_NAME, compile=False) base_model_AUX_20 = get_model(DATASET_NAME, compile=False) base_model_AUX_ANN = get_model(DATASET_NAME, compile=False) base_model_AUX_T25 = get_model(DATASET_NAME, compile=False) endd_model_AUX = endd.get_model(base_model_AUX, init_temp=1, teacher_epsilon=1e-4) endd_model_AUX_20 = endd.get_model(base_model_AUX_20, init_temp=1, teacher_epsilon=1e-4) endd_model_AUX_ANN = endd.get_model(base_model_AUX_ANN, init_temp=2.5, teacher_epsilon=1e-4) endd_model_AUX_T25 = endd.get_model(base_model_AUX_T25, init_temp=2.5, teacher_epsilon=1e-4) # Train model #endd_model.fit(x_train, np.transpose(ensemble_logits_train, (1, 0, 2)), epochs=500) #endd_model_AUX.fit(x_train_aux, np.transpose(ensemble_logits_train_aux, (1, 0, 2)), epochs=500) #endd_model_AUX_20.fit(x_train_aux_20, np.transpose(ensemble_logits_train_aux_20, (1, 0, 2)), epochs=500) endd_model_AUX_ANN.fit(x_train_aux, np.transpose(ensemble_logits_train_aux, (1, 0, 2)), epochs=500, callbacks=[ callbacks.TemperatureAnnealing(init_temp=2.5, cycle_length=400, epochs=500) ]) endd_model_AUX_T25.fit(x_train_aux, np.transpose(ensemble_logits_train_aux, (1, 0, 2)), epochs=500) # Save model saveload.save_tf_model(endd_model, MODEL_SAVE_NAME) saveload.save_tf_model(endd_model_AUX, MODEL_SAVE_NAME_AUX) saveload.save_tf_model(endd_model_AUX_20, MODEL_SAVE_NAME_AUX_20) saveload.save_tf_model(endd_model_AUX_ANN, MODEL_SAVE_NAME_AUX_ANN) saveload.save_tf_model(endd_model_AUX_T25, MODEL_SAVE_NAME_AUX_T25) # Evaluate model _, (x_test, y_test) = datasets.get_dataset("spiral") logits = endd_model_AUX.predict(x_test) print(np.argmax(logits, axis=1)) print(y_test) print(sklearn.metrics.accuracy_score(y_test, np.argmax(logits, axis=1)))
gibson_data = opt.gibson_data result_path = opt.result_path room_path = opt.room_path other_path = opt.other_path voxel_size = opt.voxel_size override = opt.override temp_path = os.path.join( result_path, model, 'scene_graph') # system path to store intermediary results export_path = os.path.join( result_path, '3D_Scene_Graphs' ) # system path to export final 3D scene graph results mesh_path = os.path.join( result_path, model, mesh_folder, 'mview_results.npz') # system path to multi-view consistency results cat2ind, ind2cat = get_dataset( ) # mapping of object categories (string) to unique ID, and vice-versa if os.path.exists(mesh_path): if not os.path.exists(temp_path): os.makedirs(temp_path) if not os.path.exists(export_path): os.makedirs(export_path) ## calculate all layers, nodes, and attributes building = load_attributes(temp_path, mesh_path, gibson_data, other_path, room_path, model, model_id, voxel_size,
checkpoint.scheduler.step() checkpoint.save() if __name__ == '__main__': arguments = parse_arguments() torch.manual_seed(arguments.seed) np.random.seed(arguments.seed) if arguments.fix_a is None and arguments.reg_type == "swd" and arguments.pruning_iterations != 1: print('Progressive a is not compatible with iterative pruning') raise ValueError if arguments.no_ft and arguments.pruning_iterations != 1: print("You can't specify a pruning_iteration value if there is no fine-tuning at all") raise ValueError get_mask = get_mask_function(arguments.pruning_type) _dataset = get_dataset(arguments) _targets = [int((n + 1) * (arguments.target / arguments.pruning_iterations)) for n in range(arguments.pruning_iterations)] # Train model print('Train model !') print(f'Regularization with t-{_targets[0]}') training_model = Checkpoint(arguments, 'training') training_model.regularization = Regularization(None, _targets[0], arguments) training_model.load() train_model(training_model, arguments, [0, arguments.epochs], _dataset, None, soft_pruning=arguments.soft_pruning) if arguments.lr_rewinding: training_model.rewind_lr()
import models.ensemble from utils import datasets from utils import saveload # Need these settings for GPU to work on my computer /Einar import tensorflow as tf physical_devices = tf.config.experimental.list_physical_devices('GPU') tf.config.experimental.set_memory_growth(physical_devices[0], True) # Example usage if __name__ == "__main__": # Fetch and wrap previously trained ensemble models ensemble_model_names = saveload.get_ensemble_model_names() model_names = ensemble_model_names[ENSEMBLE_SAVE_NAME][DATASET_NAME] wrapped_models = [ models.ensemble.KerasLoadsWhole(name) for name in model_names ] # Build ensemble ensemble = models.ensemble.Ensemble(wrapped_models) # Load data (train_images, train_labels), (test_images, test_labels) = datasets.get_dataset(DATASET_NAME) # Predict with ensemble ensemble_preds = ensemble.predict(test_images) print("Ensemble preds shape: {}".format(ensemble_preds.shape))
def train_val_test(): """train and val""" # seed set_random_seed() # model model = get_model() model_wrapper = torch.nn.DataParallel(model).cuda() criterion = torch.nn.CrossEntropyLoss().cuda() train_loader, val_loader = get_dataset() # check pretrained if FLAGS.pretrained: checkpoint = torch.load(FLAGS.pretrained) # update keys from external models if type(checkpoint) == dict and 'model' in checkpoint: checkpoint = checkpoint['model'] new_keys = list(model_wrapper.state_dict().keys()) old_keys = list(checkpoint.keys()) new_keys = [key for key in new_keys if 'running' not in key] new_keys = [key for key in new_keys if 'tracked' not in key] old_keys = [key for key in old_keys if 'running' not in key] old_keys = [key for key in old_keys if 'tracked' not in key] if not FLAGS.test_only: old_keys = old_keys[:-2] new_keys = new_keys[:-2] new_checkpoint = {} for key_new, key_old in zip(new_keys, old_keys): new_checkpoint[key_new] = checkpoint[key_old] model_wrapper.load_state_dict(new_checkpoint, strict=False) print('Loaded model {}.'.format(FLAGS.pretrained)) optimizer = get_optimizer(model_wrapper) # check resume training if FLAGS.resume: checkpoint = torch.load(FLAGS.resume) model_wrapper.load_state_dict(checkpoint['model']) optimizer.load_state_dict(checkpoint['optimizer']) last_epoch = checkpoint['last_epoch'] lr_scheduler = torch.optim.lr_scheduler.CosineAnnealingLR(optimizer, len(train_loader)*FLAGS.num_epochs) lr_scheduler.last_epoch = last_epoch print('Loaded checkpoint {} at epoch {}.'.format( FLAGS.resume, last_epoch)) else: lr_scheduler = torch.optim.lr_scheduler.CosineAnnealingLR(optimizer, len(train_loader)*FLAGS.num_epochs) last_epoch = lr_scheduler.last_epoch # print model and do profiling print(model_wrapper) if FLAGS.profiling: if 'gpu' in FLAGS.profiling: profiling(model, use_cuda=True) if 'cpu' in FLAGS.profiling: profiling(model, use_cuda=False) if FLAGS.test_only: logger.info('Start testing.') test(last_epoch, val_loader, model_wrapper, criterion, train_loader) return logger.info('Start training.') for epoch in range(last_epoch + 1, FLAGS.num_epochs): # train train(epoch, train_loader, model_wrapper, criterion, optimizer, lr_scheduler) # val validate(epoch, val_loader, model_wrapper, criterion, train_loader) # lr_scheduler.step() torch.save( { 'model': model_wrapper.state_dict(), 'optimizer': optimizer.state_dict(), 'last_epoch': epoch, }, os.path.join(saved_path, 'checkpoint_{}.pt'.format(epoch))) return
# dataset_name=DATASET_NAME, # compile=True, # weights=ENDD_AUX_MODEL_NAME) # endd_aux_tot_wrapper_type = 'individual' # endd_aux_know_wrapper_type = 'priornet' # Prepare PN+AUX model pn_base_model = saveload.load_tf_model(PN_AUX_MODEL_NAME, compile=False) pn_aux_model = cnn_priorNet.get_model(pn_base_model, dataset_name=DATASET_NAME, compile=True) pn_aux_tot_wrapper_type = 'individual' pn_aux_know_wrapper_type = 'priornet' # Load data _, (in_images, _) = datasets.get_dataset(DATASET_NAME) _, out_images = datasets.get_dataset(OUT_DATASET_NAME) # Preprocess data in_images = preprocessing.normalize_minus_one_to_one(in_images, min=0, max=255) out_images = preprocessing.normalize_minus_one_to_one(out_images, min=0, max=255) # # Calculate measures # print("Evaluating IND...") # ind_measures = evaluation.calc_ood_measures(ind_model, # in_images, # out_images, # tot_wrapper_type=ind_tot_wrapper_type, # know_wrapper_type=ind_know_wrapper_type)
architecture=runner.Architecture.VANILLA, prior_configuration=runner.PriorConfiguration.SG, n_epochs=2, root="../exports") runner_instance.reload_existing_model() # %% import matplotlib.pyplot as plt model = runner_instance.model prior = model.get_prior() encoder = model.get_encoder() decoder = model.get_decoder() generated_img = decoder(prior.sample(1)).mean() plt.imshow(generated_img[0]) # %% import sys sys.path.append('../') import utils.datasets as data calt = data.get_dataset(data.DatasetKey.CALTECH) calt['X'].shape np.reshape(calt['X'], (-1, 28, 28)).shape # %% import numpy as np calt['X'].shape plt.imshow(calt['X'][np.random.randint(5000)].reshape(28, 28), cmap="Greys") # %% np.random.randint(52000) # %% plt.imshow(runner_instance.x_train[4])