Cherche équivalence en Linq [Résolu]

Messages postés
133
Date d'inscription
dimanche 20 mai 2007
Dernière intervention
13 juillet 2012
- 3 oct. 2010 à 12:58 - Dernière réponse :
Messages postés
133
Date d'inscription
dimanche 20 mai 2007
Dernière intervention
13 juillet 2012
- 4 oct. 2010 à 22:25
Bonjour,
je ne suis pas trop habitué aux collections & cie et je bloque un peu...

Mon code initial:
'Imports System.Environment
'Imports System.Collections.Generic
Dim var1 As New Dictionary(Of String, String)
For Each E As DictionaryEntry In GetEnvironmentVariables()
   If DirectoryExists(E.Value.ToString) Then var1.Add(E.Key.ToString, E.Value.ToString)
Next

En fait je voudrais tenter une équivalence en linq...
Dim var2 = From k As Object In GetEnvironmentVariables() Where DirectoryExists(CType(k, DictionaryEntry).Value.ToString) Select k
Fonctionne mais ne me donne pas le même résultat que varClassic.
Dim var2 = From k As KeyValuePair(Of String, String) In CType(GetEnvironmentVariables(), Dictionary(Of String, String)) Where DirectoryExists(k.Value) Select k.Value
Ne fonctionne pas (InvalidCastException)

Une idée ?
Merci bien !
Afficher la suite 

Votre réponse

6 réponses

Meilleure réponse
Messages postés
107
Date d'inscription
samedi 25 novembre 2000
Dernière intervention
4 mai 2013
- 4 oct. 2010 à 09:43
3
Merci
Bonjour,

En effet, c'est de ma faute j'aurais dû faire un peu plus attention, en testant mon code (et surtout vérifier plus en détail le contenu des retours), désolé.
Je pensais pouvoir "gagner un peu" en castant en KeyValuePair(Of String, String) mais il semblerait qu'on soit obligé de passer par des DictionaryEntry.

