www.gusucode.com > datastoreio工具箱 matlab源码程序 > datastoreio/+matlab/+io/+datastore/@TabularTextDatastore/readData.m

    function [data, info] = readData(ds)
%READDATA Read subset of data from a datastore.
%   T = READDATA(TDS) reads some data from TDS.
%   T is a table with variables governed by TDS.SelectedVariableNames.
%   Number of rows in T is governed by TDS.ReadSize.
%   read(TDS) errors if there is no more data in TDS, and should be used
%   with hasdata(TDS).
%
%   [T,info] = READDATA(TDS) also returns a structure with additional
%   information about TDS. The fields of info are:
%       Filename - Name of the file from which data was read.
%       FileSize - Size of the file in bytes.
%       Offset - Starting position of the read operation, in bytes.
%       NumCharactersRead - Number of characters read from the file.
%
%   Example:
%   --------
%      % Create a TabularTextDatastore
%      tabds = tabularTextDatastore('airlinesmall.csv')
%      % Handle erroneous data
%      tabds.TreatAsMissing = 'NA'
%      tabds.MissingValue = 0;
%      % We are only interested in the Arrival Delay data
%      tabds.SelectedVariableNames = 'ArrDelay'
%      % Preview the first 8 rows of the data as a table
%      tab8 = preview(tabds)
%      % Sum the Arrival Delays
%      sumAD = 0;
%      while hasdata(tabds)
%         tab = read(tabds);
%         sumAD = sumAD + sum(tab.ArrDelay);
%      end
%      sumAD
%
%   See also - matlab.io.datastore.TabularTextDatastore, hasdata, readall, preview, reset.

%   Copyright 2016 The MathWorks, Inc.

import matlab.io.datastore.TabularTextDatastore;

% error early if no data available
if ~hasdata(ds)
    error(message('MATLAB:datastoreio:splittabledatastore:noMoreData'));
end

% if here, then we are at a split which has data or the buffer has data

if isnumeric(ds.ReadSize)
    readSize = ds.ReadSize;
    fullFile = false;
else
    readSize = Inf;
    fullFile = true;
end



scanFormats = strjoin(ds.TextscanFormats, ' ');

% error occured, pick up where we left off
% or readsize was smaller than split size
if ~isempty(ds.CurrBuffer)
    currBuffer = ds.CurrBuffer;
    currInfo = ds.CurrSplitInfo;
else
    [currBuffer, currInfo] = getNext(ds.SplitReader);
    ds.CurrSplitInfo = currInfo;
end

% this variable holds the number of characters before the data line, which
% basically in the number of characters in the header lines + any empty
% lines + the variable name line.
nCharsBeforeData = 0;

% aggregate textscan arguments.
txtScanArgs = ds.getTextscanArgs;

% handle beginning of files
if (0 == currInfo.Offset)
    
    % skip header lines and then apply the format to the variable line
    % based on ReadVariableNames (this for free takes care of empty lines
    % between header line and variable name line). The empty lines before
    % the data are taken care of by the textscan call which deals with the
    % data later. this does not take care of empty lines before the header
    % lines, that needs to specified as part of the header lines. This
    % also takes care of lines with custom whitespace, comment lines before
    % the variable line.
    [~,nCharsBeforeData] = textscan(currBuffer, ['%*[^',ds.RowDelimiter,']'], ...
                                         double(ds.ReadVariableNames), ...
                                         'HeaderLines', ds.NumHeaderLines, ...
                                                               txtScanArgs{:});
end

% for beginning of files, this is still 0 as no characters have been
% read/converted. This always holds the characters between succesive read
% calls to maintain info
nCharsRead = ds.NumCharactersReadInChunk;

try
    [data, info, nbytes] =  convertReaderData(ds, ...
                                currBuffer, currInfo, readSize, scanFormats, ...
                                txtScanArgs, nCharsRead, nCharsBeforeData, ~fullFile);
catch me
    ds.CurrBuffer = currBuffer;
    ds.CurrSplitInfo = currInfo;
    throw(me);
end

if ~fullFile && (nCharsRead + info.NumCharactersRead < numel(currBuffer))
    ds.NumCharactersReadInChunk = nCharsRead + info.NumCharactersRead;
    ds.CurrSplitInfo.Offset = ds.CurrSplitInfo.Offset + nbytes;
    ds.CurrBuffer = currBuffer;
else
    ds.NumCharactersReadInChunk = 0;
    ds.CurrSplitInfo = [];
    ds.CurrBuffer = '';
end

end