添付した図のように、複数の細胞が存在するバイナリイメージ(二値画像)から、細胞を1つ1つトリミングしたいと考えています。
何かいい案を頂けると幸いです。
※以前まで、個々の細胞の重心を求め、そこを中心として必要なピクセルにトリミングしようと考えていたのですが、
全体のバイナリイメージから個々の細胞の重心を求める方法が分からず断念致しました。

2 commentaires

Akira Agata
Akira Agata le 16 Sep 2021
バイナリーイメージ内で細胞が1つ1つ分離しているものについては、regionprops 関数で Bounding Box を計算することでトリミング (クロップ) 可能です。また、同じ関数により個々の細胞の重心も求めることができます。ただ、複数の細胞が融合して "かたまり" になっている部分では、そのような処理は困難です。
まずは細胞が1つ1つ分離しているものについてのみ計算する、というアプローチでも問題ないでしょうか?
HIGUCHI 樋口
HIGUCHI 樋口 le 23 Sep 2021
ご丁寧な説明ありがとうございました。
大変申し訳ありませんがBounding Box を用いたトリミング方法は使用方法が理解できなかったため、
御指摘頂いたregionprops関数で、1つ1つの細胞の重心座標を求めて、そこの座標を中心としたて必要なピクセル数でトリミングする方法を使用しました。
複数細胞が融合しているものに関しましては除外するので問題ありません。1つ1つが明確に分離されているものを重心位置からトリミングするというアプローチで問題ありません。

Connectez-vous pour commenter.

 Réponse acceptée

Atsushi Ueno
Atsushi Ueno le 25 Sep 2021
Modifié(e) : Atsushi Ueno le 16 Oct 2021

2 votes

各位のコメント内容を実際に動かしてみました。尚、image processing toolboxが必要です。
I = imread('saibou.png');
BW = imbinarize(rgb2gray(I)); % カラー⇒グレースケール⇒二値化
BW = imopen(BW,strel('disk',10)); % モルフォロジーオープニングで小さなドットを除く
% Bounding Box, 重心, 面積を得る
stats = regionprops('table', BW, {'Centroid', 'BoundingBox', 'Area'});
idx = stats.Area > 10000;
stats(idx,:) = []; % 面積が10000ピクセル以上の領域は以降の処理から除外する
BB = stats.BoundingBox + [-40 -40 80 80]; % Bounding Boxに余白を付ける
imshow(I); hold on; % 加工前画像。小さなドットや接触した細胞は認識されない
plot(stats.Centroid(:,1),stats.Centroid(:,2),'b*'); % 重心を表示
for i = 1:size(BB,1)
rectangle('Position', BB(i,:), 'EdgeColor', 'y'); % Bounding Boxを表示
end
hold off;
for i = 1:size(BB,1)
crop{i} = imcrop(BW, BB(i,:)); % 細胞を1つ1つトリミングする(一部はくっついたまま)
if any([crop{i}(1,:) crop{i}(end,:) crop{i}(:,1)' crop{i}(:,end)'])
crop{i} = ~crop{i}; % Bounding Boxの境界に他の細胞が写り込んだら反転表示
end
end
montage(crop); % トリミングした二値化画像を並べて表示

4 commentaires

HIGUCHI 樋口
HIGUCHI 樋口 le 30 Sep 2021
ありがとうございます。参考にさせて頂きました。
加えてもう一点質問がございます。可能でしたらご回答いただけると幸いです。
細胞個々のトリミングの前に、bwareaopen関数を用いてノイズのような非常に小さなオブジェクトを削除しました。
更に、細胞1つ1つを抽出するために、図のように細胞が重なっている大きな塊(例えば、一定の面積より大きいオブジェクト)を除去したいと考えていますが、難航しております。
何か良いアイディアはありますでしょうか。
Akira Agata
Akira Agata le 30 Sep 2021
regionprops を適用する際にあわせて面積も計算しておいて、ある値以上のものはその後の計算対象から除外するという方法で対応可能です。
たとえば @Atsushi Ueno さんのコードで regionprops が使われている部分を以下のように修正すると、面積が10000ピクセル以上の領域は以降の処理から除外されます。
stats = regionprops('table', BW, {'Centroid', 'BoundingBox', 'Area'}); % Bounding Box, 重心, 面積を得る
idx = stats.Area > 10000;
stats(idx,:) = [];
Atsushi Ueno
Atsushi Ueno le 30 Sep 2021
なるほど。早速回答に反映しました。
HIGUCHI 樋口
HIGUCHI 樋口 le 10 Oct 2021
無事細胞個々でトリミング出来ました。お二方本当にありがとうございました。

Connectez-vous pour commenter.

Plus de réponses (0)

Catégories

Produits

Version

R2021a

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!