Précédent   Forum des professionnels en informatique > Logiciels > Solutions d'entreprise > Business Intelligence > SAS > SAS Base
SAS Base Forum d'entraide sur SAS base : étape data, procédures non statistiques, procédures non graphiques, SQL
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse Proposer ce sujet en actualité
 
Outils de la discussion
Publicité
'
Vieux 14/10/2011, 11h54   #1
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Par défaut Codage des caractères

Bonjour,

je viens de récupérer un fichier issu d'une agrégation je suppose de plusieurs autres fichiers.
Il semble que le codage de caractère ne soit pas le même pour toutes les observations, pour une majorité la codification est bonne, pour certains en revanche, les caractères accentués posent problèmes

ainsi par exemple j'ai pour la commune de Saint Gély du Fesc

"ST GéLY DU FESC"

Le E accentué est lu pour cette observation é

De quel codage de caractère s'agit-il ?

Il en est de même pour un certain nombre d'autres caractères accentués sur un certain nombre d'observations.
Pour ceux-ci j'aimerais retomber sur une écriture normale, quelqu'un a t il une idée comment je pourrais procéder sans avoir à programmer une recodification "manuelle" pour tous ces caractères ?

Une fonction pré-existante de SAS avec les bons paramètres pourrait-elle faire ça ?

De sorte ajouter des lignes qui puisse rétablir le bon codage de caractère avec un code du type

Code :
1
2
 
IF INDEX(texte,'A9'x) then texte=fonction(texte);
qui transforme "ST GéLY DU FESC" en "ST GÉLY DU FESC"

Voilà si vous avez des idées ...
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 14/10/2011, 19h00   #2
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
personne n'a quelques idées ou n'a jamais rencontré ce problème ?
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 18/10/2011, 10h12   #3
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
bonjour,

il semble en fait qu'une partie des observations soient codées en UTF8 , je cherche a faire une table de passage des codes caractères usuels aux codes UTF8.

Pour cela il me faudrait un format me permettant de passer d'un binaire sur 8 caractère à un entier.

par exemple que '10101001' me donne 169.
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 18/10/2011, 14h49   #4
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Finalement je me suis débrouillé avec la ligne suivante

Code :
texte_modif=put(texte,$utf8x10.);
Mais cela ne règle pas tous les problèmes,
il y a encore des observations qui sont codés à la base en "code page 850" et UTF8.

