problème de délais

Répondre


Cette question est un moyen d’empêcher des soumissions automatisées de formulaires par des robots.
Smileys
:D :) :( :o :shock: :? 8-) :lol: :x :P :oops: :cry: :evil: :twisted: :roll: :wink: :!: :?: :idea: :arrow: :| :mrgreen: =D> #-o =P~ :^o :non: :priere: 8-|
Voir plus de smileys
  Revue du sujet
 

  Étendre la vue Revue du sujet : problème de délais

par toony.m » 15 avr. 2008, 11:10

Bon ok, j'avoue avoir été un peu faignant sur ce coup là... :wink:

La requete qui me prends le plus le temps est bien celle là:
// Recherche de toutes les entreprises
$requete_calcul="SELECT nom_entreprise,id_entreprise,departement FROM xtra_entreprise WHERE statut='Cible' AND (secteur_activite LIKE '%".$requete_secteurs.";%') AND departement IN ('".$zone1.";','".$localisationE.";') ORDER BY departement ASC, nom_entreprise ASC ";
$result_calcul=mysql_query ($requete_calcul) or die (mysql_error());
$total_E=mysql_num_rows($result_calcul);

echo "<table width=\"740\" border=\"0\" align=\"center\" cellpadding=\"0\" cellspacing=\"0\">
	  </tr>
	  <tr style=\"color:#FFFFFF; background-color:#FF8F18\">
		<td width=\"30\" align=\"center\">Dpt</td>
		<td width=\"560\">Entreprise</td>
		<td width=\"70\" align=\"right\">Contact</td>
		<td width=\"80\" align=\"center\">Statut</td>
	  </tr>";
$megatotal_g=0;
while ($row=mysql_fetch_array($result_calcul)){
	echo "<tr ";
			// on surligne les lignes si cibler_pour ou ne_pas_cibler_pour contiennent un message
			$requete_d="SELECT id_entreprise FROM xtra_entreprise WHERE id_entreprise='".$row['id_entreprise']."' AND cibler_pour LIKE '%MI".$liste_missions.";%'";
			$requete_e="SELECT id_entreprise FROM xtra_entreprise WHERE id_entreprise='".$row['id_entreprise']."' AND ne_pas_cibler_pour LIKE '%MI".$liste_missions.";%'";
			$resultat_d=mysql_query ($requete_d) or die (mysql_error());
			$total_d=mysql_num_rows($resultat_d);
			
			$resultat_e=mysql_query ($requete_e) or die (mysql_error());
			$total_e=mysql_num_rows($resultat_e);
			if($total_d>0){ echo "style=\"background-color:#b9f1ff\" "; }
			if($total_e>0){ echo "style=\"background-image:url(images/pas_cibler.gif)\" "; }
	echo ">
			<td align=\"center\">".$departement."</td>
			<td><A href=\"frame_contact.php?id=".$row['id_entreprise']."&histo=raz\" target=\"centre\" class=\"ciblage\">".$row['nom_entreprise']."</A></td>
			<td align=\"right\">";
				
			$requete_g="SELECT id_profil FROM xtra_profil WHERE id_entreprise='".$row['id_entreprise']."' AND C_codification_metier LIKE '%".$requete_metier."%'";
			$resultat_g=mysql_query ($requete_g) or die (mysql_error());
			$total_g=mysql_num_rows($resultat_g);
			
			$requete_f="SELECT id_profil FROM xtra_profil WHERE id_entreprise='".$row['id_entreprise']."'";
			$resultat_f=mysql_query ($requete_f) or die (mysql_error());
			$total_f=mysql_num_rows($resultat_f);
			if($total_g>0){ echo "<span style=\"color:#FF6600; font-weight:bold\">"; } else { echo "<span>"; }
			echo "$total_g/$total_f</span>";
echo "</td>
		<td align=\"center\">";
			$requete_c="SELECT identifie FROM xtra_entreprise WHERE id_entreprise='".$row['id_entreprise']."' AND identifie LIKE '%MI".$liste_missions.";%'";
			$resultat_c=mysql_query ($requete_c) or die (mysql_error());
			$total_c=mysql_num_rows($resultat_c);
			if($total_c>0){ echo "<span style=\"color:#006600\">IDENTIFI&Eacute;</span>"; }
			else { echo "<span style=\"color:#b4b4b4; font-size:9px;\">A identifier</span>"; }
echo "</td>
</tr>";
			$megatotal_g=$megatotal_g+$total_g;

}
echo "</table>";
Ce qui me faire perdre du temps, ce sont tous les petits select dans la boucle while de ma grande requete, et pour faire un JOIN la dedans et tout en une requete, je vois absolument pas ! :shock:

