Méthodes pour importer fichier csv dans access via winform

Fermé
Morgane_43 Messages postés 5 Date d'inscription jeudi 1 août 2013 Statut Membre Dernière intervention 14 février 2023 - 14 févr. 2023 à 10:59
 Utilisateur anonyme - 14 févr. 2023 à 20:12

Bonjour à tous, 

Je travaille actuellement sur un petit projet de récolte de données. J'ai développé un formulaire winform via vb. 
L'opérateur doit pouvoir créer un code projet et rattacher un fichier .csv. celui ci doit s'importer dans ma base de données dans la table donnees.  


Au début, je suis partie sur un import du fichier.csv dans un datagridview puis un ajout dans ma table donnees de ma base de données grâce à un Oledbcommand(INSERT INTO).

Cela fonctionne bien, mais comme il s'agit d'une boucle, dès l'instant où mon fichier est volumineux, cela met beaucoup de temps à s'importer dans ma table access. 
Je me demandais si vous aviez d'autres pistes pour faire cela ? 

Dans access j'utilise un doCmd import spreadsheet ou transfer text mais je ne crois pas qu'il y ait d'équivalence sous winform. 

Par avance merci beaucoup :) 
 


Windows / Chrome 110.0.0.0

A voir également:

4 réponses

yg_be Messages postés 23317 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 novembre 2024 Ambassadeur 1 552
14 févr. 2023 à 12:16

Je ne connais pas comment vb/winform peut interagir avec une base de données.  Je suppose que tu fais un INSERT par groupe d'enregistrements, pas un par enregistrement.

J'ai l'impression qu'il serait plus efficace de faire cela en VBA, à partir de Excel ou de Access.

0
Utilisateur anonyme
14 févr. 2023 à 13:03

Bonjour 

est ce que l'affichage des données sur la Winform est nécessaire (par exemple pour choisir quelles lignes doivent être importées, etc...)

Si NON alors importer directement chaque ligne du csv devrait te faire gagner beaucoup de temps.

Si OUI as tu chargé tes données dans une collection d'objets métier ou as tu "stocké" les infos dans le datagridview (cette 2eme solution est à éviter, notamment parce que longue)


0
Morgane_43 Messages postés 5 Date d'inscription jeudi 1 août 2013 Statut Membre Dernière intervention 14 février 2023
14 févr. 2023 à 14:40

Bonjour à vous deux, 

Merci beaucoup pour vos retours. 

yg_be : Effectivement, utiliser excel directement avec access aurait été plus simple mais en réalité ce formulaire fait partie d'une application globale et ne peut pas être détaché du winform. Le but étant d'avoir une seule application pour tout. 

Whismeril, L'affichage n'est absolument pas nécessaire car le but est d'importer toutes les lignes. Il n'y a aucun traitement à  faire dessus. 

Je vous met mon code d'import de mon fichier puis de maj de la table pour que ce soit plus parlant. 

Importer chaque ligne, ce n'est pas ce que je fais actuellement ?


Je vais regarder du côté des collections d'objets métier (que je connais très peu, j'avoue). 

Private Sub PictureBoxJoindre_Click(sender As Object, e As EventArgs) Handles PictureBoxJoindre.Click
'J'ai une image "joindre"pour joindre mon fichier

        If OpenFileDialogfichier.ShowDialog = DialogResult.OK Then
            Dim titre As String
            titre = NomFichier.Text
            Fichierjoint.Text = OpenFileDialogfichier.FileName

            Dim source As String
            source = Fichierjoint.Text
            Dim dat As DataSet
            dat = New DataSet
            Using Conn As OleDbConnection = New OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & source & ";Extended Properties=""Excel 8.0;HDR=Yes;IMEX=1""")
                Using Adap As OleDbDataAdapter = New OleDbDataAdapter("SELECT*FROM[Feuil1$]", Conn)
                    Adap.Fill(dat)
                    DataGridViewphicus.DataSource = dat.Tables(0)
                    Labelfichier.Visible = True
                End Using
            End Using
        End If

    End Sub
	
'Ici j'ai donc mon datagridview de rempli avec mes infos 

	 Private Sub PictureBoxSave_Click(sender As Object, e As EventArgs) Handles PictureBoxSave.Click
	  Dim var As Integer
                var = DataGridViewphicus.RowCount - 2
				
