2016-01-25 41 views
-1
以csv

我目前运行在大量的图片,我已经运行代码的一些数据分析如下:对外输出Regionprops在MATLAB

close all 
clear all 
clc 

A=imread('Ring_1_frame_120.jpg');  %Load picture 
             %A01-A010 = xmin ymin width height 
             %for all vials 
A001=imcrop(A,[65 159 95 332]); 
A002=imcrop(A,[182 161 95 332]); 
A003=imcrop(A,[297 164 95 332]); 
A004=imcrop(A,[402 165 90 332]); 
A005=imcrop(A,[495 168 90 332]); 
A006=imcrop(A,[606 166 90 332]); 
A007=imcrop(A,[705 171 90 332]); 
A008=imcrop(A,[808 175 90 332]); 
A009=imcrop(A,[922 175 90 332]); 
A0010=imcrop(A,[1031 175 90 332]); 

w = who; % returns the names of all your current variables in a cell. 

for i = 1:numel(w) 
    % A00 is unique to all the variables you want to process. 
    if ~isempty(strfind(w{i}, 'A00')) 
     % hard coding greenChannel and extracting the second plane. 
     eval(['greenChannel = ',w{i},'(:,:,2)']); 
     BW = edge(greenChannel,'Prewitt'); 
      %figure, imshow(BW); 

    %Dialate Lines 
     se90 = strel('line', 3, 90); 
     se0 = strel('line', 3, 0); 
     BWsdil = imdilate(BW, [se90 se0]); 
      %figure, imshow(BWsdil), title('dilated gradient mask'); 

    %Fill Lines 
     BWdfill = imfill(BWsdil, 'holes'); 
      %figure, imshow(BWdfill), title('binary image with filled holes'); 
    %Clean up borders 
     BWnobord = imclearborder(BWdfill, 4); 
      %figure, imshow(BWnobord), title('cleared border image'); 
    %Final cleanup 
     seD = strel('diamond',1); 
     BWfinal = imerode(BWnobord,seD); 
     BWfinal = imerode(BWfinal,seD); 
      figure, imshow(BWfinal), title('segmented image'); 

     L = bwlabel(BWfinal); 
     s = regionprops(L,'centroid'); 
     data(:,:,i) = s; %save the xy coords as data matrix 
    end 
end 

我想实现的是得到的目标变量s到一个csv文件,但我卡在最后一行,因为它不工作。它一直覆盖自己。 s是一个从3x1到5x1的结构,我也尝试过使用struct2cell和mat2cell,但这是不成功的。

回答

3

s结构,所以你需要做的是解压结构,使其成为一个矩阵,然后你可以保存矩阵文件。 s包含一个名为Centroid的字段,因此您需要访问该字段。

但是,在我解决这一问题之前,请检查您的工作区中有多少个变量,以便确定循环需要迭代多少次......这是非常糟糕的做法。特别是如果您将每个变量名称用作处理的单独事件。我强烈建议你使用一种结构来封装这种或某种类型的单元阵列。

如果我可以提供一个规范的岗位,请咨询用户Adriaan如何避免动态变量名是什么,我要在这里谈论揭示光的excellent post

这样的事情会起作用。我将使用单元格数组,因为(至少对我而言)它更容易。将所需的坐标放置在一个2D矩阵中,其中每行都是要处理的图像中位置的左上角以及宽度和高度(基本适用于imcrop),然后遍历每组坐标和位置裁剪后的图像作为单元格阵列中的元素。

A=imread('Ring_1_frame_120.jpg');  %Load picture 
             %A01-A010 = xmin ymin width height 

coords = [65 159 95 332; 182 161 95 332; 297 164 95 332; 402 165 90 332;... 
      495 168 90 332; 606 166 90 332; 705 171 90 332; 808 175 90 332;... 
      922 175 90 332; 1031 175 90 332]; 

numImages = size(coords,1); 
images = cell(1,numImages); 

for ii = 1 : numImages 
    images{ii} = imcrop(A,coords(ii,:)); 
end 

images现在是属于图像A裁剪图像的单元阵列:因为每个裁剪后的图像尺寸是不同的,所以你不能在这里使用一个正常的矩阵单元阵列的使用是非常重要的。要访问正确的图像,你可以使用images做到这一点,像这样:

img = images{ii}; 

ii是你要访问的图像数量。我想提出的另一个意见是您使用eval。这是真的不建议你的循环...这就是为什么我决定改变逻辑。

而是执行此操作:

for ii = 1 : numImages 
    % hard coding greenChannel and extracting the second plane. 
    greenChannel = images{ii}(:,:,2); %// Change for green channel 

    %// Now code is the same as before 
    BW = edge(greenChannel,'Prewitt'); 
    %figure, imshow(BW); 

    %Dilate Lines 
    se90 = strel('line', 3, 90); 
    se0 = strel('line', 3, 0); 
    BWsdil = imdilate(BW, [se90 se0]); 
    %figure, imshow(BWsdil), title('dilated gradient mask'); 

    %Fill Lines 
    BWdfill = imfill(BWsdil, 'holes'); 
    %figure, imshow(BWdfill), title('binary image with filled holes'); 

    %Clean up borders 
    Wnobord = imclearborder(BWdfill, 4); 
    %figure, imshow(BWnobord), title('cleared border image'); 

    %Final cleanup 
    seD = strel('diamond',1); 
    BWfinal = imerode(BWnobord,seD); 
    BWfinal = imerode(BWfinal,seD); 
    figure, imshow(BWfinal), title('segmented image'); 

    ... 
end 

好了,所以现在我们如何得到质心坐标,并将其保存到文件?您只需解开结构并获取质心坐标。确保data在顶部宣称现在是一个单元阵列:

data = cell(1, numImages); 

为什么你需要一个单元阵列(再次)的原因是因为你不知道有多少分段部件也有每裁剪图像您”再看。现在,终于在你的循环的末尾:

for ii = 1 : numImages 
    %// Your code... 
    %//... 

    L = bwlabel(BWfinal); 
    s = regionprops(L,'centroid'); 

    %// New code 
    data{ii} = reshape([s.Centroid],2,[]).'; 
end 

现在你有了质心坐标存储在每个裁剪图像单元阵列,您可以创建多个CSV的每个CSV包含每个检测到的对象的每一个质心裁剪后的图像,或者您可以将所有质心连接在一个矩阵中。

所以,请执行:

for ii = 1 : numImages 
    csvwrite(sprintf('data%d.csv', ii), data{ii}); 
end 

...或

out = cat(1, data{:}); 
csvwrite('data.csv', out); 

我不知道你想用写入文件,该文件的方法,但无论是那些应该管用。

0

需要使用序列s(i).Centroid访问结构元件,如一个最小的例如,

a =imread('circlesBrightDark.png'); 
bw = a < 100; 
s = regionprops(bw,'centroid'); 

for i =1:size(s) 
    data(:,:,i) = s(i).Centroid 
end