par Berzemus » 15 avr. 2008, 11:00

hum hum...
tout cela est intéressant mais par exemple sur ton exemple, je perds ma condition WHERE et les résultats ne sont plus les mêmes.
un petit effort quand même.. :roll: Il suffit de la rajouter (un oublie de ma part :wink: ):

Code : Tout sélectionner

select xtra_mission.intitule_post, xtra_mission.id_mission, xtra_mission.id_entreprise, xtra_entreprise.nom_entreprise from xtra_mission inner join xtra_entreprise on xtra_mission.id_entreprise = xtra_entreprise.id_entreprise where xtra_mission.agence='$agence' and xtra_mission.archive='0'
Tu peux chronomètrer avec un script de timer (ou en utilisant microtime() ). Il faudrait aussi voir si les champs que tu utilises dans tes where font partie d'un index. S'ils sont indexés, MYSQL prendra beaucoup moins de temps à les trouver.

par toony.m » 15 avr. 2008, 10:55

hum hum...
tout cela est intéressant mais par exemple sur ton exemple, je perds ma condition WHERE et les résultats ne sont plus les mêmes.

y a t-il moyen de savoir quelle requete prends le plus de temps à s'exécuter ?

En observant bien la barre d'état, je remarque que ca bouge beaucoup en fait :
la page se charge puis s'arrete, puis se recharge, puis s'arrete de nouveau, se recharge et affiche les résultats.
Je me demande si cette perte de temps n'est pas un probleme d'organisation dans ma page finalement...

Mais merci pour ton travail! :D

par Berzemus » 15 avr. 2008, 10:04

Oh, pas si motivé que ça hein :roll: .. je vais juste regarder un peu, et voir ou je peux donner une piste ou deux vers une meilleure application du langage sql..

Un premier exemple, ce bloc-ci:
// Affichage des missions sous forme de SELECT
$requete="SELECT * FROM xtra_mission WHERE agence='$agence' AND archive='0'";
$result=mysql_query ($requete) or die (mysql_error());
while ($row=mysql_fetch_array($result)) {
    $intit_poste=$row['intitule_poste'];
    $id_mission=$row['id_mission'];
    $identreprise=$row['id_entreprise'];
    
    $requete2="SELECT nom_entreprise FROM xtra_entreprise WHERE id_entreprise='$identreprise'";
    $result2=mysql_query ($requete2) or die (mysql_error());
    while ($row2=mysql_fetch_array($result2)) {
        $nomE1=$row2['nom_entreprise'];
    }
    
    echo "<OPTION value='$id_mission' ";
    if (isset($liste_missions)){if (ereg($id_mission,$liste_missions)){echo "selected";}}
    echo ">$nomE1 - $intit_poste</OPTION>";
} 
Il me semble qu'en utilisant un simple JOIN, et en organisant un peu mieux le code (pour la lisibilité), ça peux correspondre à ceci:
$requete="select  xtra_mission.intitule_post, 
		xtra_mission.id_mission, 
		xtra_mission.id_entreprise, 
		xtra_entreprise.nom_entreprise 
from xtra_mission
inner join xtra_entreprise 
	on xtra_mission.id_entreprise = xtra_entreprise.id_entreprise";
	
