縦方向、もしくは横方向のみに規定幅(50ピクセル)での畳み込みを行いたいのですが
조회 수: 3 (최근 30일)
이전 댓글 표시
50*50ピクセルの画像を横方向に5枚、縦方向に4枚づつ並べた、一枚の写真の行列画像(5*4=250*200ピクセル)を用意します。その画像をCNNにかけるために畳み込みをしたいのですが、行列画像の各要素の情報を畳み込みたいため、縦、横それぞれで畳み込みをしたいです。イメージは以下の図の通りです。このような縦方向、もしくは横方向のみに規定幅(50ピクセル)での畳み込みを行いたいのですがMATLABで行うにはどのような操作が必要になりますでしょうか。お力をお貸しください。![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/917614/image.png)
![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/917614/image.png)
댓글 수: 0
채택된 답변
Atsushi Ueno
2022년 3월 9일
上記畳み込み関数を使用しました。
base = imread('coins.png'); % サンプル画像
base = base(51:100, 51:100); % トリミング
sb = size(base) % baseは50*50ピクセルの画像
sample = repmat(base,[4 5]); % 横方向に5枚、縦方向に4枚づつ並べた一枚の写真の行列画像
st = size(sample)./sb % 縦横に並べた枚数(50*50ピクセルが(5枚,4枚)=250*200ピクセル)
imshow(sample) % sampleは横250*縦200ピクセルの画像
for i = 1:1:sb(1) % 行列画像の各要素の情報を畳み込みたいため、縦、横それぞれで畳み込みをしたい
for j = 1:1:sb(2) % このような縦方向、もしくは横方向のみに規定幅(50ピクセル)での畳み込みを行いたい
cnv1(i,j) = conv(sample(i:sb(1):end, j),ones(st(1), 1),'valid'); % 縦方向のみに規定幅(50ピクセル)での畳み込み
cnv2(i,j) = conv(sample(i, j:sb(2):end),ones(1, st(2)),'valid'); % 横方向のみに規定幅(50ピクセル)での畳み込み
end % この例では、畳み込みの係数は全て1とします(↑ここ)
end
imshow(uint8(cnv1./st(1))) % 枚数で割れば元の画像になります
추가 답변 (2개)
Atsushi Ueno
2022년 3월 8일
편집: Atsushi Ueno
2022년 3월 9일
MATLABなら(他の言語でも)、上図の様に50*50*5*4にすれば考え易いです。
![](https://www.mathworks.com/matlabcentral/answers/uploaded_files/918849/image.png)
base = imread('coins.png');
base = base(51:100, 51:100); % baseは50*50ピクセルの画像
stack = repmat(base,[1 1 5 4]); % 横方向に5枚、縦方向に4枚づつ重ねる
size(stack)
for i = 1:size(stack,1)
for j = 1:size(stack,2)
cnv1(i,j) = mean(stack(i,j,:,1)); % 横方向に5枚串刺しで画素値を平均する(変わらない)
cnv2(i,j) = mean(stack(i,j,1,:)); % 縦方向に4枚串刺しで画素値を平均する(変わらない)
end % 畳み込みの演算内容は適当に平均(mean関数)にしました
end
cnv1 = uint8(cnv1); % 結果は元の画像(base)と同じ
cnv2 = uint8(cnv2); % 結果は元の画像(base)と同じ
댓글 수: 0
Atsushi Ueno
2022년 3월 9일
image processing toolboxがあれば、上記の各種関数を参考にすべきと思います。
base = imread('coins.png');
base = base(51:100, 51:100); % baseは50*50ピクセルの画像
stack = repmat(base,[1 1 5 4]); % 横方向に5枚、縦方向に4枚づつ重ねる
fun = @(block_struct) mean(block_struct.data(:,:,:)); % 畳み込みの代わりに平均を演算する関数
tate = uint8(blockproc(squeeze(stack(:,:,:,1)),[1 1],fun)); % 横方向に5枚串刺しで画素値を平均する(変わらない)
yoko = uint8(blockproc(squeeze(stack(:,:,1,:)),[1 1],fun)); % 縦方向に4枚串刺しで画素値を平均する(変わらない)
% blockproc関数は画像データを想定していて3次元データしか受け付けないので
% 縦と横それぞれのデータを引数に渡す際にsqueze関数で1次元減らしています。
댓글 수: 0
참고 항목
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!