regionprops関数の応用について。

beboundaries関数の後にregionprops関数を使用し、画像の楕円に沿わせた曲線の長さを測りたいのですが、プログラムがうまく行きません。
regionprops関数の例が載っているページを確認しましたが、自分のプログラムと合わせることができません。
プログラムは以下の通りです。
%%画像入力
kaki_img=imread('box_dark.jpg'); %画像読み込み
%kakiimg=imcrop(kakiimg)
figure(2)
imshow(kaki_img,'Border','tight','InitialMagnification','fit');
%%画像全体のセグメンテーション
kaki_red=kaki_img(:,:,1); %画像のセグメンテーション(赤要素検出)
figure(3)
imshow(kaki_red,'Border','tight','InitialMagnification','fit');
%%画像の二値化
kaki_th=kaki_red>180;
figure(4)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%二値化画像の穴埋め
kaki_th=imfill(kaki_th,'holes');
figure(5)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%二値化画像のクリーンナップ(周囲の白を除去)
cc1=bwconncomp(kaki_th);
main1=regionprops(cc1,'Area');
A=[main1. Area];
[~,biggest]=max(A);
kaki_th(labelmatrix(cc1)~=biggest)=0; %最大の塊となっている1の要素以外の1の要素を0にする
figure(6)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%牡蠣の二値化画像の外周に色付け
BW=imbinarize(I);
%%Detec boundarries
B=bwboundaries(kaki_th,'noholes');
figure(7)
imshow(BW)
hold on
for kk=1:numel(B)
%%'c'で色を固定
plot(B{kk}(:,2),B{kk}(:,1),'c','LineWidth',2)
end

2 Comments

Kenta
Kenta on 21 Nov 2019
box_dark.jpgを添付していただけますか?
Nagae Ryoya
Nagae Ryoya on 23 Nov 2019
box_dark.jpg

Sign in to comment.

 Accepted Answer

Kenta
Kenta on 24 Nov 2019

2 votes

BW = kaki_thとして、進めれば実行できました。
以下のような図が最終的に作られました。これでいかがでしょうか。
%%画像入力
kaki_img=imread('box_dark.jpeg'); %画像読み込み
%kakiimg=imcrop(kakiimg)
figure(2)
imshow(kaki_img,'Border','tight','InitialMagnification','fit');
%%画像全体のセグメンテーション
kaki_red=kaki_img(:,:,1); %画像のセグメンテーション(赤要素検出)
figure(3)
imshow(kaki_red,'Border','tight','InitialMagnification','fit');
%%画像の二値化
kaki_th=kaki_red>180;
figure(4)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%二値化画像の穴埋め
kaki_th=imfill(kaki_th,'holes');
figure(5)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%二値化画像のクリーンナップ(周囲の白を除去)
cc1=bwconncomp(kaki_th);
main1=regionprops(cc1,'Area');
A=[main1. Area];
[~,biggest]=max(A);
kaki_th(labelmatrix(cc1)~=biggest)=0; %最大の塊となっている1の要素以外の1の要素を0にする
figure(6)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%牡蠣の二値化画像の外周に色付け
% BW=imbinarize(I);
BW = kaki_th;
%%Detec boundarries
B=bwboundaries(kaki_th,'noholes');
figure(7)
imshow(BW)
hold on
for kk=1:numel(B)
%%'c'で色を固定
plot(B{kk}(:,2),B{kk}(:,1),'c','LineWidth',2)
end
title(sprintf('boundary length is %d',size(B{1},1)))
result.PNG

8 Comments

Nagae Ryoya
Nagae Ryoya on 24 Nov 2019
この画像で、描かれている水色のラインの長さを測ることは可能ですか??
Kenta
Kenta on 24 Nov 2019
タイトルに、boundary lengthとして表示しています
Just FYIですが、「%%二値化画像のクリーンナップ(周囲の白を除去)」のセクションは bwareafilt 関数を使って下記のように簡単に書くことができます。
%%二値化画像のクリーンナップ(周囲の白を除去)
kaki_th = bwareafilt(kaki_th,1); % 面積が最大の領域 ("1" のピクセル群) のみを残す
Kenta
Kenta on 25 Nov 2019
Akira Agataさま、教えていただきありがとうございます。確かに、bwareafilt関数を使うほうが便利ですね。以下のように訂正しました。
Nagae Ryoyaさま、周長の算出方法を変更しました。こちらのほうがより正確かと思います。
詳しくはコードのほうをご確認お願い致します。最後から2行のところです。
%%画像入力
kaki_img=imread('box_dark.jpeg'); %画像読み込み
%kakiimg=imcrop(kakiimg)
figure(2)
imshow(kaki_img,'Border','tight','InitialMagnification','fit');
%%画像全体のセグメンテーション
kaki_red=kaki_img(:,:,1); %画像のセグメンテーション(赤要素検出)
figure(3)
imshow(kaki_red,'Border','tight','InitialMagnification','fit');
%%画像の二値化
kaki_th=kaki_red>180;
figure(4)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%二値化画像の穴埋め
kaki_th=imfill(kaki_th,'holes');
figure(5)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%二値化画像のクリーンナップ(周囲の白を除去)
kaki_th = bwareafilt(kaki_th,1); % 面積が最大の領域 ("1" のピクセル群) のみを残す
figure(6)
imshow(kaki_th,'Border','tight','InitialMagnification','fit');
%%牡蠣の二値化画像の外周に色付け
% BW=imbinarize(I);
BW = kaki_th;
%%Detec boundarries
B=bwboundaries(kaki_th,'noholes');
figure(7)
imshow(BW)
hold on
for kk=1:numel(B)
%%'c'で色を固定
plot(B{kk}(:,2),B{kk}(:,1),'r','LineWidth',10)
end
stats = regionprops('table',BW,'Perimeter');
title(sprintf('boundary length is %d',stats.Perimeter))
Nagae Ryoya
Nagae Ryoya on 25 Nov 2019
ありがとうございます。 教えていただいたプログラムでエラーもなくスムーズに動作しました。
statsについてですが、2725.3という値が算出されますが、実際の大きさとは異なっています。
リアルなサイズの値にすることは可能でしょうか??
Kenta
Kenta on 25 Nov 2019
これは、ピクセルの数で距離を出してます。そのため、1ピクセルあたりの距離で
スケーリングすればおおよそ近い値になると思います。
Nagae Ryoya
Nagae Ryoya on 25 Nov 2019
スケーリングについて、やり方などあれば、教えていただきたいです。
Kenta
Kenta on 25 Nov 2019
スケーリングは、撮影する対象の横に、リファレンスといって、何か長さが既知のものを置いておくのが一般的と思います。例えば、画像の横に、一辺10cmの紙をおいておき、それが今回の画像では何ピクセル分に相当するのかを見て、その比率で比例計算をすれば計算できます。ただ、今回の画像だとその基準となるマークも見つけにくそうですね。
今回は、うまくコードが走ったということで話を落ち着け、再度、上のことに取り組んでいただくのはいかがでしょうか。もしわからなそうなら、また今度聞いてもらえればと思います。

Sign in to comment.

More Answers (0)

Categories

Products

Release

R2019b

Asked:

on 21 Nov 2019

Commented:

on 25 Nov 2019

Community Treasure Hunt

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

Start Hunting!