質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.53%
Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

Q&A

解決済

2回答

2368閲覧

pytorch/conv1dモデルのtensor次元数不正エラー(FAQ)

sigefuji

総合スコア123

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

0グッド

0クリップ

投稿2022/09/07 12:28

前提

pytorchのconv1dの動作を調べています。
いくつかの資料を参考に次のコードで実行したところ、
RuntimeError: Given groups=1, weight of size [50, 1, 3], expected input[1, 40, 64] to have 1 channels, but got 40 channels instead
が発生しました。このerrorはpytorchではかなりのFAQらしいですが、明確に参考になる記事はみつけられませんでした。
自分なりに調べましたが解決にはいたりませんでした。
エラーに影響する値を、変数を変えて調べると次のことがわかりました。

[50, 1, 3]について
第1の数50:conv1dのout_channelすなわち、フィルターの数
第3の数3:kernelのサイズ
[1, 40, 64]について
第2の数40:ミニバッチサイズ
第3の数64:入力の1次元のデータの長さ

分からないこと
・[50, 1, 3], [1, 40, 64]それぞれがどの変数、状態あるいは何のテンソルをあらわすか?
(kernelサイズ3が入っていることが特に疑問)
・検索するといかにもFAQらしいのに、この問題をわかりやすく解説した記事をみつけられないこと。
(英語レベルでもかなりFAQですが解読に苦労すること)
nchwの説明はありますが、それでも理解が及びません。

このモデルでやりたいこと
・一次元データで、それに対応する教師データで学習すること
・dropout、畳み込み演算やポーリングの効果を見ること。

RuntimeError: Given groups=1, weight of size [50, 1, 3], expected input[1, 40, 64] to have 1 channels, but got 40 channels instead

該当のソースコード(全部)

python

1''' 21. データの読み込みと前処理 3''' 4import os 5from torchvision import datasets 6import torchvision.transforms as transforms 7from torch.utils.data import DataLoader 8import sys 9import numpy as np 10import torch 11 12 13p_out = 15 14rec_size = 64 15 16#file_path = "fxdata/lern_img1.byte" 17#with open(file_path, 'rb') as f: 18# data = np.frombuffer(f.read(), np.int16, offset=0) 19 20data = torch.randn(100,rec_size) #ファイルの読み込みの代わりに乱数でデータ生成 21print(data.shape) 22 23x = data.reshape(-1, rec_size) 24print("x.shape", x.shape) 25 26trec_size = 1 27#file_path = "fxdata/lern_lbl1.byte" 28#with open(file_path, 'rb') as f: 29# tdata = np.frombuffer(f.read(), np.int8, offset=0) 30tdata = torch.rand(100,trec_size)*10 #ファイルの読み込みの代わりに乱数でデータ生成 31print(tdata.shape) 32 33t = tdata.reshape(-1, trec_size) 34 35#x = torch.tensor(x, dtype=torch.float32) 36#t = torch.tensor(t, dtype=torch.int8) 37 38train_set = torch.utils.data.TensorDataset(x, t) 39 40batch_size = 40 41 42train_loader = DataLoader(train_set, 43 batch_size=batch_size, # ミニバッチのサイズ 44 shuffle=True) # シャッフルして抽出 45 46train_features, train_labels = next(iter(train_loader)) 47 48print("features",train_features.shape) 49#<class 'torch.Tensor'> 50print("size",train_features.size()) 51#torch.Size([64, 784]) 52 53print("labels",train_labels.shape) 54print("size",train_labels.size()) 55 56 57''' 582. モデルの定義 59''' 60import torch.nn as nn 61import torch.nn.functional as F 62 63class CNN(nn.Module): 64 def __init__(self): 65 66 super().__init__() 67 # 畳み込み層1 68 # inputは1次元で長さ64(=rec_size) 69 self.conv1 = nn.Conv1d(in_channels=1, 70 out_channels=50, 71 kernel_size=3, 72 #padding=(1,1), # パディングなし 73 #padding_mode='zeros' 74 )# ゼロでパディング 75 76 # 全結合層1 77 self.fc1 = nn.Linear(in_features=50*(rec_size-3), # 入力はフラット化後のサイズ rec_size=64 78 out_features=128) # ニューロン数 79 # ドロップアウト 80 self.fc_drop = nn.Dropout(0.5) 81 # 全結合層2 82 self.fc2 = nn.Linear(in_features=128, # 入力のサイズは前層のニューロン数 83 out_features=p_out) # ニューロン数はクラス数と同数 84 85 def forward(self, x): 86 87 x = self.conv1(x) 88 89 x = x.view(-1, 50 * 1 * 62) # この値を変えてもエラーは変わらない!! これ以前の問題 90 91 x = F.relu(self.fc1(x)) 92 x = self.fc_drop(x) # ドロップアウト 93 x = self.fc2(x) # 94 return x 95 96 97''' 983. モデルの生成 99''' 100import torch 101 102# 使用可能なデバイス(CPUまたはGPU)を取得する 103device = torch.device('cuda' if torch.cuda.is_available() else 'cpu') 104# モデルオブジェクトを生成し、使用可能なデバイスを設定する 105model = CNN().to(device) 106 107print("model",model) # モデルの構造を出力 108 109 110# 1ステップにおける訓練用ミニバッチを使用した学習 1エポックだけ学習 111for (x, t) in train_loader: 112 # torch.Tensorオブジェクトにデバイスを割り当てる 113 x, t = x.to(device), t.to(device) 114 #loss, preds= train_step(x, t) # 損失と予測値を取得 115 116 model.train() # モデルを訓練(学習)モードにする 117 preds = model(x) # モデルの出力を取得 118 119