$result=mysql_query ($requete) or die (mysql_error());
while ($row=mysql_fetch_array($result)) 
	{
    $intit_poste	= $row['intitule_poste'];
    $id_mission		= $row['id_mission'];
    $identreprise	= $row['id_entreprise'];
    $nomE1			= $row['nom_entreprise'];
	
	echo "<OPTION value='$id_mission' ";
    
	if (isset($liste_missions) && ereg($id_mission,$liste_missions))
		echo "selected";
    
	echo ">$nomE1 - $intit_poste</OPTION>";
	}
Et Hop, plus qu'une seule requête !! Et encore, j'ai été bien verbeux, y'a moyen de la raccourcir facilement.

Pour te faire une bonne idée, documente-toi sur la syntaxe JOIN, GROUP BY, et les sous-requêtes. (et utiliser un * dans un select, c'est déconseillé. Ne prend que ce dont tu as besoin). SQL sait faire plein de chôses tout seul, c'est dommage de s'en priver.

Le tout sans même utiliser de sous-requêtes..

En plus, comme la plupart de tes requêtes ne renvoinent qu'un seul résultat (a ce que je vois), y'a plein de place pour optimiser tout ça 8-) ( les deux premières peuvent être réunies en une seule)

par toony.m » 15 avr. 2008, 08:53

Je suis tombé sur quelqu'un de motivé apparemment... :wink:

Je passe les détails de connection, etc...voila simplement les requetes :
<?
$requete_a="SELECT localisation,codif_activ,codif_metier FROM xtra_mission WHERE id_mission='$liste_missions'";
$result_a=mysql_query ($requete_a) or die ("1".mysql_error());
while ($row_a=mysql_fetch_array($result_a)) {
	$codif_activ=$row_a['codif_activ'];
	$codif_metier=$row_a['codif_metier'];
	$localisationE=$row_a['localisation'];
	$localisationE=substr($localisationE,0,(strlen($localisationE)-1));
}

$requete_b="SELECT * FROM xtra_geociblage WHERE departement IN ('".$localisationE."')";
$result_b=mysql_query ($requete_b) or die ("2".mysql_error());
while ($row_b=mysql_fetch_array($result_b)) {
	$zone1=substr($row_b['zone1'],0,(strlen($row_b['zone1'])-1));
	$zone2=substr($row_b['zone2'],0,(strlen($row_b['zone2'])-1));
	$zone3=substr($row_b['zone3'],0,(strlen($row_b['zone3'])-1));
	$zone1=ereg_replace(";",";','",$zone1);
	$zone2=ereg_replace(";",";','",$zone2);
	$zone3=ereg_replace(";",";','",$zone3);
}

$liste_secteurs=substr($codif_activ,0,(strlen($codif_activ)-1));
$requete_secteurs=str_replace(';',';%\' OR secteur_activite LIKE \'%',$liste_secteurs);

$liste_metier=substr($codif_metier,0,(strlen($codif_metier)-1));
$requete_metier=str_replace(';',';%\' OR C_codification_metier LIKE \'%',$liste_metier);



