Question extracton rapide de données d'un GROS csv

Plus d'informations
il y a 10 ans 8 mois #15612 par Gabriel
Salut

j'ai un petit soucis, j'a un fichier CSV de 50Mo dans lequel je dois chercher a recuperer une ligne et toutes ses valeurs.

donc oui je sais
ex:
[code:1]
prenom,nom,id,
robert,duval,A1
Josiane,pires,A2

infos = import-csv .\fichier.csv | where {$_.id -eq A1}
[/code:1]

ca marche très bien, par contre avec un fichier de 50Mo ca prend du temps de le charger, puis de parser.

hors la je travaille sur une moulinette pour créer des comptes ou le support a juste besoin de saisir l'id et le reste mon script s'en occupe

le fichier CSV contient tous les employés de la boite, il est généré tous les jours mais l'ad sur lequel je travaille ne compte qu'1/10 des employés.

je me demandais si par exemple il y avait une méthode pour lire le fichier, sélectionner la ligne qui m'intéresse et en sortie un objet comme si j'avais importé un fichier CSV d'une ligne.

la je regarde pour transformer le fichier csv en un sql compact et faire des requêtes dessus (mais je n'ai jamais fait d'sql donc ca part mal)

Connexion ou Créer un compte pour participer à la conversation.

Plus d'informations
il y a 10 ans 8 mois #15624 par Laurent Dardenne
Salut,
si tu as une volumétrie importante effectivement un SGBD peut améliorer les performances. C'est plus ta conception d'origine que tu dois revoir plutôt que de tourner autour du csv, la persistance de tes objets devrait se faire directement dans la base. Sinon le problème du temps de chargement restera, certes moindre.

Ensuite ton champ ID doit être une vrai clé, ce qui implique aucune duplication. Ainsi tu utiliseras l'index de la clé primaire sur ta table.

Une base Access peut être une solution, mais sans connaitre ton environnement et ses contraintes difficile de proposer une solution.
Quant à la requête, puisque tu utilises la clé primaire, c'est juste une transformation de ton code PS.

Je te propose Access, car tu n'a pas besoin de l'installer sur le post. Le framework dotnet suffit.

Tutoriels PowerShell

Connexion ou Créer un compte pour participer à la conversation.

Plus d'informations
il y a 10 ans 8 mois #15626 par Matthew BETTON
Bonjour,

Je suis de l'avis de Laurent.

Toutefois, il est possible de gagner un temps non négligeable en utilisant des méthodes comme évoquées dans ces pages :

How to process large CSV file in powershell

How to use powershell to reorder CSV columns

Un exemple (ce script manque clairement de gestion d'erreurs et surement de 2 ou 3 autres choses... cela reste un exemple) :

[code:1]param(
[parameter(Mandatory=$false)]
[String]$FilePath = \"D:\fichier.csv\",
[parameter(Mandatory=$false)]
[String]$Delimiter = \",\",
[parameter(Mandatory=$false)]
[String] $SearchString = \"A1\",
[parameter(Mandatory=$false)]
[String] $SearchProperty = \"id\"
)

$reader = [System.IO.File]::OpenText(\"$FilePath\"«»)

$line = $reader.ReadLine()
$Properties = $line.Split(\"$Delimiter\"«»)
$i = 0
$Found = $false
foreach($Property in $Properties){
if(($Property -replace \"`\"\",\"\"«») -eq $SearchProperty){
$Found = $true
Break
}
$i++
}

if(-not $Found){
Write-Warning \"Impossible de trouver la propriété '$SearchProperty' dans le fichier '$FilePath'\"
$reader.Close()
return $null
}

Do {
$line = $reader.ReadLine()
$data = $line.Split(\"$Delimiter\"«»)

$ActualValue = $data[$i] -replace \"`\"\",\"\"

if($ActualValue -like \"$SearchString*\"«»){
$CustomObject = New-Object PSObject
$j = 0
Foreach($Property in $Properties){
Add-Member -InputObject $CustomObject -MemberType NoteProperty -Name ($Property -replace \"`\"\",\"\"«») -Value ($data[$j] -replace \"`\"\",\"\"«»)
$j ++
}
Write-Output $CustomObject
}

} Until($reader.EndOfStream)

$reader.Close()

[/code:1]

Voir avec 'Measure-Command { <code ou script> }' le temps pris pour un traitement...

@ +

Matthew

Connexion ou Créer un compte pour participer à la conversation.

Plus d'informations
Plus d'informations
il y a 10 ans 8 mois #15629 par Gabriel
Hello

merci, je sais que le csv tel quel a manipuler c'est bon sur des ficheir de taille \"honnete\".

la persistance, est plus ou moins nulle le fichier CSV est regenéré tous les soirs par le ldap (je n'ai pas un acces direct au ldap)

donc dans l'idee d'utiliser une bdd je pensais a un sqlite ou un MSSQL CE pour ne pas m'encombrer d'un serveur bdd (pas penser a Access)

merci pour tout je vais regarder.

Connexion ou Créer un compte pour participer à la conversation.

Plus d'informations
il y a 10 ans 8 mois #15632 par Laurent Dardenne
tonic8 écrit:

la persistance, est plus ou moins nulle le fichier CSV est regenéré tous les soirs par le ldap (je n'ai pas un acces direct au ldap)

S'il s'agit d'une extraction, tu seras obligé de parcourir l'intégralité du fichier pour l'insérer dans la table.Avec l'index tu évites une passe.

Si tu peux placer ton champ ID en début de ligne, un select-string + une regex peut être une autre solution.
Ainsi tu es assuré d'avoir une seule lecture du fichier csv sans avoir à traiter/transformer les lignes jugées inutiles que ce soit avec PS ou un SGBD.

Tutoriels PowerShell

Connexion ou Créer un compte pour participer à la conversation.

Temps de génération de la page : 0.086 secondes
Propulsé par Kunena