[RESOLU] boucles et fonctions

fmd
Petit nouveau ! | 5 Messages

24 juil. 2014, 13:36

Bonjours à tous,
Je veux appliquer à une suite de mots l'agorithme de levenshtein de sorte à produire en sortie pour chaque mot entré une identification ou une proposition de rapprochement avec un mot du fichier de comparaison.
Le traitment par l'agorithme de levenshtein j'en ai fait une fonction dans un fichier externe.
De la suite de mots entrée je fais un tableau et ensuite j'applique une boucle foreach dans laquelle j'appelle mon fichier contenant la fonction et je demande l'affichage du résultat.
Problème : seul le traitment du premier mot est retourné.

Je bloque ... toute aide me serait bien utile.

Avatar du membre
Modérateur PHPfrance
Modérateur PHPfrance | 8758 Messages

26 juil. 2014, 09:39

salut,

sans code on ne peux pas vraiment t'aider.

sa tu tenté d'utiliser les fonctions de traitement de tableau comme array_map?

@+
Il en faut peu pour être heureux ......

Mammouth du PHP | 2278 Messages

26 juil. 2014, 10:05

Mais Levenshtein attend DEUX chaines... Où preds-tu la deuxième chaine avec ton foreach?
Vanitas vanitatum et omnia vanitas
Mes derniers livres :
Sauvez les Mots chez BoD,
Tous les chemins mènent à ROM chez BoD

fmd
Petit nouveau ! | 5 Messages

26 juil. 2014, 14:43

Bonjour,

La première chaîne de caractères est issue des mots entrés que je transforme en tableau pour isoler mes deux mots.
La deuxième chaîne est issu d'un fichier pdf décodé en tableau puis soumis à un explode.

array_map() ne me renvoie rien dans l'état actuel du code.

Sous cette forme le code me retourne X-fois l'écho présent dans la fonction pour chaque mot entré.

<?php


    $input1 = $_POST['phrase'];
echo "Entr&eacute;e : ".$input1."</br>";


$compte=str_word_count($input1, 0);
echo "Nombre de mots : ".$compte."</br>";


$tableau=explode(" ",$input1);

function mots($wort) {
    
include('class.pdf2text.php');
$a = new PDF2Text();
$a->setFilename('dico2.pdf');
$a->decodePDF();
$words=explode(" ",$a->output());

$shortest = -1;

// boucle sur les des mots pour trouver le plus près
foreach ($words as $word) {

    // calcule la distance avec le mot mis en entrée,
    // et le mot courant
    $lev = levenshtein($wort, $word);

    // cherche une correspondance exacte
    if ($lev == 0) {

        // le mot le plus près est celui-ci (correspondance exacte)
        $closest = $word;
        $shortest = 0;

        // on sort de la boucle ; nous avons trouvé une correspondance exacte
        break;
    }

    // Si la distance est plus petite que la prochaine distance trouvée
    // OU, si le prochain mot le plus près n'a pas encore été trouvé
    if ($lev <= $shortest || $shortest < 0) {
        // définition du mot le plus près ainsi que la distance
        $closest  = $word;
        $shortest = $lev;
    }
    
        echo "S&eacute;quence entr&eacute;e : ".$wort."<br>";
if ($shortest == 0) {
    echo "Correspondance exacte trouv&eacute;e : ".$closest."</br>";
} else {
    echo "Proposition : ".$closest. "</br>";
}   

}
}

foreach ($tableau as $wort) { 
mots($wort);
}

       ?>

Mammouth du PHP | 2278 Messages

26 juil. 2014, 15:09

Si je comprends bien tu cherches le mot prévu dont le levenshtein est le plus proche du mot entré (ceci pour chaque mot)?
Vanitas vanitatum et omnia vanitas
Mes derniers livres :
Sauvez les Mots chez BoD,
Tous les chemins mènent à ROM chez BoD

fmd
Petit nouveau ! | 5 Messages

26 juil. 2014, 19:39

c'est exactement cela ...
j'entre une série de mots aux pluriel, conjuguées ou déclinées, l'automate va, pour chaque mot, parcourir le fichier dico2 en appliquant l'algorithme de levensthein puis me retourner les valeurs identiques ou proches pour chaque mot entré.
Cela fonctionne très bien avec un seul terme en entrée.

Mammouth du PHP | 2278 Messages

26 juil. 2014, 20:40

Il faut deux boucles: _un truc dans ce genre
$liste = array(); //les mots à tester
$dico = array(); //le dictionnaire
$trouve = false;
$nb_liste = count($liste);
$nb_dico = count ($dico);
$limite_diff = 1;
$indice_liste = 0;
while (($trouve == false) and ($indice_liste < $nb_liste))
{ //1
  $trouve_1 = false;
  $indice_dico = 0;
   $le_mot = $liste[$indice_liste];
   while (($trouve_2 == false) and ($indice_dico < $nb_dico))
    {//2
         $le_dico = $dico[$indice_dico];
         if( levenshtein($$le_mot, $le_dico) < $limitre_diff;)
         {//3
            $trouve_2 = true;
        }
        else
        {
           $indice_dico ++;
        }//3
    } //2
   if ($trouve_2 == true)
   {
       
   }
   else
    {

    }
$indice_liste ++;
}
mais je me demande si ce serait mieux avec le dico en base de données avec la fonction like
Vanitas vanitatum et omnia vanitas
Mes derniers livres :
Sauvez les Mots chez BoD,
Tous les chemins mènent à ROM chez BoD

fmd
Petit nouveau ! | 5 Messages

27 juil. 2014, 12:06

merci Sirakawa,
Ton code est moins tordu que le mien.
Effectivement, s'appuyer sur une base de données faciliterait les choses, mais je veux tout faire en php sur la base de fichiers.
Je mets quelle variable en echo ?

Mammouth du PHP | 2278 Messages

27 juil. 2014, 15:27

En fait, une BDD n'est qu'un système de fichiers optimisé pour un certain genre de travail.
Moi, je me sers de la base lexique que j'ai péchée à Paris XI, je crois, et qui est maintenant à l'Université se Savoie et adaptée à mes besoins. http://www.lexique.org/
Vanitas vanitatum et omnia vanitas
Mes derniers livres :
Sauvez les Mots chez BoD,
Tous les chemins mènent à ROM chez BoD

fmd
Petit nouveau ! | 5 Messages

28 juil. 2014, 11:02

Oui, un grand merci pour l'info. En fait ce n'est pas pour du français que je veux coder. Par contre les fichiers sont très intructifs et je vais les reprendre pour mes proprs besoins.
Je connais plutôt bien mysql et postgresql, mais pour l'instant je préfère utiliser un pdf pour les tests.
Encore merci