IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

VBA Access Discussion :

[vba]deplacer une donnée d un champ en fonction de la valeur d autres champs


Sujet :

VBA Access

  1. #1
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut [vba]deplacer une donnée d un champ en fonction de la valeur d autres champs
    bonjour,

    je suis pas un pro de vba et j'aimerai pouvoir deplacer une donnée d un champ en fonction de la valeur d autres champs.
    le fichier a ma disposition a la structure suivante:


    idp | item1 |dept|item3|item4....|codpostal|
    1 | 1 | 72 | 1 | 2 | 72300|
    1 | 2 | 72 | 1 | 2 | null |
    1 | 2 | 72 | 1 | 2 | 999 |
    2 | 2 | 44 | 2 | 2 | 999 |
    2 | 2 | 72 |1 | 2 | 72450|
    2 | 2 | 72 | 1 | 1 | 999 |

    je voudrai par exemple pour le patient 1 remplacer les valeurs 'null' et '999' du codpostal par la valeur 72300 si la reponse a l item2 est 72 pour les enregistrements ou il ya null et 999.Pour effectuer ce deplacement de valeur il faudrait aussi que la reponse a l'item4 soit '2'.si ces conditions ne sont pas remplis je voudrai qu il n'y ai pas de changement

    ce qui donnerai apres transformation

    idp| item1 |dept|item3|item4....|codpostal|
    1 | 1 | 72 | 1 | 2 | 72300|
    1 | 2 | 72 | 1 | 2 | 72300 |
    1 | 2 | 72 | 1 | 2 | 72300 |
    2 | 2 | 44 | 2 | 2 | 999 |
    2 | 2 | 72 |1 | 2 | 72450|
    2 | 2 | 72 | 1 | 1 | 999 |

    auriez vous une idée pour faire ca? merci d avance

  2. #2
    Membre éprouvé Avatar de jean-paul lepetit
    Inscrit en
    Février 2005
    Messages
    842
    Détails du profil
    Informations personnelles :
    Âge : 68

    Informations forums :
    Inscription : Février 2005
    Messages : 842
    Points : 919
    Points
    919
    Par défaut
    Salut,

    Pourquoi le faire en VBA, une requête mise à jour ferait très bien l'affaire, non?
    Ils ne savaient pas que c'était impossible, alors il le réalisèrent (Mark Twain)

  3. #3
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    je sais pas trop peut etre que ca peut etre fait en sql mais je vois pas....
    pourrez tu me donner le code sql auquel tu pense s il te plait?

  4. #4
    Membre éprouvé Avatar de jean-paul lepetit
    Inscrit en
    Février 2005
    Messages
    842
    Détails du profil
    Informations personnelles :
    Âge : 68

    Informations forums :
    Inscription : Février 2005
    Messages : 842
    Points : 919
    Points
    919
    Par défaut
    essaies quelque chose comme ça

    mais avant toutes choses, fait une copie de ta base originale...
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    UPDATE Tbl_Test1 SET Tbl_Test1.codepostal = "72300"
    WHERE (((Tbl_Test1.dept)="72") AND ((Tbl_Test1.codepostal) Is Null Or (Tbl_Test1.codepostal)="999") AND ((Tbl_Test1.item4)="2"));
    Ils ne savaient pas que c'était impossible, alors il le réalisèrent (Mark Twain)

  5. #5
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    bah merci de ta reponse mais en fait c est pas ca que je voudrais avoir.moi je voudrai que l 'on recupere le bon code postal pour un meme patient (qui peut etre different d un patient a l'autre)et qu on lremplace quand il le faut les valeurs 999 et null par un code postal renseigné par le patient.
    je sais pas si je suis clair?

  6. #6
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    Bonjour Shagun !

    effectivement, ce n'est pas tres clair...

    D'ou vient le code postal ? Pourquoi 72 300 et pas un autre ?
    Tu veux écrire le code postal qui correspond au patient? Pourquoi ne renseignerai-tu pas ce code postal dans ta table patient??

    Jean-Paul a raison, il te faut une requete UPDATE qui, en fonction des valeurs de ton enregistrement, écrive qqc.

    Dans ton probleme précédent, la fonction était compliquée parce qu'elle consistait a écrire des valeurs en fonctions d'enregistrements différents, tandis que la, d'apres ce que je comprends, les criteres et le champ a modifier sont sur la meme ligne !

    Eclaire-moi un peu, stp
    puis et puis et encore . Sinon sans oublier et

  7. #7
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    72300 c etait juste un exemple.
    je suis encore sur la table des items ,vu que l on a garder dans le temps l evolution des items un meme patient peut avoir plusieurs codes postaux differents je ne peux donc pas le mettre dans la table patient.Lorsqu un code patient n est pas renseigné il ya soit la valeur 999 soit il n'y a rien .Mais d un secteur a l autre l'information peut etre bien rempli sur un enregistrement
    mais mal rempli sur l'enregistrement d'apres.Je veux donc remplacer les valeurs mal renseignées par les valeurs bien renseignée par un meme patient.
    peux etre puis je modifier ton programme en enlevant la boucle des secteurs et en ayant remplacer prealablement les valeurs 999 par des null dans la table?
    est ce que c est plus clair?

  8. #8
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    en fait, je ne vois absoluement pas pourquoi tu aurais besoin du meme code que la fois précédente.

    En fait, je ne vois pas l'interaction entre les différents enregistrements.

    Je le comprends comme ca:
    Tu voudrais, pour un meme patient, dans un meme secteur, importer le code postal le plus ancien vers les enregistrements plus récents qui auraient un 999 ou Null pour code postal (d'autres criteres encore?)
    puis et puis et encore . Sinon sans oublier et

  9. #9
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    je voudrais, pour un meme patient, dans un secteur DIFFERENT, importer le code postal ou il est bien renseigné vers les enregistrements qui ont un 999 ou Null pour code postal

  10. #10
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    D'accord, peu importe le secteur, et si on a :

    P|S|cp
    1|4|Nul
    1|3|59420
    1|1|999
    1|4|23410
    1|2|Nul

    Avec P: patient, S: Secteur et cp: code postal
    Qu'est-ce que ca doit donner.

    Excuse moi, mais je préfere bien comprendre avant de me lancer et disons que tes explications ne sont pas hyper limpides !
    puis et puis et encore . Sinon sans oublier et

  11. #11
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    excuse moi pour les explications je sais elles sont pas terribles!!

    lorsque l'on a un cas comme ci dessous il faudrait rien faire car on ne peut pas privilegier un codepostal plutot qu un autre
    P|S|cp
    1|4|Nul
    1|3|59420
    1|1|999
    1|4|23410
    1|2|Nul

    en regardant les données j ai vu que ce cas est assez marginal,en general il n'y a qu'un code postal distinct pour une personne et les valeurs 999 ou null.

    merci

  12. #12
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    Bon, moi c'est l'heure de partir du boulot... J'ai commencé a écrire un petit bout de code, mais c'est pas encore assez abouti pour etre partagé.

    Je reviens vers toi demain matin.

    Salut !
    puis et puis et encore . Sinon sans oublier et

  13. #13
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    ok encore merci a demain matin

  14. #14
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    Ok, en supposant que ta table s'appelle toujours T et que ton champ qui contient le code postal s'appelle Code Postal.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    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
    Sub cp()
    'declaration des variables
    Dim db As DAO.Database
    Dim recpatient As DAO.Recordset
    Dim rec As DAO.Recordset
    Dim strsql As String
    Dim cp_collec As New Collection
     
    Set db = CurrentDb
    Set recpatient = db.OpenRecordset("Patient") 'ouvre la table patient
     
    While Not recpatient.EOF 'parcourt la table patient
    'requete SQL de selection des enregistrements en fonction du numero de patient
    strsql = "Select T.* FROM T " & _
             "WHERE T.idpatient=cint('" & recpatient.Fields("idpatient") & "')"
    'ouverture du recordset
    Set rec = db.OpenRecordset(strsql)
     
        'on parcourt chacun des enregistrements dans la requete
        While Not rec.EOF
        'si le champ "Code Postal" est différent de '999' et différent de 'Null'
         If rec.Fields("Code Postal") <> 999 And Not IsNull(rec.Fields("Code Postal")) Then
         'alors on l'ajoute a la collection cp_collec
         cp_collec.Add (rec.Fields("Code Postal"))
         End If
        rec.MoveNext
        Wend
     
        'si on a trouvé qu'un seul code postal pour un client (un seul objet dans la collection),
        'on écrit ce code postal dans tous les enregistrements de la requete.
        If cp_collec.Count = 1 Then
        rec.MoveFirst
            While Not rec.EOF
            rec.Edit
            rec.Fields("Code Postal") = cp_collec(1)
            rec.Update
            rec.MoveNext
            Wend
        End If
     
    'on efface la collection pour le patient suivant
    Set cp_collec = Nothing
     
    rec.Close
     
    recpatient.MoveNext
    Wend
    End Sub
    J'avais cru comprendre que tu avais d'autres criteres aprendre en compte mais je n'ai pas tellement cherché a comprendre. Dis moi si tu n'arrives pas les prendre en compte mais maintenant tu dois peut-etre commencer a comprendre le truc...

    A bientot
    puis et puis et encore . Sinon sans oublier et

  15. #15
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    encore mille merci pourrai tu m'expliquer vite fait le principe de collection
    car j ai trouver des definitions sur le net mais c'est pas tres clair pour moi encore.

  16. #16
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    excuse moi de te deranger a nouveau mais y a t - il un moyen pour que le programme marche si on on a plusieurs codes postaux identiques.
    je m explique
    le programme marche si on a ca:
    id|codpostal|
    1 | 72000|
    1 | null |
    1 | 999|

    y aurai t il un moyen pour qu il marche lorsqu il y a un cas comme celui la

    1 | 72000|
    1 | 72000 |
    1 | 999|

    c est a dire qu il m'affiche 72000 sur la troisieme ligne.
    merci

  17. #17
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    Ah oui, bien vu, je n'avais pas du tout pensé a ca dis donc !

    Je vais voir ca tout de suite. Il faudrait un petit code qui épure la collection de ses doublons.

    La collection, je m'en sers depuis peu, c'est une sorte de groupe de valeurs qui sont identifiées par un index. Un simple regroupement dans un meme sac.
    Du coup, tu peux traiter toutes ses valeurs assez simplement.

    Ici, je mets toutes les valeurs clés dans ce sac. De ce sac on en fait ce qu'on veut.
    puis et puis et encore . Sinon sans oublier et

  18. #18
    Membre confirmé Avatar de timoth
    Homme Profil pro
    Responsable Outils Digitaux
    Inscrit en
    Octobre 2005
    Messages
    479
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Responsable Outils Digitaux

    Informations forums :
    Inscription : Octobre 2005
    Messages : 479
    Points : 474
    Points
    474
    Par défaut
    Bon, c'est bon je crois.

    Je me suis vraiment pris la tete sur la facon d'épurer la collection de ses doublons. Je n'ai pas réussi d'ailleurs. Puis on a eu des coupures de courant. Voila pourquoi je ne suis pas revenu vers toi plus tot.

    Du coup j'ai fait une petite boucle qui regarde si la collection possede des valeurs différentes. Si c'est le cas, il ne fait rien sur la table, sinon, il recopie le code postal dans toutes les lignes.

    Voici mon code final :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    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
    Sub cp() 'declaration des variables
    Dim db As DAO.Database
    Dim recpatient As DAO.Recordset
    Dim rec As DAO.Recordset
    Dim strsql As String
    Dim cp_collec As New Collection
    Dim same_cp As Boolean
    Dim i As Integer
     
    Set db = CurrentDb
    Set recpatient = db.OpenRecordset("Patient") 'ouvre la table patient
    While Not recpatient.EOF 'parcourt la table patient
    'requete SQL de selection des enregistrements en fonction du numero de patient
    strsql = "Select T.* FROM T " & _
             "WHERE T.idpatient=cint('" & recpatient.Fields("idpatient") & "')"
    'ouverture du recordset
    Set rec = db.OpenRecordset(strsql)
    'on parcourt chacun des enregistrements dans la requete
    While Not rec.EOF
    'si le champ "Code Postal" est différent de '999' et différent de 'Null'
    If rec.Fields("Code Postal") <> 999 And Not IsNull(rec.Fields("Code Postal")) Then
    'alors on l'ajoute a la collection cp_collec
    cp_collec.Add (rec.Fields("Code Postal"))
    End If
    rec.MoveNext
    Wend
     
        'test s'il y a des valeurs différentes dans la collection
        same_cp = False 'par défaut, pas de valeur différentes
        'on balaye la collection et on compare chacune des valeurs avec la 1ere
        For i = 1 To cp_collec.Count
        If cp_collec(i) <> cp_collec(1) Then same_cp = True
        Next i
     
     
        'si on a trouvé qu'un seul code postal pour un client (un seul objet dans la collection),
        'on écrit ce code postal dans tous les enregistrements de la requete.
        If Not rec.EOF Then
            If same_cp = False Then
            rec.MoveFirst
            While Not rec.EOF
            rec.Edit
            rec.Fields("Code Postal") = cp_collec(1)
            rec.Update
            rec.MoveNext
            Wend
            End If
        End If
     
    'on efface la collection pour le patient suivant
    Set cp_collec = Nothing
    rec.Close
    recpatient.MoveNext
    Wend
    End Sub
    puis et puis et encore . Sinon sans oublier et

  19. #19
    Membre à l'essai
    Profil pro
    Inscrit en
    Mars 2007
    Messages
    55
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2007
    Messages : 55
    Points : 19
    Points
    19
    Par défaut
    merci beaucoup. je peux pas tester le programme cette apres midi y a un probleme sur mon pc ,je le teste des que je peux ,mais bon j te fais confiance j pense que ca va marcher!
    bon bah je te tiens au courant .
    merci encore

  20. #20
    Expert éminent sénior
    Avatar de rawsrc
    Homme Profil pro
    Dev indep
    Inscrit en
    Mars 2004
    Messages
    6 142
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 47
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Dev indep

    Informations forums :
    Inscription : Mars 2004
    Messages : 6 142
    Points : 16 545
    Points
    16 545
    Billets dans le blog
    12
    Par défaut
    Salut

    Je me suis permis de reprendre le code car à mon avis il n'y a pas besoin de gérer une collection pour résoudre cette problématique.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    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
    Sub MajCodesPostaux()
     
       Dim vDb As DAO.Database, vRst As DAO.Recordset, vSql As String, vCpUnique As String
     
       Set vDb = CurrentDb()
       Set vRst = vDb.OpenRecordset("Patient", dbOpenSnapShot)
     
       With vRst
     
          If Not .EOF Then
             .MoveFirst
    	 DoCmd.SetWarnings False	'désactive les messages d'alertes
     
             Do
    	    If uniciteCodePostal(!IdPatient, vCpUnique) Then
    	       vDb.Execute "UPDATE T SET [Code Postal]='" & vCpUnique & "' WHERE IdPatient=" & !IdPatient & ";"
    	    End If
    	    vCpUnique = "" 
    	    .MoveNext
      	 Loop Until .EOF
     
          End If
          .Close
     
       End With
     
       Set vRst = Nothing
       DoCmd.SetWarnings True
     
    End Sub
     
    Private Function uniciteCodePostal(ByVal pIdPatient As Long, ByRef pCpRetour As String) As Boolean
       'renvoie True si un seul code postal est trouvé dans la table T, le code postal unique est renvoyé dans pCpRetour
     
       Dim vRst As DAO.Recordset, vSql As String
     
       vSql = "SELECT DISTINCT [Code Postal] FROM T WHERE IdPatient=" & pIdPatient & " AND [Code Postal]<>999 AND [Code Postal] IS NOT NULL;"
       Set vRst = CurrentDb.OpenRecordset(vSql, dbOpenSnapshot)
     
       With vRst
          If Not .EOF Then 
             .MoveLast
             If .RecordCount = 1 Then 
                pCpRetour = ![Code Postal]
    	    uniciteCodePostal = True
             End If
          End If
          .Close
       End With
     
       Set Vrst = Nothing	    	
    End Function
    Je te conseillerai de suivre au plus près la nomenclature des noms quand tu créé tes applications : pas d'espaces, ni d'accent, libellé clair, constance dans le nommage des éléments... Bref la Faq est ton amie.

    Ouala
    Bon courage

Discussions similaires

  1. Réponses: 9
    Dernier message: 16/07/2010, 16h02
  2. Réponses: 6
    Dernier message: 15/05/2009, 18h00
  3. Réponses: 3
    Dernier message: 26/11/2007, 06h06
  4. Réponses: 1
    Dernier message: 20/04/2007, 15h35
  5. Réponses: 1
    Dernier message: 22/03/2006, 12h03

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo