# Overwriting a table with a different sized table

9 views (last 30 days)
Lisbon on 8 Jan 2020
Answered: Eric Sofen on 10 Jan 2020
Hi All,
I have a timetable that is a time series of tables. Now I need another timetable which is a subset of the first one.
The code at the moment is:
Idates = datetime(TT.Time);
NumDates = length(Idates);
I = timetable('Size', size(TT), 'VariableTypes', "table", 'VariableNames', "In",'RowTimes', Idates);
% Trying to create a for loop to get the subset of each table and overwritte I. Started by trying to writte the first row and then go for the loop:
D = TT.Issue{Idates(1)};
D2 = (strcmpi(D.Type, 'FIX') & D.RDate < datetime('now') + calyears(1));
D3 = D(D2,:);
I.In(1,1) = table('size', size(D3),'VariableTypes', {'categorical', 'categorical', 'datetime', 'datetime', 'categorical', 'datetime', 'double', 'double', 'double', 'categorical', 'categorical'},'VariableNames', {'a', 'b', 'c', 'd', 'f', 'g', 'i', 'j', 'k', 'l', 'm'});
I get the error: To assign to or create a variable in a table, the number of rows must match the height of the table.
Because each table in I is 1x0 and each D3 i'll run is a different number of rows x 11.
Can someone help this one out please?
Thanks

#### 1 Comment

Guillaume on 8 Jan 2020
Your code is a bit confusing. Possibly, attach an example timetable so we understand better what it's doing.
If TT is a timetable, TT.Time should already be datetime, what's the purpose of the conversion?
Also, length(Idates) should be the same as height(TT).
Clearly, TT has at least 3 variables (Issue, Type, RDate), so size(TT) is at least ?x3 and
I = timetable('Size', size(TT), 'VariableTypes', "table", 'VariableNames', "In",'RowTimes', Idates);
asks to create a timetable with at least 3 variables, yet only one VariableNames/Types is specified. I don't see how this line can work.
When reporting an error message always give the full text of the error message. Particularly the bit that tells you which line is responsible for the error. The two lines I see can error (the above and the last line of your code) would generate a different error message, so I'm not sure where you're getting your error.

Steven Lord on 8 Jan 2020
You haven't shown us what your data looks like, so I'll use a sample timetable from the documentation.
indoors = table2timetable(indoors);
Let's select all rows in indoors that take place on November 16th and have AirQuality less than 80. First, let's make a timerange to extract all the rows on November 16th from the timetable.
nov16 = datetime(2015, 11, 16)
onNov16 = timerange(nov16, nov16 + days(1))
indoorsOnNov16 = indoors(onNov16, :)
By default the timerange includes its left edge (midnight on November 16th) but not its right (midnight on November 17th.) Now let's select only those rows with AirQuality less than 80.
indoorsOnNov16AirQuality = indoorsOnNov16(indoorsOnNov16.AirQuality < 80, :)
D2 = (strcmpi(D.Type, 'FIX') & D.RDate < datetime('now') + calyears(1));
The first part is like the indoorsOnNov16.AirQuality < 80 indexing into indoorsOnNov16 while the second part is like the timerange indexing into indoors.

Eric Sofen on 10 Jan 2020
There are two ways that timetables (or table) can contain tables. In one approach, the table is the same height as the timetable. This is what you're headed toward when you're preallocating your timetable of a certain size with a table variable.
>> tt = timetable(array2table(rand(3)),'SampleRate',1)
tt =
3×1 timetable
Time Var1
Var1 Var2 Var3
_____ ______________________________
0 sec 0.41772 0.20526 0.82871
1 sec 0.68249 0.83642 0.094549
2 sec 0.68056 0.70892 0.081738
The other approach is to have a timetable variable that is a cell array containing tables of different sizes. I think this is what you want based on the last line of your code where you're assigning one table into one element of the timetable.
>> tt = timetable({array2table(rand(3)); array2table(rand(2)); array2table(rand(4))}, 'SampleRate', 1)
tt =
3×1 timetable
Time Var1
_____ ___________
0 sec {3×3 table}
1 sec {2×2 table}
2 sec {4×4 table}
% Where indexing into one element gives the contained table (note {} rather than () to extract the contents):
>> >> tt.Var1{seconds(1)}
ans =
2×2 table
Var1 Var2
_______ _______
0.37023 0.44687
0.39302 0.4759