我有一个简单的Swing按钮刷新jtable,但是在随机点击后,应用程序冻结,有时无限期,有时它会在一分钟左右后响应。我从来没有做任何特定于线程的方法所以我认为可能s the issue but I don
知道从哪里开始或如何修改方法,如果这是造成冻结的原因。
这是代码:
private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
recorrerLista();
}
public EventList recorrerLista(){
Persistir p = Persistir.getInstancia();
Vector<Pedidos> lista2 = p.listarPedidos();
Iterator it = lista2.iterator();
if(!pedList.isEmpty()){
pedList.clear();
}
while(it.hasNext()){
Vector v = new Vector();
v = (Vector) it.next();
int index = (Integer)v.get(0);
Pedidos ped = new Pedidos();
ped = p.buscarPedidoPorId(index);
pedList.add(ped);
}
return pedList;
}
编辑:我尝试在SwingWorker中插入持久化类(Persistir)的方法,但现在UI不会显示。
这是代码
public Vector listarPedidos() throws InterruptedException, ExecutionException{
SwingWorker listar = new SwingWorker<Vector, Vector>(){
@Override
protected Vector doInBackground() throws Exception {
Vector<Articulos> lista = null;
EntityManagerFactory emf = Persistence.createEntityManagerFactory("PedidosPU" );
EntityManager em = emf.createEntityManager();
em.getTransaction().begin();
try {
Query query = em.createNativeQuery("SELECT * FROM pedidosview WHERE ENTREGADO='P' ORDER BY fecha_pedido");
lista = (Vector) query.getResultList();
} catch (Exception e) {
System.out.println( e.getMessage() );
em.getTransaction().rollback();
} finally {
em.close();
emf.close();
}
return lista;
}
};
return (Vector) listar.get();
}
public Vector listarPedidos(){
//Vector<Articulos> lista = null;
final EntityManagerFactory emf = Persistence.createEntityManagerFactory("PedidosPU" );
final EntityManager em = emf.createEntityManager();
final SwingWorker worker = new SwingWorker(){
private Vector lista;
@Override
protected Object doInBackground() throws Exception {
em.getTransaction().begin();
try {
Query query = em.createNativeQuery("SELECT * FROM pedidosview WHERE ENTREGADO='P' ORDER BY fecha_pedido");
lista = (Vector) query.getResultList();
} catch (Exception e) {
System.out.println( e.getMessage() );
em.getTransaction().rollback();
} finally {
em.close();
emf.close();
}
return lista;
}
};
worker.execute();
return lista;
}
ActionPerformed()
。但它似乎完全跳过了代码private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {
final Persistir p = Persistir.getInstancia();
SwingWorker<Void, Pedidos> worker = new SwingWorker<Void, Pedidos>() {
//private Vector lista2;
@Override
protected Void doInBackground() throws Exception {
EntityManagerFactory emf = Persistir.createEntityManagerFactory("PedidosPU" );
EntityManager em = emf.createEntityManager();
String jqpl = "SELECT * FROM pedidosview WHERE ENTREGADO='P' ORDER BY fecha_pedido";
//TypedQuery<Articulos> query = em.createQuery(jpql, Articulos.class);
Query query = em.createNativeQuery("SELECT * FROM pedidosview WHERE ENTREGADO='P' ORDER BY fecha_pedido");
//query.setParameter("param", "P");
//lista = (Vector) query.getResultList();
List<Pedidos> lista2 = query.getResultList();
publish((Pedidos[])lista2.toArray());
em.close();
emf.close();
return null;
}
@Override
protected void process(List<Pedidos> chunks) {
Iterator it = lista2.iterator();
if(!pedList.isEmpty()){
pedList.clear();
}
while(it.hasNext()){
Vector v = new Vector();
v = (Vector) it.next();
int index = (Integer)v.get(0);
Pedidos ped = new Pedidos();
ped = p.buscarPedidoPorId(index);
pedList.add(ped);
}
}
@Override
protected void done() {
jButton1.setEnabled(true);
}
};
worker.execute();
}
答案 0 :(得分:6)
您的SwingWorker实施非常类似于您根本没有任何内容,因为在listarPedidos()
结束时您调用get()方法:
public Vector listarPedidos() throws InterruptedException, ExecutionException {
...
return (Vector) listar.get();
}
因此导致Event Dispatch Thread被阻止,直到doInBackground()完成:
您应该使用publish()和process()代替。由于您使用JPA,我假设您可以设法获得名为Articulos
的实体,因此您可以执行以下操作:
SwingWorker<Void, Articulos> worker = new SwingWorker<Void, Articulos>() {
@Override
protected Void doInBackground() throws Exception {
EntityManagerFactory emf = Persistence.createEntityManagerFactory("PedidosPU" );
EntityManager em = emf.createEntityManager();
String jqpl = "SELECT a FROM Articulos a WHERE a.entregado = :param";
TypedQuery<Articulos> query = em.createQuery(jpql, Articulos.class);
query.setParameter("param", "P");
List<Articulos> resultList = query.getResultList();
publish((Articulos[])resultList.toArray());
em.close();
emf.close();
}
@Override
protected void process(List<Articulos> chunks) {
// add your items to the table model here
// this code runs in the EDT
}
@Override
protected void done() {
refreshButton.setEnabled(true);
}
};
worker.execute();
考虑到Vector classm的使用,我怀疑你的表模型是DefaultTableModel(如果不是这样的情况,pelase忽视了这个偏离主题的评论),这不是与复杂工作的最好的盟友模特课。
如果是这种情况(考虑到您似乎会说西班牙语),请参阅this post (in Spanish) (或in English,礼貌谷歌翻译)关于创建使用域类的可重用表模型。如果您不会说西班牙语,您仍然可以查看this entry (或in English)末尾发布的GenericDomainTableModel
班级代码,因为,它非常明显。