J'aimerais savoir s'il y a un moyen simple de faire la table de correspondance entre les caractères cp850 et les caractères habituels SAS, à savoir une table
avec une variable num de 128 à 255, une variable cp850 avec le caractère en "code page 850" et la variable std en caractère standard (std=byte(num)

par exemple pour num=130 cp850='é' std=','
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 18/10/2011, 15h27   #5
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
euh... c'est peut être idiot ce que je vais indiquer mais quelques fonctions TRANWRD doivent suffire (puisque seules les lettres accentuées posent difficultés)

Code :
1
2
3
4
5
6
7
8
9
10
 
DATA test;
input x $25.;
cards;
ST GéLY DU FESC
;
DATA toto;SET test;
   x=tranwrd(x,'é','É');
run;
proc print;run;
bon évidemment, on pourrait rêver d'une solution plus "pure" mais si tu es pressé...

(où alors il y a quelque chose qui m'échappe...)

a+

Sébastien Ringuedé
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 18/10/2011, 15h40   #6
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Citation:
Envoyé par z6c3po Voir le message
euh... c'est peut être idiot ce que je vais indiquer mais quelques fonctions TRANWRD doivent suffire (puisque seules les lettres accentuées posent difficultés)

Code :
1
2
3
4
5
6
7
8
9
10
 
DATA test;
input x $25.;
cards;
ST GéLY DU FESC
;
DATA toto;SET test;
   x=tranwrd(x,'é','É');
run;
proc print;run;
bon évidemment, on pourrait rêver d'une solution plus "pure" mais si tu es pressé...

(où alors il y a quelque chose qui m'échappe...)

a+

Sébastien Ringuedé

Merci de ta participation, enfin quelqu'un ! ^^

Et bien...

J'ai commencé par des tranwrd, mais ce fichier est une compilation de fichiers en provenance de plusieurs destinations, eux mêmes étant en provenance de plusieurs destinations.
Certaines parties du fichier on donc subies de multiples exportations et les exportations n'ont pas toujours été bien gérées, d'où mes problèmes.

Bien sûr naïvement j'y suis allé le coeur vaillant en écrivant quelques transword... puis quelques autres, et j'arrive à des choses comme ça par exemple

Code :
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
texte2=tranwrd(texte2,'Ï¿½Ï¿½Ï¿½Ï¿½Ï¿½Ï¿½','E');
texte2=tranwrd(texte2,'Ï¿½Ï¿½','E');
texte2=tranwrd(texte2,'°','° ');
texte2=tranwrd(texte2,'°¨','° ');
texte2=tranwrd(texte2,'Ã?Â?Ã?Â','E');
texte2=tranwrd(texte2,'Ã?°','° ');
texte2=tranwrd(texte2,'ŀŒ','OE');
texte2=tranwrd(texte2,'Ã?ª','Ê');
texte2=tranwrd(texte2,'Ã?¢','Â');
texte2=tranwrd(texte2,'Ã?¨','È');
texte2=tranwrd(texte2,'Ã?Â?','É');
texte2=tranwrd(texte2,'é','É');
texte2=tranwrd(texte2,'è','È');
texte2=tranwrd(texte2,'ç','Ç');
texte2=tranwrd(texte2,'â','Â');
texte2=tranwrd(texte2,'ê','Ê');
texte2=tranwrd(texte2,'ô','Ô');
texte2=tranwrd(texte2,'û','Û');
texte2=tranwrd(texte2,'ï','Ï');
texte2=tranwrd(texte2,'BƒT','BÂT');
texte2=tranwrd(texte2,'CHƒT','CHÂT');
texte2=tranwrd(texte2,'ÀŠ','Â');
texte2=tranwrd(texte2,'À°','É');
i=INDEX(texte2,'ƒ');
IF i>0 then do; IF substr(texte2,i-1,1) IN (' ','A','B','C','D','E','F','G','H','I','J','K',
'L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z')
AND substr(texte2,i+1,1) IN (' ','A','B','C','D','E','F','G','H','I','J','K',
'L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z')
then substr(texte2,i,1)='Â';end;
texte2=tranwrd(texte2,'ë','Ë');
texte2=tranwrd(texte2,'î','Î');
texte2=tranwrd(texte2,'È','È');
texte2=tranwrd(texte2,' ÃÂ* ',' À ');
texte2=tranwrd(texte2,'Þ','Ê');
texte2=tranwrd(texte2,'ö','U');
texte2=tranwrd(texte2,'À¡','Ç');
texte2=tranwrd(texte2,'À¹','É');
texte2=tranwrd(texte2,'€Š','É');
texte2=tranwrd(texte2,'é','É');
texte2=tranwrd(texte2,'Ã?©','É');
texte2=tranwrd(texte2,'I¿½','Â');
texte2=tranwrd(texte2,'½','OE');
texte2=tranwrd(texte2,'è','È');
texte2=tranwrd(texte2,'ê','Ê');
texte2=tranwrd(texte2,'ç','Ç');
texte2=tranwrd(texte2,'î','Î');
texte2=tranwrd(texte2,'É','É');
texte2=tranwrd(texte2,'ô','Ô');
texte2=tranwrd(texte2,'â','Â');
texte2=tranwrd(texte2,'Ê','É');
texte2=tranwrd(texte2,'È','È');
texte2=tranwrd(texte2,'Ô','Ô');
texte2=tranwrd(texte2,'ï','Ï');
texte2=tranwrd(texte2,'Ç','Ç');
texte2=tranwrd(texte2,'Â','Â');
texte2=tranwrd(texte2,'ë','Ë');
texte2=tranwrd(texte2,'û','Û');
texte2=tranwrd(texte2,'Ë','Ë');
texte2=tranwrd(texte2,' Ã*',' À ');
texte2=tranwrd(texte2,' À ',' À ');
/*num2=index(texte2,'C3'x);num2=rank(substr(texte2,num2-1,1));numhex2=put(num2,hex2.);*/
texte2=tranwrd(texte2,'C38F'x,'I');
texte2=tranwrd(texte2,'Û','Û');
texte2=tranwrd(texte2,'ÃŽ','Î');
texte2=tranwrd(texte2,'þ','Ç');
texte2=tranwrd(texte2,'ä','Ë');
texte2=tranwrd(texte2,'ü','Ü');
texte2=tranwrd(texte2,'ö','Ô');
texte2=tranwrd(texte2,'ÿ','Y');
texte2=tranwrd(texte2,'C3A0'x,' À '); 
texte2=tranwrd(texte2,'C396'x,'Ô');
texte2=tranwrd(texte2,'Ì','U');
Attention je n'ai pas tout mis ce n'est qu'une partie du code....

Il y a encore plein de cas non gérés... d'où à présent l'idée de partir des tables de caractères et construire automatiquement les équivalences surtout maintenant que j'ai compris que l'essentiel des problèmes proviennent d'une mauvaise gestion de l'UTF8 lors des diverses exportations, mâtiné de passage incontrôlés d'OEM à ANSI ou vice-versa.
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 14h43   #7
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
bon, c'est effectivement pas amusant ton affaire...

j'ai essayé de bricoler des trucs avec ça :

http://www.kostis.net/charsets/

j'ai lu tous les charsets avec SAS pour voir ce que ces caractères exotiques pouvaient devenir une fois dans une table SAS... pas vraiment utile en fait...

mais, autre possibilité : je devine que tes noms de commune, ce n'est qu'un début (et qu'ensuite, tu continueras le com-bat = d'autres variables seront à "convertir").

Pourquoi ne pas partir d'une liste des communes propres (l'INSEE en propose une) pour construire ta table de conversion ?

Ça risque de ne pas être simple puisque, par exemple, pour le É tu as trouvé au moins 10 chaines... ('é','Ã?Â?', 'é', 'À°', 'À¹', '€Š', 'é', 'Ã?©', 'É' et 'Ê')

et que tes TRANSWRD devront porter un premier sur les chaînes les plus longues pour finir avec les chaines les plus petites....

a+

Sébastien Ringuedé
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 17h12   #8
Modérateur
 
Homme Samir SELMANE
Consultant en Business Intelligence
Inscription : février 2011
Messages : 1 011
Détails du profil
Informations personnelles :
Nom : Homme Samir SELMANE
Localisation : France

Informations professionnelles :
Activité : Consultant en Business Intelligence
Secteur : Conseil

Informations forums :
Inscription : février 2011
Messages : 1 011
Points : 1 712
Points : 1 712
Citation:
Envoyé par jerome_pdv2 Voir le message
Finalement je me suis débrouillé avec la ligne suivante

Code :
texte_modif=put(texte,$utf8x10.);
Mais cela ne règle pas tous les problèmes,
il y a encore des observations qui sont codés à la base en "code page 850" et UTF8.

J'aimerais savoir s'il y a un moyen simple de faire la table de correspondance entre les caractères cp850 et les caractères habituels SAS, à savoir une table
avec une variable num de 128 à 255, une variable cp850 avec le caractère en "code page 850" et la variable std en caractère standard (std=byte(num)

par exemple pour num=130 cp850='é' std=','

Hello,
Vu que ton fichier contient plusieurs codages , j’imagine qu’il est résultat d’une fusion de plusieurs fichiers issus de plusieurs sources , As-tu un moyen ( critère) pour découper ton fichier selon la source, et traiter chacun avec le format approprié et fusionner le tout par la suite ?
s_a_m est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 17h14   #9
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Effectivement il y a des noms de commune, mais aussi des lieux dits, des adresses (nom de rue etc...).

Je n'ai donc pas de corpus exhaustif auquel comparer...

Alors je ne sais pas vraiment ou je vais, je me heurte essentiellement a une programmation complexe à priori, je ne désespère pas de la simplifier.

Par contre on a une régle de décision possible, lorsqu'on a plusieurs "transcodages" possible, on arrive a trouver le bon automatiquement, en sélectionnant celui qui donne la chaine de plus faible longueur.

Néanmoins il y a un hic, c'est que le bon à la plus faible longueur, mais des mauvais on également la même longueur, par exemple é peut donner 'é' ou 'Ù'...

Je continue mon bricolage...

Par contre si tu peux m'en dire plus (et si tu as le temps) sur É =
'é','Ã?Â?', 'é', 'À°', 'À¹', '€Š', 'é', 'Ã?©', 'É' et 'Ê'

je suis preneur.

Effectivement je suis parti d'une table

http://www.ascii.ca/cp850.htm

merci pour le lien !
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 17h19   #10
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
@Datametrics

Je n'ai pas regardé le problème sous cet aspect pour l'instant, c'est effectivement une piste pour la suite des traitement, là j'en suis a implanter les transcodages pas trop "bourrinement" pour me construire des informations annexes me permettant ensuite de faire des choix, dont par exemple la longueur du résultat (plus petite longueur = probable bon décodage, longueur supérieure à la minimale = décodage erroné).

Alors effectivement j'ai bien une variable de provenance, mais elle ne concerne que le premier niveau (les sous fichiers qui ont servis à constituer le fichier), et je subodore que c'est dans des fichiers de niveau encore inférieurs que le problème s'est posé ou pas (c'est à dire dans les sous-sous fichiers qui ont servi a construire les sous-fichiers ), je suis donc pas encore convaincu de son utilité, mais je comptais quand même bien vérifier au cas où...


Mais aussi la présence d'un décodage réussi dans la chaine permet de donner une indication sur la methode a utiliser pour les autres caractère de l'observation.
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 17h25   #11
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
Citation:
Envoyé par jerome_pdv2 Voir le message
Par contre si tu peux m'en dire plus (et si tu as le temps) sur É =
'é','Ã?Â?', 'é', 'À°', 'À¹', '€Š', 'é', 'Ã?©', 'É' et 'Ê'
ben, c'est ce que j'ai repris dans ton programme (l'extrait indiqué plus haut)

Citation:
Envoyé par jerome_pdv2 Voir le message
Néanmoins il y a un hic, c'est que le bon à la plus faible longueur, mais des mauvais on également la même longueur, par exemple é peut donner 'é' ou 'Ù'...
Je continue mon bricolage...
euh.. tu veux dire que, des fois, é donne é et que des fois, il faut le remplacer par Ù ?

comme l'indique Sam, si tu ne peux pas retrouver l'origine de chaque observation, j'ai quand même peu d'espoir pour toi...

tu peux poster une table (ou un txt) contenant les noms de tes communes sans doublon que je jette un oeil ?

a+

Sébastien Ringuedé
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 17h38   #12
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Citation:
Envoyé par z6c3po Voir le message
ben, c'est ce que j'ai repris dans ton programme (l'extrait indiqué plus haut)



euh.. tu veux dire que, des fois, é donne é et que des fois, il faut le remplacer par Ù ?

comme l'indique Sam, si tu ne peux pas retrouver l'origine de chaque observation, j'ai quand même peu d'espoir pour toi...

tu peux poster une table (ou un txt) contenant les noms de tes communes sans doublon que je jette un oeil ?

a+

Sébastien Ringuedé
Pour le 1 Ok , j'avais mal compris, oui effectivement il y a pas mal de possibilités et certaines d'ailleurs tordues

par exemple ces codes 'é','Ã?Â?', 'é', 'À°', 'À¹', '€Š'
proviennent d'une double mauvaise importation ou exportation (c'est comme ont veut...) et j'ai mis du temps à m'en rendre compte.


Pour la liste ok, je vous en met une demain matin, les problèmes étant tout de même "épars" je vais vous en faire une sélection pour vous donner un fichier pas trop gros ET pertinent (peu d'intérêt si rien n'est à corriger)...


Pour les "collisions" effectivement pour compliquer la chose par exemple

en "CP 850 UTF8" : "é" correspond à 'é'
en "ANSI UTF8" : "é" correspond à 'Ú'

il y a plein d'exemple comme ceci...


Dans l'idéal le programme va devoir donc choisir pour la traduction de "01 impasse du général delfosse"

entre

"01 impasse du général delfosse"

et

"01 impasse du gÚnÚral delfosse"

Dans ce dernier cas cela nous amène à avoir une majuscule au milieu de minuscules, cela peut peut être constituer une règle de "disqualification".

(avec ici un cas de transcodage d'indice de répétition d'ordre 2 / double transcodage)



Pour suivre la piste levée par datamétrics, il est peut être possible de construire des "sous corpus" pertinents sur la base des observations bien codées si j'arrive à les rattacher aux autres par proximité géographique, ce qui n'est pas une mince affaire car le sous produit du résultat est entre autre de coder le code commune.... (on se mord la queue).

Je vais y réfléchir.

Il y a aussi des approches "probabilistes" qui semblent jouables, 'é' est plus courant que 'Ú'

Pour vous donner une idée de la structure du fichier, le fichier est composé
  • d'un code provenance : prov
  • 4 champs d'adresse : adresse1 adresse2 adresse3 commune (libellé de la commune)
  • du code postal : CP

Enfin et comme c'est un fichier "brut de brut" comme on les aime tous, bien sûr, ce qui doit normalement se retrouver dans commune peu se retrouver dans adresse1 à 3...
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 19h55   #13
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Au niveau programmation je sèche sur un os...

J'ai fait des tables de passage

CP850 UTF8 -> ANSI
CP850 UTF8(x2) --> ANSI
ANSI UTF8 --> ANSI
ANSI UTF8(x2) --> ANSI

Par exemple pour la troisième table de passage, à partir de ma variable texte, je créé une variable texte3 correspondant au transcodage avec la table de passage 3 "ANSI UTF8 --> ANSI" , dans laquelle je remplace le code UTF8 par le caractère suivi d'une information sous la forme '(nom_table_passage*texte_remplacé*)'
ici nom_table_passage='UTF8'
et pour la première observation texte_remplacé='‚'

donc toujours pour la même observation

texte='R‚sidence du Parc'
texte3 vaut donc 'Ré(UTF8*‚*)sidence du Parc'

à l'étape suivante je supprimer l'information '(nom_table_passage*texte_remplacé*)' à l'aide d'une expression régulière

et j'obtiens un texte

texte3_='Résidence du Parc'

Je souhaite passer par l'intermédiaire "texte3" au lieu de passer directement à texte3_ pour savoir qu'est ce qui a été remplacé et où, ceci afin de faire des tests de pertinence (par exemple une minuscule au milieu de minuscules = pertinence à priori forte, une majuscule accentuée au milieu de minuscules = pertinence à priori très faible, mais une majuscule en début de mot suivi de minuscules pertinence à priori moyenne ou forte etc...).

Pour l'observation 7 j'ai donc successivement
texte='PLACE GÂNÂRAL KOENIG'
texte3='PLACE GÉ(UTF8*Â*)NÉ(UTF8*Â*)RAL KOENIG'
texte3_='PLACE GÉNÉRAL KOENIG'

Pour savoir ce qui a été remplacé et où , je veux créér les variables suivantes
car_1='É' place_1=8
car_2='É' place_2=10

car_x est le caractère de substitution et place_x la place dans la chaine de caractère finale (texte3_).

L'ordre n'est pas forcément important( car_1 peut correspondre par exemple au dernier caractère de la chaine ou au premier, peut importe du moment qu'ils y sont tous et donc autant de variables créées), ils sont de toute façon implicitement ordonnés par la valeur de place_x si j'en ai besoin ultérieurement.

Do voilà tranwrd remplace mais ne donne pas l'information (et ne peux pas car il y a des centaines de tranwrd à la suite), d'où pourquoi je voulais passer par mon intermédiaire texte3.

Si il y a x caractères remplacés dans la chaine je dois générer car_1 à car_x et place_1 et place_x à partir de la variable texte3 , le nombre de variables générées est donc variable selon les observations, 0 si aucun demplacement 1x2 variables (car_1 et place_1) si un remplacement, 2x2 variables si deux remplacement etc...


Et là je ne sais pas trop comment m'y prendre pour construire ces variables, j'ai des idées mais elles semblent bien compliquées, et je ne suis pas encore arrivé à les "coucher en code"...


Voici un petit échantillon de données pour ce cas précis.


Code :
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
 
Obs texte
 
  1 R‚sidence du Parc
  2 1 ALL‚e des Ragottinieres
  3 1 croas hent qu‚r‚
  4 11 Ruelle des M‚nagÅ*res
  5 12 pont M‚vault
  6 14 impasse du verger R‚sidence
  7 15 PLACE GÂNÂRAL KOENIG
  8 209 chemin du Pr‚ Montchain
  9 21 av de la FORˆt
 10 3 ALL‚e des jardins
 11 32 ALL‚e des Pins
 12 44 chemin de la Vall‚e
 13 6 ALL‚e Jacquard
 14 72 BIS ALLÂE DU BOIS
 15 74 avenue de b‚arne
 16 8 rue d’apres
 17 839 rue des Fusill‚s
 18 9 rue Honor‚ de Balzac
 19 9 rue st l‚onard
 20 LE CH‚TELARD
 21 ALL‚e des lauriers
 22 chemin des c“tes 9
 
Obs texte3                                         texte3_
 
  1(UTF8*‚*)sidence du Parc                   Résidence du Parc
  2 1 ALLé(UTF8*‚*)e des Ragottinieres           1 ALLée des Ragottinieres
  3 1 croas hent qué(UTF8*‚*)(UTF8*‚*)       1 croas hent quéré
  4 11 Ruelle des Mé(UTF8*‚*)nagÅ*res            11 Ruelle des MénagÅ*res
  5 12 pont Mé(UTF8*‚*)vault                     12 pont Mévault
  6 14 impasse du verger Ré(UTF8*‚*)sidence      14 impasse du verger Résidence
  7 15 PLACE GÉ(UTF8*Â*)(UTF8*Â*)RAL KOENIG    15 PLACE GÉNÉRAL KOENIG
  8 209 chemin du Pré(UTF8*‚*) Montchain         209 chemin du Pré Montchain
  9 21 av de la FORê(UTF8*ˆ*)t                    21 av de la FORêt
 10 3 ALLé(UTF8*‚*)e des jardins                 3 ALLée des jardins
 11 32 ALLé(UTF8*‚*)e des Pins                   32 ALLée des Pins
 12 44 chemin de la Vallé(UTF8*‚*)e              44 chemin de la Vallée
 13 6 ALLé(UTF8*‚*)e Jacquard                    6 ALLée Jacquard
 14 72 BIS ALLÉ(UTF8*Â*)E DU BOIS                 72 BIS ALLÉE DU BOIS
 15 74 avenue de bé(UTF8*‚*)arne                 74 avenue de béarne
 16 8 rue dÆ(UTF8*’*)apres                       8 rue dÆapres
 17 839 rue des Fusillé(UTF8*‚*)s                839 rue des Fusillés
 18 9 rue Honoré(UTF8*‚*) de Balzac              9 rue Honoré de Balzac
 19 9 rue st lé(UTF8*‚*)onard                    9 rue st léonard
 20 LE CHé(UTF8*‚*)TELARD                        LE CHéTELARD
 21 ALLé(UTF8*‚*)e des lauriers                  ALLée des lauriers
 22 chemin des cô(UTF8*“*)tes 9                  chemin des côtes 9
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 20h57   #14
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
et bien moi je continue à vouloir une liste de tes communes (et rien que des communes) pour tenter quelque chose ;-)

a+

Sébastien Ringuedé
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 21h02   #15
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
ok,

j'avais pris l'option de tout traiter en même temps, ce qui fait que j'ai tout mis dans une même variable d'où la présence prépondérante des adresses dans mon exemple.

Comme promis je te met ça demain avec seulement des communes.
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 19/10/2011, 21h16   #16
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
chic

(bon demain, c'est un peu chaud mais je regarderai cela...)
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 20/10/2011, 10h20   #17
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
voici...



Finalement je pense que le passage par les tranwrd est un peu lourd (plusieurs centaines), je me demande si je ne peux pas faire une analyse des chaines caractères par caractères, mais dans ce cas ce qui serait pratique ce serait d'avoir l'équivalent des "pointeurs" de C ? Ca existe en SAS ?
Fichiers attachés
Type de fichier : zip communes_extrait.zip (25,6 Ko, 8 affichages)
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 20/10/2011, 11h19   #18
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
et bien c'est tout à fait mignon...
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 21/10/2011, 15h41   #19
Membre habitué
 
Sébastien Ringuedé
Inscription : janvier 2011
Messages : 61
Détails du profil
Informations personnelles :
Nom : Sébastien Ringuedé
Localisation : France, Loiret (Centre)

Informations forums :
Inscription : janvier 2011
Messages : 61
Points : 114
Points : 114
bon et bien c'est l'échec...

j'avais dans l'idée de faire la chose suivante :

1- l'Insee donne un txt contenant toutes les communes de France
2- je prends les communes de la table de Jérôme et leur donne une forme proche de celle que j'observe dans la table INSEE et je vais "comparer".

proche c'est quoi ?

ben ça dépend... dans la table de Jérôme, les communes sont généralement écrites soit en minuscules, soit en majuscules. On ne peut pas trop s'amuser à tout passer en minuscules ou en majuscules (parce que on risque de créer encore plus de de problèmes en modifiant la casse des caractères étranges...) (ça mériterait quand même un semblant de vérification...).

Lorsqu'elles sont en minuscules, la forme, dans les données INSEE est la suivante :

Boigny-sur-Bionne
La-Ferté-Saint-Aubin

jamais d'espace, toujours des tirêts, propcase sauf sur un certain nombre de mot que vous pouvez obtenir au moyen du programme suivant :

Code :
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
 
DATA TABLE;
INFILE "f:\Nouveau dossier (2)\france2011.txt" dlm='09'x DSD firstobs=2;
input ACTUAL CHEFLIEU CDC RANG REG DEP :$10. COM AR CT MODIF POLE $
      TNCC ARTMAJ :$10. NCC :$50. ARTMIN :$10. NCCENR :$50. ARTICLCT :$10. NCCCT :$50. ;
;run;
 
DATA minus;
input minus $ @@;
cards;
a b c d e f g h i j k l m n o p q r s t u v w x y z
;
 
proc sql;
SELECT minus format=$quote3. INTO :minus separated BY ',' FROM minus;
quit;
 
DATA temp (keep=mot);
  SET TABLE ;
  IF countw(nccenr,' ')=1;
  n=1 ;
  do until (scan(nccenr,n,"-'")='');
     IF substr(scan(nccenr,n,"-'"),1,1) IN (&minus) then do ;
        mot=scan(nccenr,n,"-'");
        output;
     end;
	 n+1;
  end;
  run;
 
proc sort DATA=temp nodupkeys;
BY mot;
run;
 
proc print DATA=temp noobs;
run;
donc, on regarde les noms de communes dans la table de Jérôme, on détermine s'ils sont principalement écrits en minuscules ou en majuscules, puis en fonction du type (minuscules ou majuscules), on effectue un certain nombre de bricolages pour arriver à la mise en forme la plus proche possible de celle de la table INSEE. Ces bricolages, par exemple pour les communes écrites essentiellement avec des minuscules incluent le remplacement de / par sur, de St par Saint, Ste par Sainte, des blancs par -, PROPCASE sauf sur les mots listés par le programme plus haut etc. etc.

une fois que ces modifications sont faites, on enregistre dans de nouvelles variables les caractères bizarres : si trois caractères bizarres se suivent, ils sont enregistrés dans la même variable, si dans le nom de la commune, on a deux caractères bizarres qui ne se suivent pas, on aura alors deux variables. J'enregistre aussi la position des caractères bizarres (en fait, pour chaque chaîne, la position du premier caractère bizarre).

une fois que c'est fait, on remplace dans le nom de la commune le ou les caractères bizarres qui se suivent par un seul _.

je veux en fait pouvoir exécuter un programme de ce type :

Code :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
 
DATA toto;
input commune $;
cards ;
Orléans
Blois
Tours
;
 
DATA tutu;
input commune $;
cards;
Orl_ans
;
 
proc sql ;
   SELECT toto.commune,tutu.commune 
      FROM toto,tutu 
      WHERE toto.commune LIKE tutu.commune ;
run;
c'est à partir de ce type de résultat que j'espérais pouvoir construire ma table de conversion.

voici ce que j'obtiens (et c'est la fin du rêve)

Code :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
 
initial    final     n
 
  ‚          é       2
            É       1
  š          è       4
  À          à       3
  é         E       1
  é         É       1
  É          A       1
  㢠        â       3
  ã§         ç       1
  㨠        e       1
  㨠        è      21
  ã©         e       1
  ã©         o       1
  ã©         y       4
  ã©         É       1
  ã©         è       3
  ã©         é      61
  ã´         ô       4
  ú          é       2
  þ          è       2
n mesure le nombre de fois où le lot de caractères bizarre a été utilisé à la place de la lettre saisie dans la variable FINAL.

ã© est utilisé essentiellement pour é mais il est aussi utilisé pour è, É, y, o et e...

et je n'ai même pas tenté d'utiliser ces associations plus haut pour voir le résultat sur les noms de rue proposés plus haut...

Je ne sais donc pas s'il y a un moyen de faire "parfaitement propre" en tout cas, ma méthode n'a pas marché...

désolé

a+

Sébastien Ringuedé
z6c3po est déconnecté   Envoyer un message privé Réponse avec citation 10
Vieux 21/10/2011, 17h06   #20
Membre éclairé
 
Homme
statisticien
Inscription : mai 2011
Messages : 212
Détails du profil
Informations personnelles :
Sexe : Homme
Localisation : France, Paris (Île de France)

Informations professionnelles :
Activité : statisticien
Secteur : Administration - Collectivité locale

Informations forums :
Inscription : mai 2011
Messages : 212
Points : 319
Points : 319
Bonjour,

merci d'avoir essayé quand même.

pour ma part, j'ai continué sur ma lancée,

J'avais créé 4 tables de passages possibles, ce qui donne 4 possibilités de textes.
Ces 4 tables de passages ne règlent pas tous les problèmes, mais l'essentiel il me semble. Je dois encore faire des vérifications sur certains cas.

Ensuite cela consistait à retenir les chaines de plus faible longueur parmi les 4.
Lorsqu'il y a doute entre plusieurs, je calcule un score probabiliste, que j'appelle vraissemblance, basé sur la fréquence des caractères dans la partie semblant "propre" des données (en fait sur le log de la fréquence).
Le a a un score de 200 et les caractères peu fréquent 0.
Ensuite je regarde dans la chaine quels sont les caractères de substitution, et leur associe leur score.

Le é a un score de 182 par exemple, si il y a dans une chaine deux sous chaines substituées par un é et rien d'autre je fais la somme des deux soit 182+182=364.

Je regarde la vraissemblance des 4 textes, et je conserve celui à la plus forte vraissemblance.

Après sondage, sur un millier d'adresses/communes/ complément d'adresse j'obtiens un taux de réussite de 99% amplement suffisant pour mes besoins.

Je vais voir ce que ça donne sur la liste des communes transmises, je pense que le taux de réussite devrait être inférieur cependant.
jerome_pdv2 est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse Proposer ce sujet en actualité Cette discussion est résolue.
Outils de la discussion



Fuseau horaire GMT +2. Il est actuellement 07h17.


 
 
 
 
Partenaires

Hébergement Web