Décalage de thread ... help please

[Résolu]
Signaler
Messages postés
41
Date d'inscription
dimanche 24 octobre 2004
Statut
Membre
Dernière intervention
29 juin 2005
-
Messages postés
41
Date d'inscription
dimanche 24 octobre 2004
Statut
Membre
Dernière intervention
29 juin 2005
-
Bonjour,

après plusieurs problèmes avec les threads, j'ai voulu vérifier quelque chose de simple. Or même ce code source simple ne fonctionne pas comme je veux. Voici le source :

///////// Class main /////////
public class Main {
/** Creates a new instance of Main */
public Main() {
}

public static void main(String[] args) {
NewClass thr = new NewClass();
thr.start();
}
}

///////////Class NewClass, celle du thread ////////////
public class NewClass extends Thread{

/** Creates a new instance of NewClass */
public NewClass() {
}
public void run()
{
while(true)
{
oh();
try
{
sleep(1000);
}
catch(InterruptedException e)
{
System.out.println("erreur thread update " + e);
}
}
}

public void oh()
{
Timestamp t3 = new Timestamp(0);
t3.setTime(System.currentTimeMillis());
System.out.println("update graphik " + t3.toString());
}
}

Ce que je veux faire est simple. Je veux que toutes les secondes, le thread m'affiche l'heure courante avec la fonction oh(). Le problème est qu'à l'exécution de ce prog, il se cré un décalage. La fonction oh() affiche :
12:08:18.117
12:08:19.118
12:08:20.119

Bref il se cré un décalage de 1 millisec toutes les secondes. Cette différence est très faible mais très importante pour moi. Pouvez-vous me corriger mon source pour qu'il m'affiche :
12:08:18.117
12:08:19.117
12:08:20.117

Un grand merci.

6 réponses

Messages postés
333
Date d'inscription
dimanche 25 mai 2003
Statut
Membre
Dernière intervention
23 novembre 2009
1
Pour préciser un peu,



Dans l'exemple au dessus, on triche évidemment en affichant une heure
qui est calculée en rajoutant n*1000 à une valeur d'origine.

Mais ce qui est important, c'est que l'affichage est déclencher de
façon très régulière (+- 1ms dans mon test), avec des écarts qui ne se
propagent pas.



On peut donc aussi moins tricher, en affichant l'heure réelle. Mais le résultat est moins beau !



update graphik 2005-05-10 13:48:08.175 -> 1115725688182

update graphik 2005-05-10 13:48:09.175 -> 1115725689175

update graphik 2005-05-10 13:48:10.176 -> 1115725690176

update graphik 2005-05-10 13:48:11.176 -> 1115725691176

update graphik 2005-05-10 13:48:12.176 -> 1115725692177

update graphik 2005-05-10 13:48:13.175 -> 1115725693175

update graphik 2005-05-10 13:48:14.176 -> 1115725694176


le code correspondant :

-----

public class Main {

/** Creates a new instance of Main */

public Main() {

}



public static void main(String[] args) {

NewClass thr = new NewClass();

thr.start();

}

}



///////////Class NewClass, celle du thread ////////////

class NewClass

extends Thread {



/** Creates a new instance of NewClass */

public NewClass() {

}



public void run() {

int n = 0;

long t0 = System.currentTimeMillis();

oh();

while (true) {

t0 +=1000;

try {

sleep(t0-System.currentTimeMillis());

}

catch (InterruptedException e) {

System.out.println("erreur thread update " + e);

}

oh();

}

}



public void oh() {

Timestamp t3 = new Timestamp(0);

t3.setTime(System.currentTimeMillis());

System.out.println("update graphik " + t3.toString()+" -> "+System.currentTimeMillis());

}

}



-----
Dobel
[Une fois rien, c'est rien; deux fois
rien, ce n'est pas beaucoup, mais pour trois fois rien, on peut déjà
s'acheter quelque chose, et pour pas cher]
Messages postés
16
Date d'inscription
samedi 7 mai 2005
Statut
Membre
Dernière intervention
18 mai 2005

Ton code n'est s'execute ni de facon instantanée, ni prioriairement sur les autres process, ce qui peut expliquer le decalage.



Pour le deuxieme probleme, tu peux toujours tenter un setPriority(MAX_PROPRITY)


Pour le premier, y'a pas de solution simple. Si tu arrives a calculer
le temps d'execution, tu peux ajuster la duree du sleep, mais ca
va dependre de la machine sur laquelle le code tourne...
Messages postés
333
Date d'inscription
dimanche 25 mai 2003
Statut
Membre
Dernière intervention
23 novembre 2009
1
ton code ne tient pas compte du temps de l'affichage. Je te propose une version modifiée.



On répcupère une valeur t0 de l'horloge, et on synchronise le programme par rapport à t0 +n*1000;





voilà le résultat que j'ai obtenu

A droite, l'heure système au moment de l'affichage dans la console. Ce n'est pas la même que l'heure qui est affichée à gauche

Les petites fluctuations correspondent à des délais d'affichages non constants, mais elles ne sont pas propagées.



update graphik 2005-05-10 13:30:27.078 -> 1115724627087

update graphik 2005-05-10 13:30:28.078 -> 1115724628079

update graphik 2005-05-10 13:30:29.078 -> 1115724629080

update graphik 2005-05-10 13:30:30.078 -> 1115724630080

update graphik 2005-05-10 13:30:31.078 -> 1115724631080

update graphik 2005-05-10 13:30:32.078 -> 1115724632080

update graphik 2005-05-10 13:30:33.078 -> 1115724633079

update graphik 2005-05-10 13:30:34.078 -> 1115724634080







public class Main {

/** Creates a new instance of Main */

public Main() {

}



public static void main(String[] args) {

NewClass thr = new NewClass();

thr.start();

}

}



///////////Class NewClass, celle du thread ////////////

class NewClass

extends Thread {



/** Creates a new instance of NewClass */

public NewClass() {

}



public void run() {

long t0 = System.currentTimeMillis();

oh(t0); // on affiche l'heure de t0. Cet affichage prend du temps.

while (true) {

t0 +=1000;// prochain repère : t0+1000

try {


sleep(t0-System.currentTimeMillis());//on fait une pause jusqu'à
atteindre l'heure t0+1000;

}

catch (InterruptedException e) {

System.out.println("erreur thread update " + e);

}

oh(t0);//on affiche t0+1000;

}

}



public void oh(long t) {

Timestamp t3 = new Timestamp(0);

t3.setTime(t);

System.out.println("update graphik " + t3.toString()+" -> "+System.currentTimeMillis());

}

}




A+


Dobel
[Une fois rien, c'est rien; deux fois rien,
ce n'est pas beaucoup, mais pour trois fois rien, on peut déjà
s'acheter quelque chose, et pour pas cher]
Messages postés
41
Date d'inscription
dimanche 24 octobre 2004
Statut
Membre
Dernière intervention
29 juin 2005

Salut Dobel,
merci pour tes réponses précises et rapides. Ca marche ! Réponse acceptée sans pb.
J'en profite de tes compétences pour te diriger vers un de mes posts que je n'ai toujours pas pu résoudre : http://www.javafr.com/forum.v2.aspx?ID=450878

Si toutefois t'avais une idée, ça serait génial.

Merci encore.
Messages postés
333
Date d'inscription
dimanche 25 mai 2003
Statut
Membre
Dernière intervention
23 novembre 2009
1
lol, c'est juste que j'ai constaté que ça allait être mon 201ème
message, donc je voulais poster quelque chose de pas trop con :D

Dobel
[Une
fois rien, c'est rien; deux fois rien, ce n'est pas beaucoup, mais pour
trois fois rien, on peut déjà s'acheter quelque chose, et pour pas cher]
Messages postés
41
Date d'inscription
dimanche 24 octobre 2004
Statut
Membre
Dernière intervention
29 juin 2005

ok, merci quand meme