测试ResNet预训练模型在ImageNet验证集上的准确率结果
(1) 使用pytorch提供的dataloader来加载数据并测试准确率。
运行命令:
python test_imagenet.py --data [your imagenet validation set path]
test_imagenet.py文件内容
import torch
import torch.nn as nn
import torch.optim as optim
import torch.backends.cudnn as cudnn
import torch.nn.functional as F
import os
import shutil
import argparse
import numpy as np
import torchvision
import torchvision.datasets as datasets
import torchvision.transforms as transforms
import torchvision.models as models
from bisect import bisect_right
import time
import math
parser = argparse.ArgumentParser(description='PyTorch ImageNet Training')
parser.add_argument('--data', default='/dev/shm/ImageNet/val/', type=str, help='trainset directory')
parser.add_argument('--dataset', default='ImageNet', type=str, help='Dataset name')
parser.add_argument('--arch', default='resnet18', type=str, help='network architecture')
parser.add_argument('--batch-size', type=int, default=256, help='batch size')
parser.add_argument('--num-workers', type=int, default=8, help='number workers')
parser.add_argument('--gpu', type=str, default='0')
parser.add_argument('--manual_seed', type=int, default=0)
# global hyperparameter set
args = parser.parse_args()
os.environ["CUDA_VISIBLE_DEVICES"] = args.gpu
np.random.seed(args.manual_seed)
torch.manual_seed(args.manual_seed)
torch.cuda.manual_seed_all(args.manual_seed)
num_classes = 1000
test_set = datasets.ImageFolder(
args.data,
transforms.Compose([
transforms.Resize(256),
transforms.CenterCrop(224),
transforms.ToTensor(),
transforms.Normalize(mean=[0.485, 0.456, 0.406],
std=[0.229, 0.224, 0.225]),
]))
testloader = torch.utils.data.DataLoader(
test_set, batch_size=args.batch_size, shuffle=False,
num_workers=args.num_workers, pin_memory=True)
# --------------------------------------------------------------------------------------------
# Model
print('==> Building model..')
net = models.__dict__[args.arch](pretrained=True).cuda()
cudnn.benchmark = True
def correct_num(output, target, topk=(1,)):
"""Computes the precision@k for the specified values of k"""
maxk = max(topk)
batch_size = target.size(0)
_, pred = output.topk(maxk, 1, True, True)
correct = pred.eq(target.view(-1, 1).expand_as(pred))
res = []
for k in topk:
correct_k = correct[:, :k].float().sum()
res.append(correct_k.item())
return res
net.eval()
correct1 = 0
correct5 = 0
total = 0
sum_time = time.time()
with torch.no_grad():
batch_start_time = time.time()
for batch_idx, (inputs, target) in enumerate(testloader):
inputs, target = inputs.cuda(), target.cuda()
logits = net(inputs)
print('batch_idx:{}/{}, Duration:{:.2f}'.format(batch_idx, len(testloader), time.time()-batch_start_time))
batch_start_time = time.time()
prec1, prec5 = correct_num(logits, target, topk=(1, 5))
correct1 += prec1
correct5 += prec5
total += target.size(0)
acc1 = round(correct1/total, 4)
acc5 = round(correct5/total, 4)
print('Test accuracy_1:{:.4f}\n'
'Test accuracy_5:{:.4f}\n'
.format(acc1, acc5))
print('avg times:', (time.time()-sum_time)/50000)
(2)在实际应用中,可能会遇到单张图像的推理,也可以手工一张一张读,然后传入网络进行推理。
运行命令:
python test_imagenet.py --data [your imagenet validation set path]
test_imagenet.py文件内容
import torch
import torch.nn as nn
import torch.optim as optim
import torch.backends.cudnn as cudnn
import torch.nn.functional as F
import os
import shutil
import argparse
import numpy as np
import torchvision
import torchvision.datasets as datasets
import torchvision.transforms as transforms
import torchvision.models as models
from bisect import bisect_right
import time
import math
from PIL import Image
parser = argparse.ArgumentParser(description='PyTorch ImageNet Training')
parser.add_argument('--data', default='/dev/shm/ImageNet/val/', type=str, help='trainset directory')
parser.add_argument('--dataset', default='ImageNet', type=str, help='Dataset name')
parser.add_argument('--arch', default='resnet18', type=str, help='network architecture')
parser.add_argument('--batch-size', type=int, default=256, help='batch size')
parser.add_argument('--num-workers', type=int, default=8, help='number workers')
parser.add_argument('--gpu', type=str, default='0')
parser.add_argument('--manual_seed', type=int, default=0)
# global hyperparameter set
args = parser.parse_args()
os.environ["CUDA_VISIBLE_DEVICES"] = args.gpu
np.random.seed(args.manual_seed)
torch.manual_seed(args.manual_seed)
torch.cuda.manual_seed_all(args.manual_seed)
num_classes = 1000
# Model
print('==> Building model..')
net = models.__dict__[args.arch](pretrained=True).cuda()
cudnn.benchmark = True
net.eval()
trans = transforms.Compose([
transforms.Resize(256),
transforms.CenterCrop(224),
transforms.ToTensor(),
transforms.Normalize(mean=[0.485, 0.456, 0.406],
std=[0.229, 0.224, 0.225]),
])
correct1 = 0
total = 0
dirs = []
for dir in os.listdir(args.data):
dirs.append(dir)
dirs.sort()
label = -1
with torch.no_grad():
for dir in dirs:
cur_dir = os.path.join(args.data, dir)
label = label + 1
for jpeg in os.listdir(cur_dir):
raw_image = Image.open(os.path.join(cur_dir, jpeg)).convert("RGB")
image = trans(raw_image)
image = torch.unsqueeze(image, 0).cuda()
logits = net(image)
probs = F.softmax(logits, dim=1)
value, index = probs.max(dim=1)
if index == label:
correct1 = correct1 + 1
total = total + 1
acc1 = round(correct1/total, 4)
print('Sample number:{}, all number: 50000, Test accuracy_1:{:.4f}'.format(total, acc1))
相比用pytorch的dataloader来加载数据,手工载入速度要更慢一些,但是准确率结果都是一样的,并且过程更加透明,更可控。