For i As Integer = 0 To var
                       Using Co As OleDbConnection = New OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=L:********.accdb")
                            Co.Open()
Using cdm As OleDbCommand = New OleDbCommand("INSERT INTO T_Donnees ([*],[**],[***],[****],[*****],[*******],[*********]) VALUES (@*,@**,1,[@***],@****,@*******,@*********)", Co)
cdm.Parameters.AddWithValue("@*", DataGridViewphicus.Rows(i).Cells(17).Value)
cdm.Parameters.AddWithValue("@**", DataGridViewphicus.Rows(i).Cells(1).Value)
cdm.Parameters.AddWithValue("@****", DataGridViewphicus.Rows(i).Cells(8).Value)
cdm.Parameters.AddWithValue("@*****", DataGridViewphicus.Rows(i).Cells(7).Value)                                                               
cdm.Parameters.AddWithValue("@******",DataGridViewphicus.Rows(i).Cells(44).Value)
cdm.Parameters.AddWithValue("@*********", DataGridViewphicus.Rows(i).Cells(45).Value)
                             
                                cdm.ExecuteNonQuery()
                                Co.Close()
                            End Using
                        End Using
                    Next i
                End If
	End Sub

Encore merci pour votre aide

0
yg_be Messages postés 23317 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 novembre 2024 1 552
14 févr. 2023 à 17:21

Pour accélérer l'exécution, il faudrait sortir de la boucle les instructions de création, ouverture et fermeture de la connexion Co.

peut-être (je ne sais pas à quoi sert "using" ni surtout end using):

Using Co As OleDbConnection = New OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=L:********.accdb")
Co.Open()
For i As Integer = 0 To var
Using cdm As OleDbCommand = New OleDbCommand("INSERT INTO T_Donnees ([*],[**],[***],[****],[*****],[*******],[*********]) VALUES (@*,@**,1,[@***],@****,@*******,@*********)", Co)
cdm.Parameters.AddWithValue("@*", DataGridViewphicus.Rows(i).Cells(17).Value)
cdm.Parameters.AddWithValue("@**", DataGridViewphicus.Rows(i).Cells(1).Value)
cdm.Parameters.AddWithValue("@****", DataGridViewphicus.Rows(i).Cells(8).Value)
cdm.Parameters.AddWithValue("@*****", DataGridViewphicus.Rows(i).Cells(7).Value)                                                               
cdm.Parameters.AddWithValue("@******",DataGridViewphicus.Rows(i).Cells(44).Value)
cdm.Parameters.AddWithValue("@*********", DataGridViewphicus.Rows(i).Cells(45).Value)
cdm.ExecuteNonQuery()
End Using
Next i
Co.Close()
End Using
0
Utilisateur anonyme
14 févr. 2023 à 20:12

Tout d'abord, il y a des années que je n'ai pas travaillé avec Access et je ne me souviens pas de l'avoir fait de cette manière.


C'est bien un fichier csv que tu ouvres ou un fichier Excel?

Parce que ça

 Using Conn As OleDbConnection = New OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & source & ";Extended Properties=""Excel 8.0;HDR=Yes;IMEX=1""")
                Using Adap As OleDbDataAdapter = New OleDbDataAdapter("SELECT*FROM[Feuil1$]", Conn)
                    Adap.Fill(dat)
                    DataGridViewphicus.DataSource = dat.Tables(0)
                    Labelfichier.Visible = True
                End Using
            End Using

ça fait plus penser à Excel.

Un csv c'est un fichier texte, y'a pas besoin de lancer une armada de Dataset, d'OleDbConnection et d'OleDbDataAdapter pour l'ouvrir.

La classe File et sa méthode ReadAllLine suffit amplement.

De plus, dans un csv, il n'y a que du texte (des string, pas de int, de double de bool, de datetime etc...), donc cela tend à faire penser que l'insertion dans Access n'a pas besoin de données typées (bien que cela soit possible).

Et dans ce cas, il n'y aurait même pas besoin de classe métier intermédiaire, juste découpé chaque ligne du csv et mettre les "morceaux" dans la requette.

Mais si c'est Excel et que les données sont typées, il sera peut-être nécessaire d'avoir une classe métier.

Ensuite, cette boucle


Quand j'étais petit, la mer Morte n'était que malade.
George Burns


0