Quoiqu'il en soit, voici une version modifiée qui devrait (si j'ai pas encore foiré mes tests) marcher (la toute dernière solution ne sera plus présente car devenant identique à ton code de départ (enfin pas vérifié je pense qu'il faudrait rajouter le Cast(Of DictionaryEntry) tout de même)).

Dim var1 As New Dictionary(Of String, String)
For Each E As DictionaryEntry In Environment.GetEnvironmentVariables
    If IO.Directory.Exists(E.Value.ToString) Then var1.Add(E.Key.ToString, E.Value.ToString)
Next

' Type de var2: IEnumerable(Of <type anonyme>)
Dim var2 =
    From
        entry
    In
        Environment.GetEnvironmentVariables.
        Cast(Of DictionaryEntry)()
    Where
        IO.Directory.Exists(entry.Value.ToString)
    Select
        Key = entry.Key.ToString,
        Value = entry.Value.ToString

' Ici j'aurais pu aussi écrire var2.ToDictionary(...)
Dim var2Bis As Dictionary(Of String, String) =
    (
        From
            entry
        In
            Environment.GetEnvironmentVariables.
            Cast(Of DictionaryEntry)()
        Where
            IO.Directory.Exists(entry.Value.ToString)
    ).ToDictionary(Function(entry) entry.Key.ToString, Function(entry) entry.Value.ToString)

' Type de var3: IEnumerable(Of <type anonyme>)
Dim var3 =
    Environment.GetEnvironmentVariables.
    Cast(Of DictionaryEntry).
    Where(Function(entry) IO.Directory.Exists(entry.Value.ToString)).
    Select(Function(entry) New With
                           {
                               .Key = entry.Key.ToString,
                               .Value = entry.Value.ToString
                           })

' Ici j'aurais pu aussi écrire var3.ToDictionary(...)
Dim var3Bis As Dictionary(Of String, String) =
    (
        Environment.GetEnvironmentVariables.
        Cast(Of DictionaryEntry).
        Where(Function(entry) IO.Directory.Exists(entry.Value.ToString))
    ).ToDictionary(Function(entry) entry.Key.ToString, Function(entry) entry.Value.ToString)


Une petite note tout de même au passage, pour ce problème très spécifique, si personnellement j'avais à choisir, sache tout de même que j'utiliserais ta solution originelle, qui même si n'est pas en Linq, et tout aussi "efficace", claire et concise, Linq n'est pas nécessairement une solution miracle à tous les problèmes, je voulais le préciser :)

Cordialement !

P.S.: Encore désolé pour le code foireux lol

Merci Sehnsucht 3

Avec quelques mots c'est encore mieux Ajouter un commentaire

Codes Sources a aidé 90 internautes ce mois-ci

Commenter la réponse de Sehnsucht
Messages postés
107
Date d'inscription
samedi 25 novembre 2000
Dernière intervention
4 mai 2013
- 3 oct. 2010 à 15:21
0
Merci
Bonjour,

Voilà plusieurs approches possibles, à toi de voir ce qui est le plus lisible/adapté à tes yeux
(Note: je remets ta façon de faire en début et je sais que j'ai une présentation "aérée" qui peux géner en première lecture)
(Note bis: les versions 2 et 3 sont similaires c'est juste la manière de les écrire qui change façon SQL ou façon POO)

Dim var1 As New Dictionary(Of String, String)
For Each E As DictionaryEntry In Environment.GetEnvironmentVariables
    If IO.Directory.Exists(E.Value.ToString) Then var1.Add(E.Key.ToString, E.Value.ToString)
Next

' Type de var2: IEnumerable(Of KeyValuePair(Of String, String))
Dim var2 =
    From
        kvp
    In
        Environment.GetEnvironmentVariables.
        Cast(Of KeyValuePair(Of String, String))()
    Where
        IO.Directory.Exists(kvp.Value)

' Ici j'aurais pu aussi écrire var2.ToDictionary(...)
Dim var2Bis As Dictionary(Of String, String) =
    (
        From
            kvp
        In
            Environment.GetEnvironmentVariables.
            Cast(Of KeyValuePair(Of String, String))()
        Where
            IO.Directory.Exists(kvp.Value)
    ).ToDictionary(Function(kvp) kvp.Key, Function(kvp) kvp.Value)

' Type de var3: IEnumerable(Of KeyValuePair(Of String, String))
Dim var3 =
    Environment.GetEnvironmentVariables.
    Cast(Of KeyValuePair(Of String, String)).
    Where(Function(kvp) IO.Directory.Exists(kvp.Value))

' Ici j'aurais pu aussi écrire var3.ToDictionary(...)
Dim var3Bis As Dictionary(Of String, String) =
    (
        Environment.GetEnvironmentVariables.
        Cast(Of KeyValuePair(Of String, String)).
        Where(Function(kvp) IO.Directory.Exists(kvp.Value))
    ).ToDictionary(Function(kvp) kvp.Key, Function(kvp) kvp.Value)

Dim var1Bis As New Dictionary(Of String, String)
For Each kvp In Environment.GetEnvironmentVariables.Cast(Of KeyValuePair(Of String, String))()
    If IO.Directory.Exists(kvp.Value) Then var1Bis.Add(kvp.Key, kvp.Value)
Next


Cordialement !
Commenter la réponse de Sehnsucht
Messages postés
133
Date d'inscription
dimanche 20 mai 2007
Dernière intervention
13 juillet 2012
- 3 oct. 2010 à 17:30
0
Merci
Salut Sehnsucht
Merci beaucoup pour ton aide !

J'essaie de comprendre un peu et je teste ça dès que j'ai un moment !
Je suis pas trop à l'aise avec ces trucs la...

bonne soirée
++
Commenter la réponse de sturtrid
Messages postés
133
Date d'inscription
dimanche 20 mai 2007
Dernière intervention
13 juillet 2012
- 4 oct. 2010 à 08:55
0
Merci
Salut,

je viens de tester tes propositions et malheureusement aucune d'entre elles ne fonctionne... C'est curieux car cela compile effectivement, mais en mode run, on a soit la levée d'une InvalidCastException, soit la variable var contient les membres de l'exception à la place du contenu attendu.

je vais continuer à chercher une solution, si quelqu'un y voit plus clair que moi... N'hésitez pas !

Merci d'avoir proposé une solution Sehnsucht !
++
Commenter la réponse de sturtrid
Messages postés
133
Date d'inscription
dimanche 20 mai 2007
Dernière intervention
13 juillet 2012
- 4 oct. 2010 à 21:58
0
Merci
Bonsoir,

Merci beaucoup de me proposer un nouveau code.
Je viens de le voir et ne l'ai pas encore testé (ferai un test demain).
Du coup je suis effectivement resté sur l'idée générale de départ et j'ai peaufiné mon code... Je n'avais jamais utilisé de requêtes Linq et comme on en entend pas mal parler je m'étais dit que ça serait peut être bien de les utiliser. Mais t'as raison, après réflexion je pense rester sur la version "classique". Question perf je ne sais pas ce que cela donne, mais c'est effectivement plus concis.

Encore un grand merci pour ton aide précieuse !
Bonne soirée
++
Commenter la réponse de sturtrid
Messages postés
133
Date d'inscription
dimanche 20 mai 2007
Dernière intervention
13 juillet 2012
- 4 oct. 2010 à 22:25
0
Merci
Re,
en fait j'ai testé vite fait (trop curieux) et effectivement cela fonctionne parfaitement (type énumérable ou dictionnaire suivant la méthode).
Je verrai demain si cela est plus adapté ou pas...

++
Commenter la réponse de sturtrid

Vous n'êtes pas encore membre ?

inscrivez-vous, c'est gratuit et ça prend moins d'une minute !

Les membres obtiennent plus de réponses que les utilisateurs anonymes.

Le fait d'être membre vous permet d'avoir un suivi détaillé de vos demandes et codes sources.

Le fait d'être membre vous permet d'avoir des options supplémentaires.