// Affichage des missions sous forme de SELECT
$requete="SELECT * FROM xtra_mission WHERE agence='$agence' AND archive='0'";
$result=mysql_query ($requete) or die (mysql_error());
while ($row=mysql_fetch_array($result)) {
	$intit_poste=$row['intitule_poste'];
	$id_mission=$row['id_mission'];
	$identreprise=$row['id_entreprise'];
	
	$requete2="SELECT nom_entreprise FROM xtra_entreprise WHERE id_entreprise='$identreprise'";
	$result2=mysql_query ($requete2) or die (mysql_error());
	while ($row2=mysql_fetch_array($result2)) {
		$nomE1=$row2['nom_entreprise'];
	}
	
	echo "<OPTION value='$id_mission' ";
	if (isset($liste_missions)){if (ereg($id_mission,$liste_missions)){echo "selected";}}
	echo ">$nomE1 - $intit_poste</OPTION>";
}

 
 
 // Liste des secteurs sous forme de SELECT
 $liste_secteurs=ereg_replace(";",",",$liste_secteurs);
 $requete="SELECT codif_activite FROM xtra_codif_activite WHERE id_codif_activite IN (".$liste_secteurs.")";
 $resultat=mysql_query ($requete) or die (mysql_error());
 while($row=mysql_fetch_array($resultat)){
	 $liste_ok .=$row['codif_activite'].", ";
 }
 echo "<BR>Secteur(s) d'activité : <span style=\"color:#FF6600;\">".substr($liste_ok,0,(strlen($liste_ok)-2))."</span>"; 
 
 
  // Liste des métiers sous forme de SELECT
 $liste_metier=ereg_replace(";",",",$liste_metier);
 $requete="SELECT codif_metier FROM xtra_codif_metier WHERE id_codif_metier IN (".$liste_metier.")";
 $resultat=mysql_query ($requete) or die (mysql_error());
 while($row2=mysql_fetch_array($resultat)){
	 $liste_ok2 .=$row2['codif_metier'].", ";
 }
 echo "<BR>Métier(s) : <span style=\"color:#FF6600;\">".substr($liste_ok2,0,(strlen($liste_ok2)-2))."</span>"; 

// Recherche de toutes les entreprises
$requete_calcul="SELECT nom_entreprise,id_entreprise,departement FROM xtra_entreprise WHERE statut='Cible' AND (secteur_activite LIKE '%".$requete_secteurs.";%') AND departement IN ('".$zone1.";','".$localisationE.";') ORDER BY departement ASC, nom_entreprise ASC ";
$result_calcul=mysql_query ($requete_calcul) or die (mysql_error());
$total_E=mysql_num_rows($result_calcul);

echo "<table width=\"740\" border=\"0\" align=\"center\" cellpadding=\"0\" cellspacing=\"0\">
	  </tr>
	  <tr style=\"color:#FFFFFF; background-color:#FF8F18\">
		<td width=\"30\" align=\"center\">Dpt</td>
		<td width=\"560\">Entreprise</td>
		<td width=\"70\" align=\"right\">Contact</td>
		<td width=\"80\" align=\"center\">Statut</td>
	  </tr>";
$megatotal_g=0;
while ($row=mysql_fetch_array($result_calcul)){
	echo "<tr ";
			// on surligne les lignes si cibler_pour ou ne_pas_cibler_pour contiennent un message
			$requete_d="SELECT id_entreprise FROM xtra_entreprise WHERE id_entreprise='".$row['id_entreprise']."' AND cibler_pour LIKE '%MI".$liste_missions.";%'";
			$requete_e="SELECT id_entreprise FROM xtra_entreprise WHERE id_entreprise='".$row['id_entreprise']."' AND ne_pas_cibler_pour LIKE '%MI".$liste_missions.";%'";
			$resultat_d=mysql_query ($requete_d) or die (mysql_error());
			$total_d=mysql_num_rows($resultat_d);
			
			$resultat_e=mysql_query ($requete_e) or die (mysql_error());
			$total_e=mysql_num_rows($resultat_e);
			if($total_d>0){ echo "style=\"background-color:#b9f1ff\" "; }
			if($total_e>0){ echo "style=\"background-image:url(images/pas_cibler.gif)\" "; }
	echo ">
			<td align=\"center\">".$departement."</td>
			<td><A href=\"frame_contact.php?id=".$row['id_entreprise']."&histo=raz\" target=\"centre\" class=\"ciblage\">".$row['nom_entreprise']."</A></td>
			<td align=\"right\">";
				
			$requete_g="SELECT id_profil FROM xtra_profil WHERE id_entreprise='".$row['id_entreprise']."' AND C_codification_metier LIKE '%".$requete_metier."%'";
			$resultat_g=mysql_query ($requete_g) or die (mysql_error());
			$total_g=mysql_num_rows($resultat_g);
			
			$requete_f="SELECT id_profil FROM xtra_profil WHERE id_entreprise='".$row['id_entreprise']."'";
			$resultat_f=mysql_query ($requete_f) or die (mysql_error());
			$total_f=mysql_num_rows($resultat_f);
			if($total_g>0){ echo "<span style=\"color:#FF6600; font-weight:bold\">"; } else { echo "<span>"; }
			echo "$total_g/$total_f</span>";
echo "</td>
		<td align=\"center\">";
			$requete_c="SELECT identifie FROM xtra_entreprise WHERE id_entreprise='".$row['id_entreprise']."' AND identifie LIKE '%MI".$liste_missions.";%'";
			$resultat_c=mysql_query ($requete_c) or die (mysql_error());
			$total_c=mysql_num_rows($resultat_c);
			if($total_c>0){ echo "<span style=\"color:#006600\">IDENTIFI&Eacute;</span>"; }
			else { echo "<span style=\"color:#b4b4b4; font-size:9px;\">A identifier</span>"; }
echo "</td>
</tr>";
			$megatotal_g=$megatotal_g+$total_g;

}
echo "</table>";
?>
Si on peut simplifier ça et ba chapeau!
Dans tous les cas l'affichage des différents select ne peut pas se faire autrement que requete par requete je pense.

