[Solucionado]Duda funcionamiento Thread/Hilos

Iniciado por NetJava, 23 Marzo 2011, 12:16 PM

0 Miembros y 2 Visitantes están viendo este tema.

NetJava

Buenas,

estoy haciendo una aplicación que tiene diferentes funciones. Una de ellas es la de leer archivos .txt y guardar su contenido en BD, y lo que estoy haciendo es utilizar hilos para mejorar los tiempos, pero no estoy muy seguro de que estén funcionando bien. Bueno os pregunto una duda bastante básica:

1.- Si dos procesos (en dos hilos) leen de un mismo archivo, lo pueden hacer a la vez¿? O hay que sincronizarlos¿?

2.- Si un hilo se ocupa de un archivo y otro se ocupa de otro archivo ocuparían el tiempo de un solo archivo, no¿? XD Lo que me preocupa es que a la vez están conectando a la BD (creo que no debería pasar nada con la BD en cuanto a sincronizar hilos) y a lo mejor hay hay conflicto.


Código (java) [Seleccionar]

        public void run(){
try{
while(!terminar){
//lo que se ejecutara.
Contenido = ARCHI.LeerArchivo(url);
ALGORIT.FiltradoSeparacion(Contenido);
//this.terminar = true;
}
}catch(Exception ex){
ex.printStackTrace();
}
}


Lo que esta dentro se ejecuta, no¿? Es así de simple parece.

Saludos y muchas gracias!

Debci

1- Para que los hilos acedan a un recurso estático, tienen que estar sincronizados.

2- Pueden entrar tanto hilos como gustes a la DB, si no, no podrían estar conectados vários usuarios a la vez en una MySQL por ejemplo, mientras no se contradiga un hilo a otro, todo deberia funcionar como debiere.

Un saludo

NetJava

#2
Buenas,

muchas gracias. Pregunto un poco más. He hecho un ejemplo para para poder comprender más el funcionamiento. En el ejemplo únicamente hay 3 "JLabel" que realizan una cuenta ascendente 0/100000000, cada uno con sus botones de empezar, detener y seguir. Aun que estos dos últimos me da igual por el momento.

- El primer "JLabel" con su botón de comienzo sigue el proceso normal de la aplicación, no pasa por ningún hilo.

- Los dos siguientes pasan por hilo, cada uno en el momento en el que se le de a -empezar, y empieza la cuenta en ese orden.

Tengo una clase "hilo" que en su méto "run" llama a la clase algoritmo donde empieza la secuencia. El código de la clase "hilo" es el siguiente.

Código (java) [Seleccionar]

package PackEjemThread1;

import javax.swing.*;

public class hilo extends Thread{

private algoritmo algo_0 = new algoritmo();
private boolean terminar_0 = false;
private JLabel jlbl_0 = new JLabel();
//private int a = 0;

public hilo(JLabel jlbl_0){
//this.a = a;
this.jlbl_0 = jlbl_0;
}

public void run(){

while(!terminar_0){
//lo que se ejecutara.
algo_0.generarsecuencia(jlbl_0);
//this.terminar_0 = true;
}
}

public void setTerminar0(boolean terminar0){
this.terminar_0=terminar0;
}
}


Ahora el código de la clase "algoritmo":
Código (java) [Seleccionar]

package PackEjemThread1;

import java.*;
import java.awt.*;
import javax.swing.*;

public class algoritmo {
public algoritmo(){}

public void generarsecuencia(JLabel jlbl){
for(int i = 0; i <= 100000000; i++){
for(int a = 0; a < 100000000; a++){
for(int z = 0; z < 100000000; z++){

}
}
jlbl.setText(i+"/100000000");
}
}

public void generarsecuencia1(JLabel jlbl){
for(int i = 0; i <= 100000000; i++){

jlbl.setText(i+"/100000000");
}
}
}



La clase "algoritmo" no tiene nada especial. Bueno lo que he podido comprobar es que funcionan en paralelo y es perfecto. Pero en el ejemplo donde realmente querría utilizarlo no es así en el momento en el que empieza a trabajar con la BD.

Bueno pues realizo una pregunta más especifica. En el código que mostré al principio se ve que primero se trabaja con una .txt, y después la información la paso a la BD. Exactamente en el .txt hay por ejempo 500000 palabras, y una a una la cotejo con la BD y si no existe la guardo. El problema es que con el archivo se trabaja bien, pero en el momento de guardar en la BD saltan excepciones por todos lados... Cosa que no pasa si no utilizo hilos... Hay que seguir un orden especial con las clases que se llaman desde el método "run()" de la clase "hilo"¿?¿?
Se os ocurre por que saltán excepciones en la clase que conecta con la BD¿?

