How do I change my code to stop a for loop simply replacing rows of outputs in a uitable?

function drainage_system_design_rough
n=input('How many pipes are in the system? ');
PRef=[1:1:n];
for PRef=1:n
disp('Pipe reference:')
disp(PRef)
L=input('Pipe Length:');
schedule=input('Do you want to add pipe to drainage schedule? (Yes=1, No=0)?: ');
if schedule==1
col={'Pipe Length(m)'};
row={PRef};
dat={L};
uitable('columnname',col,'rowname',row,'data',dat);
end
end
I am really new to MATLAB but want to create a simple table to store drainage system information. I want the rows of the table to be labelled by the pipe references (the number of which depend on the number of pipes in the system). However, each time the for loop is executed only the information for the last pipe is stored in the table and it replaces the informaton for the previous pipe. If any could help me code this better so I had a table that added rows each time the for loop was executed but also stored the previous rows, that would be much appreciated.

 Accepted Answer

Uitables do not have an append mode. When you specify data, you either need to specify the specific row, or reload all the data. Given the functionality you want, my approach would be to first extract the existing values/rownames, then append the new values to the end, and pass the combined values back in as the table data.
fig = uifigure;
uit = uitable(fig,'columnname','Pipe Length(m)',"RowName",{},"Data",[]);
n=input('How many pipes are in the system? ');
PRef=[1:1:n];
for PRef=1:n
disp('Pipe reference:')
disp(PRef)
L=input('Pipe Length:');
schedule=input('Do you want to add pipe to drainage schedule? (Yes=1, No=0)?: ');
if schedule==1
uit.Data = [uit.Data;L];
uit.RowName = {uit.RowName{:};PRef};
end
end

7 Comments

Hi Cris, thank you for your help. I have tried to implement the code you have suggested and follow your guidance but I am still running into trouble. Firstly, I get an error after entering in information for a second pipe so only information for one pipe shows up in the table. Secondly, I have now expanded my code to include multiple inputs but I am unsure how to modify the code so that the table can display all the collected values for each pipe.The code I am working on is below and any extra help would be highlighy appreciated.
function drainage_system_design_rough
fig = uifigure;
uit = uitable(fig,'columnname','Pipe Length(m)',"RowName",{},"Data",[]);
n=input('How many pipes are in the system? ');
PRef=[1:n];
for PRef=1:n
disp('Please input data for the following pipe:')
disp('Pipe reference')
disp(PRef)
USMHRef=input('Upstream Manhole Reference: ');
Dia=input('Pipe diameter (mm): ');
L=input('Pipe length (m): ');
K=input('Pipe roughness value: ');
USCL=input('Upstream cover level (mAOD): ');
USIL=input('Upstream invert level (mAOD): ');
G=input('Desired pipe gradient: ');
schedule=input('Do you want to add pipe to drainage schedule? (Yes=1, No=0)?: ');
if schedule==1
uit.Data = [uit.Data;L];
uit.RowName = {uit.RowName{:};1:n};
end
end
You say you got an error, but did not say what the error was.
The example I shared works. Were you able to get that to run?
The following is the error I receive when using your example and entering the last pipe into the program:
Error using vertcat
Dimensions of arrays being concatenated are not consistent.
Error in drainage_system_design_rough (line 15)
uit.RowName = {uit.RowName{:};PRef};
I tested with 3 pipes, adding the 1st and 3rd to the table.
How many pipes are you trying to enter? What are the values you are entering?
Whether I try 3 or more pipes I always get that error message once I input the information for the 3rd pipe. I am just entering standard values for pipe length like 10 and 20.
Yup, I see it. Part of the fun of working with cells... Here's an updated and simplified version. I have removed the inputs, for loop, and if statement.
fig = uifigure;
uit = uitable(fig,'columnname','Pipe Length(m)',"RowName",{},"Data",[]);
PRef=1:5;
L=[5 7 9 11 15];
p=1;
uit.Data = [uit.Data;L(p)];
uit.RowName = [uit.RowName;num2str(PRef(p))];
p=2;
uit.Data = [uit.Data;L(p)];
uit.RowName = [uit.RowName;num2str(PRef(p))];
p=3;
uit.Data = [uit.Data;L(p)];
uit.RowName = [uit.RowName;num2str(PRef(p))];
p=4;
uit.Data = [uit.Data;L(p)];
uit.RowName = [uit.RowName;num2str(PRef(p))];
p=5;
uit.Data = [uit.Data;L(p)];
uit.RowName = [uit.RowName;num2str(PRef(p))];
Hi Cris, thanks for that. Can you please see the below code. I have expandad the original code to now include multiple inputs that I require in my uitable so I need to keep the structure of the for loop to input the different values for the different pipes. As mentioned before, how can I changed this code to get rid of the error message and expand it for multiple inputs that need to be separate colums?
function drainage_system_design_rough3
fig = uifigure;
uit = uitable(fig,'columnname','Pipe Length(m)',"RowName",{},"Data",[]);
n=input('How many pipes are in the system? ');
PRef=[1:n];
for PRef=1:n
disp('Please input data for the following pipe:')
disp('Pipe reference')
disp(PRef)
USMHRef=input('Upstream Manhole Reference: ');
Dia=input('Pipe diameter (mm): ');
L=input('Pipe length (m): ');
K=input('Pipe roughness value: ');
USCL=input('Upstream cover level (mAOD): ');
USIL=input('Upstream invert level (mAOD): ');
G=input('Desired pipe gradient: ');
schedule=input('Do you want to add pipe to drainage schedule? (Yes=1, No=0)?: ');
if schedule==1
uit.Data = [uit.Data;L];
uit.RowName = {uit.RowName{:};1:n};
end
end

