Search code examples
matlabfile-ioimporttextscan

Importing data block with Matlab


I have a set of data in the following format, and I would like to import each block in order to analyze them with Matlab.

                        Emax=0.5/real

----------------------------------------------------------------------

           4.9750557                           14535
           4.9825821                           14522
            4.990109                           14511
           4.9976354                           14491
           5.0051618                           14481
           5.0126886                           14468
            5.020215                           14437
           5.0277414                           14418
           5.0352678                           14400
           5.0427947                           14372
           5.0503211                           14355
           5.0578475                           14339
           5.0653744                           14321

                        Emax=1/real

----------------------------------------------------------------------
           24.965595                          597544
           24.973122                          597543
           24.980648                          597543
           24.988174                          597542
           24.995703                          597542
           25.003229                          597542

I have modified this piece of code from MathWorks, but I think, I have problems dealing with the spaces between each column.

Each block of data consist of 3874 rows and is divided by a text (Emax=XX/real) and a line of ----, unfortunately is the only way the software export the data.


Solution

  • Here is one way to import the data:

    % read file as a cell-array of lines
    fid = fopen('file.dat', 'rt');
    C = textscan(fid, '%s', 'Delimiter','');
    C = C{1};
    fclose(fid);
    
    % remove separator lines
    C(strncmp('---',C,3)) = [];
    
    % location of section headers
    headInd = [find(strncmp('Emax=', C, length('Emax='))) ; numel(C)+1];
    
    % extract each section
    num = numel(headInd)-1;
    blocks = struct('header',cell(num,1), 'data',cell(num,1));
    for i=1:num
        % section header
        blocks(i).header = C{headInd(i)};
    
        % data
        X = regexp(C(headInd(i)+1:headInd(i+1)-1), '\s+', 'split');
        blocks(i).data = str2double(vertcat(X{:}));
    end
    

    The result is a structure array containing the data from each block:

    >> blocks
    blocks = 
    2x1 struct array with fields:
        header
        data
    
    >> blocks(2)
    ans = 
        header: 'Emax=1/real'
          data: [6x2 double]
    
    >> blocks(2).data(:,1)
    ans =
       24.9656
       24.9731
       24.9806
       24.9882
       24.9957
       25.0032