IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage Java Discussion :

Lenteur sur accès à un buffer.


Sujet :

Langage Java

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre éclairé Avatar de kkt8
    Profil pro
    Inscrit en
    Janvier 2005
    Messages
    472
    Détails du profil
    Informations personnelles :
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2005
    Messages : 472
    Par défaut Lenteur sur accès à un buffer.
    Bonjour,

    Je lance un outils qui me recrache les versions des plugins de mon eclipse, c'est juste du texte agrémenté de quelques balises html.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
     
    public void takeVersions()
    {
    	Process proc = null;
    	try {
    		proc = Runtime.getRuntime().exec("sxversions.exe --html");
    		} catch (IOException e) {
    			e.printStackTrace();
    		}
    	InputStream out = proc.getInputStream();
    	MyBuffer bufferOut = new MyBuffer();
    	MyThread readOutThread = new MyThread(bufferOut, out);
    	try {
    		proc.getOutputStream().close();
    	} catch (IOException e2) {
    		e2.printStackTrace();
    	}
     
    	readOutThread.start();
     
    	// STDOUT
    	String sOut;
    	int nbTgt = 0;
     
    	try{
    		fAboutHtml = File.createTempFile("aboutVersions", ".html");
    		fAboutHtml.deleteOnExit();
    		BufferedWriter stdin = new BufferedWriter(new FileWriter(fAboutHtml));
     
    		while ((sOut = bufferOut.get()) != null) {
    			nbTgt++;
    			if(!sOut.isEmpty()) {
    				stdin.write(sOut);
    				stdin.newLine();
    			}
    			stdin.close();
    		}catch (IOException e) {
    	}
    }
    // Class MyBuffer to stock my feedbacks
    class MyBuffer {
    	private List<String> list;
    	private int nbConnected;
     
    	@SuppressWarnings("unchecked")
    	public MyBuffer() {
    		list = Collections.synchronizedList(new LinkedList());
    		nbConnected = 0;
    	}
     
    	public void add(String s) {
    		synchronized (list) {
    			list.add(s);
    			list.notify();
    		}
    	}
     
    	public String get() {
    		System.err.flush();
    		String s;
    		synchronized (list) {
    			if (list.size() == 0) {
    				try {
    					list.wait();
    				} catch (InterruptedException e) {
    					e.printStackTrace();
    				}
    			}
    			s = (String) list.remove(0);
    		}
    		return s;
    	}
     
    	public void connect() {
    		nbConnected++;
    	}
     
    	public void disconnect() {
    		nbConnected--;
    		if (nbConnected == 0) {
    			add(null);
    		}
    	}
    }
     
    // ////////////Class MyThread to create my buffer readers
    class MyThread extends Thread {
    	private MyBuffer buffer;
    	private InputStream in;
     
    	public MyThread(MyBuffer buffer, InputStream in) {
    		this.in = in;
    		this.buffer = buffer;
    		buffer.connect();
    	}
     
    	public void run() {
    		BufferedReader br = new BufferedReader(new InputStreamReader(in));
    		String s;
    		try {
    			while ((s = br.readLine()) != null) {
    				buffer.add(s);
    			}
    			in.close();
    			buffer.disconnect();
    		} catch (IOException e) {
    			e.printStackTrace();
    	}
    }
    ça marche très bien sauf que mon while prends des plombes ... style 5à7 secondes pour parcourir les 194 enregistrements (nb de nbTgt):
    while ((sOut = bufferOut.get()) != null) {

    J'arrive pas à voir ce qui cloche dans mon code.
    Une idée afin d'optimiser un peu ???

  2. #2
    Expert éminent
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Billets dans le blog
    1
    Par défaut
    Salut,


    Pourquoi toutes ces synchronisation ?
    Pourquoi ne pas tout faire en séquentiel dans le même thread ?

    Que dois-tu faire précisément ? Si je comprend bien tu veux simplement copier la réponse dans un fichier c'est ca ?

    a++

    PS : Si tu ne traites pas les flux d'entrée et d'erreurs, il est préférable de les fermer. De même depuis Java 5.0 il est préférable d'utiliser ProcessBuilder...

  3. #3
    Membre éclairé Avatar de kkt8
    Profil pro
    Inscrit en
    Janvier 2005
    Messages
    472
    Détails du profil
    Informations personnelles :
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2005
    Messages : 472
    Par défaut
    bonjour,
    je veux simplement copier la réponse dans un fichier, c'est bien ça !
    Comment je peux faire pour faire en séquentiel dans le même thread ?
    Pourquoi il est préférable d'utiliser ProcessBuilder ? à la place de process j'imagine ?

    Merci de ta réponse je vais creuser dans ce sens.

  4. #4
    Expert éminent
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par kkt8 Voir le message
    Comment je peux faire pour faire en séquentiel dans le même thread ?
    Ben il suffit de faire la copie juste après l'ouverture du process.
    Comme tu ne traites pas les autres flux il est inutile de passer par un thread supplémentaire...

    Citation Envoyé par kkt8 Voir le message
    Pourquoi il est préférable d'utiliser ProcessBuilder ? à la place de process j'imagine ?
    Parce que c'est la nouvelle manière de créer des Process, plus complète et plus claire, avec des paramètres bien séparés.

    De toute manière désormais Runtime.exec() appelle ProcessBuilder... alors autant le faire directement et utiliser une API claire.


    Par exemple pour une copie binaire, cela pourrait donner cela :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    // On crée le process en séparant bien les paramètres :
    Process proc = new ProcessBuilder("sxversions.exe", "--html").start();
    try {
    	// On ferme les flux inutilisés :
    	proc.getErrorStream().close();
    	proc.getOutputStream().close();
    	// Note : on pourrait aussi utiliser .redirectErrorStream()
    	// pour fusionner le flux d'erreur avec la sortie standard
     
    	// On récupère le flux de sortie standard du process :
    	InputStream input = proc.getInputStream();
    	try {
    		// On ouvre le fichier de destination :
    		File fAboutHtml = File.createTempFile("aboutVersions", ".html");
    		FileOutputStream output = new FileOutputStream(fAboutHtml);
    		try {
    			byte[] bytes = new byte[8192];
    			int len;
    			// Et on copie de l'un vers l'autre...
    			while ( (len=input.read(bytes)) >= 0 )
    				output.write(bytes, 0, len);
    		} finally {
    			output.close();
    		}
    	} finally {
    		input.close();
    	}			
    } finally {
    	// on détruit le process (au cas où il bloquerait)
    	proc.destroy();
    }
    Il n'y a pas besoin de faire une copie de char à moins de vouloir changer le charset pendant le traitement...

    a++

  5. #5
    Membre éclairé Avatar de kkt8
    Profil pro
    Inscrit en
    Janvier 2005
    Messages
    472
    Détails du profil
    Informations personnelles :
    Localisation : France, Isère (Rhône Alpes)

    Informations forums :
    Inscription : Janvier 2005
    Messages : 472
    Par défaut
    Merci, j'ai mieux compris ce que disait au niveau des flux (c'était pas vraiment clair pour moi)

    Bah pas mieux au niveau du temps, ça met toujours 5/6 secondes
    et sinon oui j'ai besoin de faire juste une modif sur un charset.

  6. #6
    Expert éminent
    Avatar de adiGuba
    Homme Profil pro
    Développeur Java/Web
    Inscrit en
    Avril 2002
    Messages
    13 938
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Java/Web
    Secteur : Transports

    Informations forums :
    Inscription : Avril 2002
    Messages : 13 938
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par kkt8 Voir le message
    Bah pas mieux au niveau du temps, ça met toujours 5/6 secondes
    Quel est le temps du processus seul lorsque tu le lances en ligne de commande ?

    Citation Envoyé par kkt8 Voir le message
    et sinon oui j'ai besoin de faire juste une modif sur un charset.
    Dans ce cas il faut englober tes InputStream/OutputStream dans des InputStreamReader/OutputStreamWriter, en spécifiant le bon charset...


    a++

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Lenteur d'accès à MySQL via le réseau
    Par fredouille31 dans le forum Requêtes
    Réponses: 1
    Dernier message: 10/02/2006, 08h39
  2. Lenteur et acces concurrent
    Par JeanMarc_T2k dans le forum Bases de données
    Réponses: 7
    Dernier message: 04/12/2004, 20h57
  3. question sur les vertex buffer et index buffer
    Par airseb dans le forum DirectX
    Réponses: 9
    Dernier message: 25/08/2003, 02h38

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo