Optimisation programme java

Signaler
-
Messages postés
16370
Date d'inscription
samedi 31 mai 2008
Statut
Modérateur
Dernière intervention
18 juillet 2021
-
Bonjour,
Je voudrais optimiser mes programmes en java (petits jeux, utilitaires) mais je ne trouves aucunes méthodes sur internet.. j'essaye toujours d'optimiser mes programmes du mieux que je le peux en réduisant la recherche dans des arraylist, le nombre de fps mais mon programme mange 30, 40 voir même 70% du processeur, aidez moi !
(j'utilise un paint component pour dessiner mes images, une jframe et un repaint pour actualiser les images/dessins)


Configuration: Windows / Firefox 90.0

2 réponses

Messages postés
16370
Date d'inscription
samedi 31 mai 2008
Statut
Modérateur
Dernière intervention
18 juillet 2021
2 856
Bonjour,

Tout d'abord, il ne faudrait pas trop généraliser, chaque programme est différent, et il n'y a pas de solution miracle, si un programme nécessite de faire beaucoup de calculs, alors il utilisera beaucoup le processeur.
Il y a toujours plusieurs manières de faire les choses, certaines sont meilleures que d'autres, mais cela dépend souvent du contexte, et à part avoir le code à disposition, impossible de te dire que c'est ici ou là qu'il faut améliorer ton programme.

Je me permets quand même quelques propositions :
1) Il est préférable d'exécuter ton programme directement en ligne de commande, pas depuis ton IDE (Eclipse, IntelliJ, etc.) qui vont rajouter des surcouches à ton programme qui vont augmenter l'utilisation du processeur.
2) Il est possible de monitorer n'importe quelle application Java, il existe de nombreux outils pour ça (gratuits ou payants) notamment quelques uns fournis avec le JDK
https://docs.oracle.com/javase/8/docs/technotes/guides/troubleshoot/tooldescr025.html
En les utilisant correctement tu pourrais identifier par exemple les méthodes les plus gourmandes, et savoir lesquelles améliorer en priorité.
3) Tu peux aussi faire une analyse du code avec des outils comme Sonar, qui pourraient t'indiquer des mauvaises pratiques de programmation, parfois sources de bugs et donc éventuellement de ralentissements.
https://www.sonarqube.org/sonarlint/
En entreprise, chaque code est systématiquement analysé, cela évite de laisser passer des bugs qui pourraient être évités.

	public static void Enemies(){
		if(asteroide_location.size()==0) {
			for(int i=0; i<asteroide_number; i++) {
				int[]loc= {r.nextInt(frame.getWidth()),(r.nextInt(7000)+250)*-1}; 
				int[]size = {r.nextInt(100)+asteroide_min_size_x, r.nextInt(50)+asteroide_min_size_y};
				asteroide_location.add(loc);
				asteroide_size.add(size);
				}
		}
		else {

			for(int i=asteroide_location.size()-1; i<asteroide_number; i++) {
				int[]loc= {r.nextInt(frame.getWidth()),(r.nextInt(7000)+250)*-1}; 
				int[]size = {r.nextInt(100)+asteroide_min_size_x, r.nextInt(100)+asteroide_min_size_y};
				asteroide_location.add(loc);
				asteroide_size.add(size);
			}
		}
	}
	public static boolean Colision(int posx1, int posy1, int sizew1, int sizeh1, int posx2, int posy2, int sizew2, int sizeh2, int decalage) {
		if(posx1>=posx2&&posx1<=posx2+sizew2) {
			if(posy1>=posy2&&posy1<=posy2+sizeh2) {
				return true;
			}
			else {
				return false;
			}
		}
		else {
			return false;
		}
	}

public void paintComponent(Graphics g) {
		super.paintComponent(g);
		if(left==true&&plane_location.x>0) {
			plane_location.x-=plane_speed;
		}
		if(right==true&&plane_location.x<frame.getWidth()-plane_size.getWidth()) {
			plane_location.x+=plane_speed;
		}
		if(top==true&&plane_location.y>=0) {
			plane_location.y-=plane_speed;
		}
		else if(plane_location.y<=frame.getContentPane().getHeight()-plane_size.height-50) {
			plane_location.y+=(int)(plane_speed/1.5);
		}
		switch(collisions) {	
			case 1:
				if(plane_location.y>=plane_location_save.y+150) {
					collisions = 0; 
				}
				plane_location.x+=asteroide_speed+plane_speed;
			case 2:
				if(plane_location.y<=plane_location_save.y-150) {
					collisions = 0; 
				}
				plane_location.y+=plane_speed+asteroide_speed;
			case 3:
				if(plane_location.x>=plane_location_save.x+150) {
					collisions = 0; 
				}
				plane_location.x+=plane_speed;
			case 4:
				if(plane_location.x<=plane_location_save.x-150) {
					collisions = 0; 
				}
				plane_location.x-=plane_speed;
			default:
				collisions = 0; 
		}
		g.drawImage(background_image, 0,0, frame.getContentPane().getWidth(), frame.getContentPane().getHeight(), this); 
		g.drawImage(plane_image, plane_location.x, plane_location.y, plane_size.width, plane_size.height, this); 
		for(int i=0; i<asteroide_number; i++) {
			asteroide_location.get(i)[1]+=asteroide_speed; 
			int posx = asteroide_location.get(i)[0]-15; 
			int posy = asteroide_location.get(i)[1]-15; 
			int sizew = asteroide_size.get(i)[0]-15; 
			int sizeh = asteroide_size.get(i)[1]-15; 
			if(Colision(plane_location.x-15, plane_location.y-15, plane_size.width-15, plane_size.height-15, posx, posy, sizew, sizeh, plane_speed)) {
				invincible = true;
				if(take_dommage==true) {
					take_dommage=false; 
					plane_life-=asteroide_dommage; 
					if(plane_life<=0) {
						System.exit(0);
					}
				}
				time=System.currentTimeMillis(); 
				if(time-timer>=delay_collision) {
					take_dommage=true;
					invincible = false; 
					timer = System.currentTimeMillis(); 
				}
			}
			g.drawImage(enemie_image, posx, posy, sizew, sizeh, this);
			if(posy>=frame.getHeight()+250+100) {
				asteroide_location.get(i)[0]=(r.nextInt(frame.getWidth()));
				asteroide_location.get(i)[1]=((r.nextInt(100)+250)*-1);
				asteroide_number+=1; 
				Enemies(); 
			}
		}
		g.fillRect(asteroide_number, asteroide_min_size_y, asteroide_min_size_x, asteroide_dommage);
		
		
	}
Messages postés
16370
Date d'inscription
samedi 31 mai 2008
Statut
Modérateur
Dernière intervention
18 juillet 2021
2 856
Pour monitorer il faut un code complet, le but étant d'analyser le comportement du programme pendant son exécution.

Pour obtenir des données pertinentes il faut aussi découper le code, car si tu n'as que trois méthodes avec tout ton code dedans, ça ne va pas beaucoup t'aider de savoir que c'est paintComponent qui consomme toutes les ressources, en vrai on s'en doute déjà un peu.

Mais quand on voit des boucles ou des if, si chaque cas est géré par des petites méthodes à part on pourra plus facilement se rendre compte que ce if là on ne l'appelle jamais alors que le else à côté est toujours exécuté, que la boucle for tourne beaucoup plus souvent qu'elle ne devrait, etc.

De manière générale, lorsque tu veux faire un affichage qui bouge petit à petit, il coûte généralement moins cher de dessiner le différentiel plutôt que de tout redessiner de zéro.
Exemple : tu as ton avion en 100,150 (de taille 20x30), qui se déplace en 110,155. Dans ce cas il suffit de redessiner ton image de fond sur la zone 20x30 ou était l'avion précédemment (en 100,150) avant de dessiner l'avion à sa nouvelle position en 120,155.
Cela t'évitera de redessiner l'intégralité de ton image sur toute une zone qui n'a pas été modifiée et qui devrait donc être affichée de la même manière d'une frame sur l'autre