2012-09-13 86 views
1

我需要閱讀下列csv文件在MATLAB:閱讀CSV與混合型數據

2009-04-29 01:01:42.000;16271.1;16271.1 
2009-04-29 02:01:42.000;2.5;16273.6 
2009-04-29 03:01:42.000;2.599609;16276.2 
2009-04-29 04:01:42.000;2.5;16278.7 
... 

我想有三列:
時間戳;值1;值2

我試過辦法這裏描述:
Reading date and time from CSV file in MATLAB
修改爲:

filename = 'prova.csv'; 
fid = fopen(filename, 'rt'); 
a = textscan(fid, '%s %f %f', ... 
     'Delimiter',';', 'CollectOutput',1); 
fclose(fid); 

但它回退了1x2單元格,其第一個元素是a{1}='ÿþ2',另一個是空的。

我也試圖解答適應我的情況下,對這些問題:
importing data with time in MATLAB
Read data files with specific format in matlab and convert date to matal serial time
但我沒有成功。

如何導入csv文件?

編輯 @macduff的答案後,我試圖複製粘貼在一個新的文件上面報道的數據和使用:

a = textscan(fid, '%s %f %f','Delimiter',';'); 

和它的作品。 不幸的是,沒有解決問題,因爲我不得不處理csv文件自動生成,這似乎是奇怪的MATLAB行爲的原因。

+1

也許Matlab出於某種原因在第一行上窒息?您是否對生成的文件和使用複製粘貼進行了區別?你可以從Matlab複製/粘貼編程並使其工作嗎? – Superbest

回答

0

關於嘗試什麼:

a = textscan(fid, '%s %f %f','Delimiter',';'); 

對於我來說,我得到:

a = 

{4x1 cell} [4x1 double] [4x1 double] 

這樣的a每個元素對應於您的CSV文件列。這是你需要的嗎?

謝謝!

+0

感謝您的回答,但從您的代碼我得到:'a = {1x1 cell} [0x1 double] [0x1 double]' – Iovem

0

似乎你正在以正確的方式前進。你提供的例子在這裏沒有問題,我得到你想要的輸出。什麼是1x2單元格?

如果我是你,我會再次嘗試使用該文件的較小子集,比如說10行,然後查看輸出是否更改。如果是,則嘗試100行等,直到找到4x1單元+ 4x2陣列分解成1x2單元的位置。可能是空行或單個空字段或其他,這會強制textscan收集更多級別單元中的數據。

請注意,'CollectOutput',1將最後兩列收集到一個數組中,因此您最終將得到1個包含字符串的4x1單元格數組,以及1個包含雙精度值的4x2數組。這確實是你想要的嗎?否則,請參閱@ macduff的帖子。

+0

感謝您的答案。單元格的第一個元素是'a {1} ='ÿþ2',其他元素是空的....我嘗試將更多數據添加到原始文件(10行,50,100 ...),但沒有任何更改... 。如果我將另一個'csv'中的整個數據集(約2萬行)複製粘貼完美 – Iovem

0

我不得不解析這樣的大文件,我發現我不喜歡這個工作的textscan。我只是使用一個基本的while循環來解析文件,並且我使用datevec將時間戳記組件提取到6個元素的時間向量中。

%% Optional: initialize for speed if you have large files 
n = 1000 %% <# of rows in file - if known> 
timestamp = zeros(n,6); 
value1 = zeros(n,1); 
value2 = zeros(n,1); 

fid = fopen(fname, 'rt'); 
if fid < 0 
    error('Error opening file %s\n', fname); % exit point 
end 

cntr = 0 
while true 
    tline = fgetl(fid); %% get one line 
    if ~ischar(tline), break; end; % break out of loop at end of file 
    cntr = cntr + 1; 

    splitLine = strsplit(tline, ';'); %% split the line on ; delimiters 
    timestamp(cntr,:) = datevec(splitLine{1}, 'yyyy-mm-dd HH:MM:SS.FFF'); %% using datevec to parse time gives you a standard timestamp vector 
    value1(cntr) = splitLine{2}; 
    value2(cntr) = splitLine{3}; 
end 

%% Concatenate at the end if you like 
result = [timestamp value1 value2];