Sign in to comment.

More Answers (1)

The code as it is currently written is creating a brand-new uitable every time the loop runs.
You need to update the code to either:
  1. Collect all the data, then create a uitable once with all the data.
  2. Create a uitable once at the beginning, then add data to the existing uitable.
Example of option 1:
ncols = 4;
nrows = 4;
colnames = cell(ncols,1);
rownames = cell(nrows,1);
data = cell(nrows,ncols);
for r = 1:nrows
for c = 1:ncols
rownames{r} = ['Row ' num2str(r)];
colnames{c} = ['Column ' num2str(c)];
data{r,c} = r*c;
end
end
uitable('ColumnName', colnames, 'RowName', rownames, 'Data', data)
Example of option 2:
tbl = uitable;
tbl.RowName = {};
tbl.ColumnName = {};
tbl.Data = {};
ncols = 4;
nrows = 4;
for r = 1:nrows
for c = 1:ncols
tbl.RowName{r} = ['Row ' num2str(r)];
tbl.ColumnName{c} = ['Column ' num2str(c)];
tbl.Data{r,c} = r*c;
end
end
The end result of both will be the same, but the first option is significantly more efficient.

1 Comment

Hi Benjamin, thank you for the help. I have tried to implement both your suggestions into my code.
  • For the first option I find that I get a similar issue to my original problem where only the information for the last pipe I enter through the for loop is stored in the uitable?
  • For the second option I find that no data is added to the table that is created at the start of the code so I am just left with a blank table?
Below I have pasted the two codes I have used (note that the inputs have been expanded compared to my original) and any help you could provide would be appreciated:
Table created at end of code:
function drainage_system_design_rough2
n=input('How many pipes are in the system? ');
PRef=[1:n];
for PRef=1:n
disp('Please input data for the following pipe:')
disp('Pipe reference')
disp(PRef)
USMHRef=input('Upstream Manhole Reference: ');
Dia=input('Pipe diameter (mm): ');
L=input('Pipe length (m): ');
K=input('Pipe roughness value: ');
USCL=input('Upstream cover level (mAOD): ');
USIL=input('Upstream invert level (mAOD): ');
G=input('Desired pipe gradient: ');
end
ncols = 7;
nrows = n;
for r = 1:nrows
for c = 1:ncols
rownames = {1:n};
colnames = {'Pipe Dia(mm)','Pipe Gradient','Pipe Length(m)','Pipe Roughness','US MH','US CL(mAOD)','US IL(mAOD)'};
data = {Dia,G,L,K,USMHRef,USCL,USIL};
end
end
uitable('ColumnName',colnames,'RowName',rownames,"Data",data);
Table created at start of code:
function drainage_system_design_rough3
tbl=uitable;
rownames={};
colnames={};
data={};
n=input('How many pipes are in the system? ');
PRef=[1:n];
for PRef=1:n
disp('Please input data for the following pipe:')
disp('Pipe reference')
disp(PRef)
USMHRef=input('Upstream Manhole Reference: ');
Dia=input('Pipe diameter (mm): ');
L=input('Pipe length (m): ');
K=input('Pipe roughness value: ');
USCL=input('Upstream cover level (mAOD): ');
USIL=input('Upstream invert level (mAOD): ');
G=input('Desired pipe gradient: ');
end
ncols = 7;
nrows = n;
for r = 1:nrows
for c = 1:ncols
rownames = {1:n};
colnames = {'Pipe Dia(mm)','Pipe Gradient','Pipe Length(m)','Pipe Roughness','US MH','US CL(mAOD)','US IL(mAOD)'};
data = {Dia,G,L,K,USMHRef,USCL,USIL};
end
end

Sign in to comment.

Categories

Find more on Develop Apps Programmatically in Help Center and File Exchange

Products

Release

R2020b

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!