2022年度第9回卒研セミナー(2022/06/16)

関連サイトと資料

itertools.productとenumerate

# 評価で試す学習率
LR_TESTS = [1e-3, 2e-4, 5e-5]
  
# 試すウェイトは、人物の方が分散が大きいので、クラス1側を0.5より少なくする
WEIGHT_TESTS = [0.1, 0.2, 0.3, 0.4, 0.5]
  
for lr in LR_TESTS:
  for weight in WEIGHT_TESTS:
    print(f'lr={lr}, weight={weight}')
    

# 評価で試す学習率
LR_TESTS = [1e-3, 2e-4, 5e-5]
  
# 試すウェイトは、人物の方が分散が大きいので、クラス1側を0.5より少なくする
WEIGHT_TESTS = [0.1, 0.2, 0.3, 0.4, 0.5]
  
for (lr, weight) in itertools.product(LR_TESTS, WEIGHT_TESTS):
  print(f'lr={lr}, weight={weight}')
    

# 評価で試す学習率
LR_TESTS = [1e-3, 2e-4, 5e-5]
  
# 試すウェイトは、人物の方が分散が大きいので、クラス1側を0.5より少なくする
WEIGHT_TESTS = [0.1, 0.2, 0.3, 0.4, 0.5]
  
for t, (lr, weight) in enumerate(itertools.product(LR_TESTS, WEIGHT_TESTS)):
  print(f't={t}, lr={lr}, weight={weight}')
    

学習したパラメータを用いて、全データを識別する

使用したGPU処理に要した時間
GeForce RTX20801分50秒(110秒)
GeForce GTX1050Ti3分7秒(187秒)

import numpy as np
import pandas as pd
import os
from PIL import Image
  
import torch
from torch import nn
from torchvision import transforms, models
from torch.utils.data import Dataset, DataLoader
  
# proxy
os.environ["http_proxy"] = "http://ccproxyz.kanagawa-it.ac.jp:10080"
os.environ["https_proxy"] = "http://ccproxyz.kanagawa-it.ac.jp:10080"
    

USE_DEVICE = 'cuda:0' if torch.cuda.is_available() else 'cpu'
device = torch.device(USE_DEVICE)
  
# データがあるディレクトリ
INPUT_DIR = 'forest-path-movie-dataset-main/forest-path-movie-dataset-main/'
  
# 保存しておいたモデルを読み込む
model = models.resnet50(pretrained=False)
model.fc = nn.Linear(2048, 2)
model.load_state_dict(torch.load('./YAMA-DNN1/chapt02-model1.pth'))
model.to(device)
  
# モデルを推論用に設定する
model.eval()
    

# データセットの定義ファイルを読み込む
df = pd.read_csv(INPUT_DIR+'all_file2.csv')
  
# シーン毎に分割するので、groupbyして取り出す
file, person = [], []
for g in df.groupby(df.scene):
    file.append(g[1].file.values.tolist())
    person.append(g[1].person.values.tolist())
  
test_X = sum(file, [])
test_y = sum(person, [])
    

class MyTransform:
    def __init__(self):
        self.data_transform = transforms.Compose([
          transforms.Resize((224,224)),
          transforms.ToTensor(),
          transforms.Normalize(mean=[0.485, 0.456, 0.406],
                                     std=[0.229, 0.224, 0.225])
        ])
        
    def __call__(self, img):
        return self.data_transform(img)
    

class MyDataset(Dataset):
    def __init__(self, X, y, transform):
        # 初期化 Xはファイル名のリスト、yは人物が写っているかどうかのリスト
        self.X = X
        self.y = y
        self.transform = transform
  
    def __len__(self):
        # データセットの長さを返す
        return len(self.X)
  
    def __getitem__(self, pos):
        # posの場所にあるデータを返す
        f = INPUT_DIR + self.X[pos] # ファイルパス
        X = Image.open(f) # ファイルを読み込む
        X = self.transform(X)
        y = self.y[pos]
        return X, y
    

BATCH_SIZE = 16
test_ds = MyDataset(test_X, test_y, transform=MyTransform())
data_loader = DataLoader(test_ds, batch_size=BATCH_SIZE, shuffle=False)
    

true_valid = []
pred_valid = []

with torch.no_grad():
  for X, y in data_loader:
    X = X.to(device) # GPUを使うときはGPUメモリ上に乗せる

    res = model(X)
    res = res.detach().cpu().numpy() # CPUメモリに入れてnumpy化
    pred_valid.extend(res.argmax(axis=1).tolist())

    true_valid.extend(y.tolist())
  
n_valid = sum([v1 == v2 for v1, v2 in zip(pred_valid, true_valid)])
total = len(true_valid)
rate = n_valid / total * 100
print(f'正しい識別数={n_valid} 全データ数={total} 識別率={rate:.2f}%')
    

GeForce RTX2080での動作結果

GeForce GTX1050Tiでの動作結果