Bueno estoy escribiendo mucho, pero ya de paso termino bien. Como veis en el código anterior "ALGORIT.FiltradoSeparacion(Contenido);" desde el método se llama a al siguiente código:

Código (java) [Seleccionar]

package PackApliGenerarDiccionario1;

import java.*;
import java.util.*;
import java.sql.*;
import javax.swing.*;
import javax.swing.JOptionPane;

public class DBManagement {

private String drv = "com.mysql.jdbc.Driver";
private String db = "jdbc:mysql://localhost:3306/bd_diccionario1";
private String userpass = "root";
private int idPalabra = 0;
private int MaxIdPalabra = 0;

private Connection Conectar;
private Statement St;

public int valortotal = 0;
private int valorcorrecto = 0;
private int valormomento = 0;

public DBManagement(){
try{
Class.forName(drv);
Conectar = DriverManager.getConnection(db, userpass, userpass);
St = Conectar.createStatement();
}catch(Exception e){
e.printStackTrace();
}
}

public void newCodigo(){
String SQL = "SELECT MAX(idpalabras) FROM palabras;";
try{
ResultSet aux = St.executeQuery(SQL);
aux.next();
idPalabra = aux.getInt(1);
}catch(Exception e){
e.printStackTrace();
}
}

public void fillTable(String dato, JLabel jlbl){
valormomento+=1;
if(Cotejar(dato) == 0){
valorcorrecto +=1;
newCodigo();
idPalabra +=1;
String SQL = "INSERT INTO palabras (idpalabras, palabras) Values ('" + idPalabra + "','" + dato + "');";
try{
St.executeUpdate(SQL);
}catch(Exception e){
e.printStackTrace();
}
}
jlbl.setText(valorcorrecto+"/"+valormomento+"/"+valortotal);
}

public int Cotejar(String d){
String SQL = "SELECT palabras FROM palabras WHERE palabras = '"+ d +"';";
String palabra = "";
int s = 0;
try{
ResultSet aux = St.executeQuery(SQL);
aux.next();
palabra = aux.getString(1);
//JOptionPane.showMessageDialog(null,""+palabra,"Message",JOptionPane.INFORMATION_MESSAGE);
if((palabra == null) || (palabra == "") || (palabra == " ")){
s = 0;
}else{
s = 1;
}
//JOptionPane.showMessageDialog(null,""+s,"Message",JOptionPane.INFORMATION_MESSAGE);
}catch(Exception ex){
ex.printStackTrace();
}
return s;
}

public Statement getSt(){
return St;
}

}




Bueno pues nada, solo recordar que el código funciona en una situación normal, pero no si se hace a través de hilos XD.
Muchas gracias a todos, y sobre todo a los que lean hasta el final este pestiño.

Saludos!!!

NetJava

Buenas,

pues cierro esta consulta por que creo que al final funciona, aunq saltan excepciones pero creo que ya lo he pillado y ya rula. Muchas gracias y saludos!!

P.D: No pongo resultado, por que creo que funcionaba más o menos desde el principio.

NetJava

Buenas,

pensaba que el problema  ya estaba solucionado, pero no... jajajaja, llevo un buen rato intentando encontrar una solución y no consigo nada de nada. El problema esta en que no me conecta a la BD directamente, se que el código conecta perfectamente pero por algún motivo ahora que lo estoy utilizando en otra aplicación que he empezado de cero, y con Thread, no funciona... solo se suponía que tenia que copiar y pegar el código y ya funcionaria...
Código (java) [Seleccionar]


private String drv1 = "com.mysql.jdbc.Driver";
private String db1 = "jdbc:mysql://localhost:3306/bd_diccionario1";
private String userpass1 = "root";

        private Connection conectar1;
private Statement st1;

public DBManagement(){
try{
Class.forName(drv1);
conectar1 = DriverManager.getConnection(db1, userpass1, userpass1);
st1 = conectar1.createStatement();
}catch(Exception e){
}
}



Al llamar al constructor para crear un objeto de esta clase salta la excepcion con un mensaje "com.mysql.jdbc.Driver". Bueno como había dicho esto lo hago desde un Thread.

Muchas de antemano. Seguiré buscando  :-\

Debci

Estas seguro de tener agregada la lib de JDBC en el IDE en este nuevo proyecto?
O en classpath en su defecto :P

Saludos

NetJava

Buenas,   ;D ;D ;D ;D ;D ;D ;D Justo ese era el problema XD!!! Esta mañana cuando me he dado cuenta casi me tiro por la ventana XD. Muchas gracias!!!! :silbar: