SilverRay SilverRay - 1 month ago 16
MySQL Question

Iterate 2D array of ResultSet to JTable

I have a resultset class that all of the query operations are stored. My problem is thatI am trying to fill a jtable with resultset data but I am only able to display the data in one column where I have three. This is the snippet of the resultset class:

public static List<List<String>> getAllFabrics() throws SQLException{
sql = "SELECT * FROM fabric";

List<List<String>> values = new ArrayList<>();
List<String> id = new ArrayList<>();
List<String> item = new ArrayList<>();
List<String> supplier = new ArrayList<>();
stmt = con.createStatement();
rs = stmt.executeQuery(sql);
//metaData = rs.getMetaData();
//int columnNum = metaData.getColumnCount();
while(rs.next()){
id.add(String.valueOf(rs.getInt("id")));
item.add(rs.getString("ItemDesc"));
supplier.add(rs.getString("Supplier"));

}
values.add(id);
values.add(item);
values.add(supplier);

return values;
}


and this is the jtable method that I am trying for hours to solve:

public static DefaultTableModel loadTable(){
ModelDB model = null;
DefaultTableModel tableModel = new DefaultTableModel();
tableModel.addColumn("ID");
tableModel.addColumn("Fabric");
tableModel.addColumn("Supplier");

try{
List<String> id = model.getAllFabrics().get(0);
List<String> item = model.getAllFabrics().get(1);
List<String> supplier = model.getAllFabrics().get(2);

//System.out.println(model.getAllFabrics().size()); tableModel.addRow(new Object[]{subRow});
for(List<String> row:model.getAllFabrics()){
tableModel.addRow(new Object[]{id,item,supplier});
}


}catch(SQLException ex){
ex.printStackTrace();
}
return tableModel;
}


I can't find a way to iterate the values to display in their respective column.

Answer

Original answer

You are almost there! You only need to change the loop:

for(int i = 0; i < id.size(); i++) {
    tableModel.addRow(new Object[] {id.get(i),item.get(i),supplier.get(i)});
}

But as said in the comments, you should consider changing to an array of rows, not columns.

Edit

This is one approach. It is basically same as your code except the rows/columns are interchanged so the method returns a List of rows, not columns:

public static List<List<String>> getAllFabrics() throws SQLException{
    sql = "SELECT * FROM fabric";
    List<List<String>> values = new ArrayList<>();
    stmt = con.createStatement();
    rs = stmt.executeQuery(sql);
    while(rs.next()){
        List<String> row = new ArrayList<>();
        row.add(String.valueOf(rs.getInt("id")));
        row.add(rs.getString("ItemDesc"));
        row.add(rs.getString("Supplier"));
        // Now row contains {id, item, supplier}
        values.add(row);
    }
    return values;
}

Then in your loadTable() method change to:

...

try{
    for(List<String> row: model.getAllFabrics()){
        tableModel.addRow(row.toArray(new String[row.size()]);
    }
...

In your original code you call model.getAllFabrics() multiple times to get the return value. This is not good because every time you do that the method gets called and it needs to make the SQL-request again etc. Store the return value in a variable instead. In this case though as the return value is only accessed once you can equally just do as I described above.

Hope this helps :)