試したこと

色々値を変えたとき偶然、mat1、mat2の関係が不正の趣旨のエラーになることもありましたが、本質はよく理解していない点で同じではないかと。
データはファイルから読みますが、提示コードは、ランダムに発生したデータとしています。本題と同じエラーが発生します。
x = x.view(-1, 50 * 1 * 62)については、この値を変えてもエラーには影響しません(この命令以前で発生するエラーに見える)

補足情報(FW/ツールのバージョンなど)

コンソール出力

torch.Size([100, 64]) x.shape torch.Size([100, 64]) torch.Size([100, 1]) features torch.Size([40, 64]) size torch.Size([40, 64]) labels torch.Size([40, 1]) size torch.Size([40, 1]) model CNN( (conv1): Conv1d(1, 50, kernel_size=(3,), stride=(1,)) (fc1): Linear(in_features=3050, out_features=128, bias=True) (fc_drop): Dropout(p=0.5, inplace=False) (fc2): Linear(in_features=128, out_features=15, bias=True) ) Traceback (most recent call last): File "C:\book\shuwa\chap06\sec06\test_1d.py", line 125, in <module> preds = model(x) # モデルの出力を取得 File "C:\anaconda3\envs\py38tor3\lib\site-packages\torch\nn\modules\module.py", line 1130, in _call_impl return forward_call(*input, **kwargs) File "C:\book\shuwa\chap06\sec06\test_1d.py", line 95, in forward x = self.conv1(x) File "C:\anaconda3\envs\py38tor3\lib\site-packages\torch\nn\modules\module.py", line 1130, in _call_impl return forward_call(*input, **kwargs) File "C:\anaconda3\envs\py38tor3\lib\site-packages\torch\nn\modules\conv.py", line 307, in forward return self._conv_forward(input, self.weight, self.bias) File "C:\anaconda3\envs\py38tor3\lib\site-packages\torch\nn\modules\conv.py", line 303, in _conv_forward return F.conv1d(input, weight, bias, self.stride, RuntimeError: Given groups=1, weight of size [50, 1, 3], expected input[1, 40, 64] to have 1 channels, but got 40 channels instead

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

jbpb0

2022/09/09 01:28 編集

> Given groups=1, weight of size [50, 1, 3], expected input[1, 40, 64] to have 1 channels, but got 40 channels instead x = data.reshape(-1, rec_size) ↓ 修正 x = data.reshape(-1, 1, rec_size) 参考 https://qiita.com/sshuv/items/79d9364b8675fdc080cf の 「作成されたインスタンスconv1dを使うために、畳み込みの入力配列を用意しましょう。入力配列は三次元でなければなりません。」 の下
jbpb0

2022/09/09 01:30 編集

上記を直したら、別のエラー RuntimeError: mat1 and mat2 shapes cannot be multiplied (40x3100 and 3050x128) が出ます > x = x.view(-1, 50 * 1 * 62) の「62」と、「in_features=50*(rec_size-3)」の「rec_size-3」(=61)が合ってないためです self.fc1 = nn.Linear(in_features=50*(rec_size-3), ↓ 修正 self.fc1 = nn.Linear(in_features=50*(rec_size-2),
jbpb0

2022/09/09 01:38

pytorchのネットワークの確認は、「torchinfo」が便利です インストールしたら、この質問のコードの場合は、下記で表示できます from torchinfo import summary summary(model, input_size=(batch_size, 1, rec_size)) 参考 https://yiskw713.hatenablog.com/entry/2021/06/01/070144
guest

回答2

0

ベストアンサー

Given groups=1, weight of size [50, 1, 3], expected input[1, 40, 64] to have 1 channels, but got 40 channels instead

 

python

1x = data.reshape(-1, rec_size)

↓ 修正

python

1x = data.reshape(-1, 1, rec_size)

 
参考
PyTorchのConv1dを理解する

「作成されたインスタンスconv1dを使うために、畳み込みの入力配列を用意しましょう。入力配列は三次元でなければなりません。」
の下

投稿2022/09/10 00:06

編集2022/09/10 00:08
jbpb0

総合スコア7649

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

3次元(+α)にすれば、一見正常動作したように見えたのですが、さらに検討すると不可解な現象もありましたので、ご返事はちょっと保留にしていましたが、それはそれでまたあとからと言うことで、この質問は解決とさせていただきます。ありがとうございました。

投稿2022/09/10 01:29

sigefuji

総合スコア123

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.53%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問