par Berzemus » 14 avr. 2008, 16:43

Ah.. ben je serais pas étonné que, en fait, y'a moyen de résumer tout ça en quelques, voir une, requête(s) seulement..

Et n'aie pas peur de la longueur, tant que mets des tags
 autour de ton code, tu peux poster tout ce que tu veux comme longueur..  :wink:

par toony.m » 14 avr. 2008, 16:32

Je peux pas faire de copier coller, ca serait trop long.
Disons que schématiquement parlant, ça donne ça :

requete1 type SELECT
requete2 type SELECT en fonction du resultat de requete 1

requete3 type SELECT
tant que resultat {

requete4 type SELECT

}

requete5 type SELECT
requete6 type SELECT

requete7 type SELECT en fonction du resultat de requete 2
tant que resultat {

requeteA type SELECT
requeteB type SELECT
requeteC type SELECT
requeteD type SELECT
requeteE type SELECT
requeteF type SELECT

}

Ce qui doit prendre le temps, c'est d'executer les 6 requetes qui sont dans la boucle à chaque fois mais je vois pas comment faire autrement...

par Berzemus » 14 avr. 2008, 15:54

oui c'est vrai que d'un certain côté, optimiser un peu ta requête sql pourrait t'aider.. :roll:

Juste par curiosité, on pourrait jeter un oeil à la requête, et au traitement de celui-ci ?

par toony.m » 14 avr. 2008, 15:51

Ouhla!
Tout se langage m'est totalement inconnu!!

Explain ?
index? :shock:

je vais faire quelques recherches!

par Alkann » 14 avr. 2008, 15:44

As tu essayer de faire un Explain de ta requête afin de voir où elle prends le plus de temps.
As tu mis des index pour augmenter les performances ?

par toony.m » 14 avr. 2008, 15:15

Tout cela à l'air bien alléchant et merci beaucoup!
Mais je n'ai pas la possibilité de rajouter de plugin chez mon hébergeur (enfin je crois (AMEN)).

:?

D'autres solutions ?

par Berzemus » 14 avr. 2008, 15:06

Tu peux mettre le résultats de tes requêtes dans un cache, par exemple.

http://www.phpfrance.com/forums/voir_re ... php#242869

problème de délais

par toony.m » 14 avr. 2008, 14:40

Bonjour à tous,

J'ai requete qu'y dure 7 à 10 sec quand je l'exécute dans ma page php.
Et a force, ça devient très long, quand on y retourne toute les 3 secondes.
Je cherche un moyen de stocker les résultat une bonne fois pour toute quelque part (tableau?) pour y accéder plus rapidement et éviter le re-calcul de cette requete.
J'ai remarqué que si je ne fais pas appel à d'autres page entre temps, un coup d'historique -1 me sort la page tres rapidement.

Mais est-il possible de faire cela autrement, avec des sessions notamment ?

Est-ce raisonnable ou faut-il que je change ma façon d'opérer ?