una - llenar un jtable con un arreglo java
¿Cómo rellenar datos en una JTable con base de datos? (7)
Quiero mostrar una JTable que muestre los datos de una tabla de base de datos tal como está.
Hasta ahora, he usado JTable que muestra datos del Objeto [] [].
Sé que una forma de mostrar los datos es convertir primero la tabla de la base de datos en Objeto [] [], pero ¿existe alguna otra que sea fácil pero más poderosa y flexible?
Debe crear un TableModel personalizado. Allí puede especificar de dónde y cómo provienen los datos.
Realmente debes entender completamente cómo funciona JTable + TableModel y luego seguir una de las respuestas publicadas anteriormente.
Dependiendo de lo que haya hecho y de lo que esté dispuesto a hacer, he estado usando Netbeans con su soporte Beans Binding para una aplicación basada en bases de datos con mucho éxito. Usted vincula su JTable a una base de datos y genera automáticamente las consultas JPA.
Estoy dando un pequeño método para mostrar datos de la tabla de base de datos en JTable. Debe pasar solo el conjunto de resultados de la tabla de base de datos como parámetro.
// rs is the ResultSet of the Database table
public void displayData(ResultSet rs)
{
//jt Represents JTable
//jf represents JFrame
int i;
int count;
String a[];
String header[] = {"1","2","3","4","5"}; //Table Header Values, change, as your wish
count = header.length;
//First set the Table header
for(i = 0; i < count; i++)
{
model.addColumn(header[i]);
}
jt.setModel(model); //Represents table Model
jf.add(jt.getTableHeader(),BorderLayout.NORTH);
a = new String[count];
// Adding Database table Data in the JTable
try
{
while (rs.next())
{
for(i = 0; i < count; i++)
{
a[i] = rs.getString(i+1);
}
model.addRow(a); //Adding the row in table model
jt.setModel(model); // set the model in jtable
}
}
catch (Exception e)
{
JOptionPane.showMessageDialog(null, "Exception : "+e, "Error", JOptionPane.ERROR_MESSAGE);
}
}
La mejor manera de llenar jTable con ResultSet
Prerrequisitos
1) El conjunto de resultados "rs" se rellena con los datos que necesita. 2) JTable "jTable1" se crea antes de la mano 3) Table Header se implementa antes de la mano
Implementación
java.sql.ResultSet rs = datacn.executeSelectQuery(query);
//Filling JTable with Result set
// Removing Previous Data
while (jTable1.getRowCount() > 0) {
((DefaultTableModel) jTable1.getModel()).removeRow(0);
}
//Creating Object []rowData for jTable''s Table Model
int columns = rs.getMetaData().getColumnCount();
while (rs.next())
{
Object[] row = new Object[columns];
for (int i = 1; i <= columns; i++)
{
row[i - 1] = rs.getObject(i); // 1
}
((DefaultTableModel) jTable1.getModel()).insertRow(rs.getRow() - 1,row);
}
Otra forma potente y flexible de mostrar los datos de la base de datos en una JTable es cargar los datos resultantes de su consulta en un CachedRowSet , luego conectarlo a la JTable con el adaptador TableModel .
- Consulta ---> Datos de la base de datos ---> RowSet
- RowSet <--> adaptador TableModel <--> JTable
Este book de George Reese proporciona el código fuente de su clase RowSetModel para adaptar un RowSet como un TableModel. Trabajó para mí fuera de la caja. Mi único cambio fue un nombre mejor para la clase: RowSetTableModel .
Un RowSet es una subinterfaz de ResultSet, agregado en Java 1.4. Así que un RowSet es un ResultSet.
Una implementación de CachedRowSet hace el trabajo por usted, en lugar de que usted cree una clase de fila, una lista de objetos de fila y ResultSetMetaData como se explica en otras respuestas en esta página.
Sun / Oracle proporciona una implementación de referencia de CachedRowSet. Otros proveedores o controladores JDBC también pueden proporcionar implementaciones.
Sé que la pregunta es antigua, pero para cualquiera que siga la solución de Adamski, se debe tener cuidado al compartir el ResultSet
y el ResultSetMetadata
entre los hilos de la interfaz SwingWorker
y SwingWorker
. Obtuve una excepción de estado interno inconsistente al usar este enfoque con SQLite. La solución es cargar cualquier metadata a campos privados antes de ejecutar SwingWorker
y tener las funciones de obtención (getColumnName, etc.) para devolver los campos.
Yo recomendaría tomar el siguiente enfoque:
- Cree una clase de
Row
para representar una fila leída de suResultSet
. Esto podría ser un simple envoltorio alrededor de unObject[]
. - Cree una colección
List<Row>
, y la subclaseAbstractTableModel
para ser respaldada por esta colección. - Use un
SwingWorker
para completar suList<Row>
leyendo elResultSet
subyacente en un hilo de fondo (es decir, dentro del métododoInBackground()
). Llame al método de publicación deSwingWorker
para publicar lasRow
nuevamente en el hilo de despacho de eventos (por ejemplo, cada 100 filas). - Cuando se llama al método de
process
SwingWorker
con la última parte de las filas leídas, agréguelas a suList<Row>
y dispare losTableEvent
apropiados para hacer que la pantalla se actualice. - Además, use el
ResultSetMetaData
para determinar laClass
de cada columna dentro de la definición deTableModel
. Esto hará que se representen correctamente (lo cual no será el caso si simplemente usa unObject[][]
2DObject[][]
array).
La ventaja de este enfoque es que la interfaz de usuario no se bloqueará cuando se procesen grandes conjuntos de resultados, y que la pantalla se actualizará gradualmente a medida que se procesen los resultados.
EDITAR
Código de ejemplo añadido a continuación:
/**
* Simple wrapper around Object[] representing a row from the ResultSet.
*/
private class Row {
private final Object[] values;
public Row(Object[] values) {
this.values = values;
}
public int getSize() {
return values.length;
}
public Object getValue(int i) {
return values[i];
}
}
// TableModel implementation that will be populated by SwingWorker.
public class ResultSetTableModel extends AbstractTableModel {
private final ResultSetMetaData rsmd;
private final List<Row> rows;
public ResultSetTableModel(ResultSetMetaData rsmd) {
this.rsmd = rsmd;
this.rows = new ArrayList<Row>();
}
public int getRowCount() {
return rows.size();
}
public int getColumnCount() {
return rsmd.getColumnCount();
}
public Object getValue(int row, int column) {
return rows.get(row).getValue(column);
}
public String getColumnName(int col) {
return rsmd.getColumnName(col - 1); // ResultSetMetaData columns indexed from 1, not 0.
}
public Class<?> getColumnClass(int col) {
// TODO: Convert SQL type (int) returned by ResultSetMetaData.getType(col) to Java Class.
}
}
// SwingWorker implementation
new SwingWorker<Void, Row>() {
public Void doInBackground() {
// TODO: Process ResultSet and create Rows. Call publish() for every N rows created.
}
protected void process(Row... chunks) {
// TODO: Add to ResultSetTableModel List and fire TableEvent.
}
}.execute();