none
Anonyme Datentypen übergabe RRS feed

  • Frage

  • Hallo zusammen,

    es ist ja ohne Probleme möglich Anonyme Datentypen zu erstellen

    Nun habe ich folgendes Problem :

    Mein Datalayer gibt mir folgendes/bzw. soll folgendes zurückgeben.

    public List<object > GetFilesForUpload()
        {
          var e = from i in db.Files
              where i.Uploaded
              where i.FoundWave
              select new
                    {
                      i.Kampagne,
                      i.Kdnr,
                      i.xml,
                      i.file
                    };
          return e.Cast<object>().ToList();
        }

    Nur wie werte ich das Objekt wieder aus ?Oder soll ich mir dafür lieber einen Struct erstellen ?

     

    Grüße

    Donnerstag, 24. Juni 2010 11:07

Antworten

  • Hallo Pawel,

    es ist ja ohne Probleme möglich Anonyme Datentypen zu erstellen

    Nun habe ich folgendes Problem :

    Mein Datalayer gibt mir folgendes/bzw. soll folgendes zurückgeben.

    public List<object > GetFilesForUpload()
      {
       var e = from i in db.Files
         where i.Uploaded
         where i.FoundWave
         select new
            {
             i.Kampagne,
             i.Kdnr,
             i.xml,
             i.file
            };
       return e.Cast<object>().ToList();
      }

    Nur wie werte ich das Objekt wieder aus ?

    Besser ist es hier, wenn Du Dir eine eigene Klasse mit den Eigenschaften erstellst, die Du benötigst und mit dieser dann Deine Abfrage erstellst:

    class UploadFileInfo { 
    	public string Kampagne {get; set;} 
    	public int KdNr {get; set;} 
    	public string Xml {get; set;} 
    	public string File {get; set;} 
    	
    	public UploadFileInfo(
    			string kampagne, 
    			int kdNr, 
    			string xml, 
    			string file) 
    	{ 
    		this.Kampange = kampagne;
    		this.KdNr = kdNr; 
    		this.Xml = xml; 
    		this.File = file; 
    	} 
    } 
    // ... 
    
    public List>UploadFileInfo< GetFilesForUpload() { 
    	var e = from i in db.Files 
    		where i.Uploaded 
    		where i.FoundWave 
    		select new UploadFileInfo ( 
    				i.Kampagne, 
    				i.Kdnr, 
    				i.xml, 
    				i.file 
    				); 
    	return e.ToList(); 
    } 
    
    Kann noch Fehler enthalten, da frei geschrieben. Aber das Prinzip sollte klar sein.

    Thorsten Dörfler
    Microsoft MVP Visual Basic
    vb-faq.de
    • Als Antwort markiert Pawel Warmuth Donnerstag, 24. Juni 2010 12:26
    Donnerstag, 24. Juni 2010 11:35
    Beantworter
  • Hallo Pawel,

    das ginge nur via Reflection, siehe z. B.:
    http://blogs.msdn.com/b/wriju/archive/2007/10/26/c-3-0-anonymous-type-and-net-reflection-hand-in-hand.aspx

    Aber will man typisiert weiterarbeiten, ist es sinnvoller selbst eine Klasse zu erstellen.
    In einigen Fällen wäre eine Alternative - weil oben das Wort mit X vorkommt ;-)
    ein XDocument -> XElement zu nutzen.

    Gruß Elmar

    • Als Antwort markiert Pawel Warmuth Donnerstag, 24. Juni 2010 12:26
    Donnerstag, 24. Juni 2010 11:42
    Beantworter

Alle Antworten

  • Hallo Pawel,

    es ist ja ohne Probleme möglich Anonyme Datentypen zu erstellen

    Nun habe ich folgendes Problem :

    Mein Datalayer gibt mir folgendes/bzw. soll folgendes zurückgeben.

    public List<object > GetFilesForUpload()
      {
       var e = from i in db.Files
         where i.Uploaded
         where i.FoundWave
         select new
            {
             i.Kampagne,
             i.Kdnr,
             i.xml,
             i.file
            };
       return e.Cast<object>().ToList();
      }

    Nur wie werte ich das Objekt wieder aus ?

    Besser ist es hier, wenn Du Dir eine eigene Klasse mit den Eigenschaften erstellst, die Du benötigst und mit dieser dann Deine Abfrage erstellst:

    class UploadFileInfo { 
    	public string Kampagne {get; set;} 
    	public int KdNr {get; set;} 
    	public string Xml {get; set;} 
    	public string File {get; set;} 
    	
    	public UploadFileInfo(
    			string kampagne, 
    			int kdNr, 
    			string xml, 
    			string file) 
    	{ 
    		this.Kampange = kampagne;
    		this.KdNr = kdNr; 
    		this.Xml = xml; 
    		this.File = file; 
    	} 
    } 
    // ... 
    
    public List>UploadFileInfo< GetFilesForUpload() { 
    	var e = from i in db.Files 
    		where i.Uploaded 
    		where i.FoundWave 
    		select new UploadFileInfo ( 
    				i.Kampagne, 
    				i.Kdnr, 
    				i.xml, 
    				i.file 
    				); 
    	return e.ToList(); 
    } 
    
    Kann noch Fehler enthalten, da frei geschrieben. Aber das Prinzip sollte klar sein.

    Thorsten Dörfler
    Microsoft MVP Visual Basic
    vb-faq.de
    • Als Antwort markiert Pawel Warmuth Donnerstag, 24. Juni 2010 12:26
    Donnerstag, 24. Juni 2010 11:35
    Beantworter
  • Hallo Pawel,

    das ginge nur via Reflection, siehe z. B.:
    http://blogs.msdn.com/b/wriju/archive/2007/10/26/c-3-0-anonymous-type-and-net-reflection-hand-in-hand.aspx

    Aber will man typisiert weiterarbeiten, ist es sinnvoller selbst eine Klasse zu erstellen.
    In einigen Fällen wäre eine Alternative - weil oben das Wort mit X vorkommt ;-)
    ein XDocument -> XElement zu nutzen.

    Gruß Elmar

    • Als Antwort markiert Pawel Warmuth Donnerstag, 24. Juni 2010 12:26
    Donnerstag, 24. Juni 2010 11:42
    Beantworter
  • Hallo,

     

    ok der einfachheithalber mache ich mir dann doch meine Klasse ;-)

    Elmar, das Problem ist das auf die Datenbank auch nicht .net Programme zugreifen und denen ist schwierig XDocument beizubringen ;-)

    Also bleibt da wohl der XML string ^^

    Danke für eure Antworten !

    Donnerstag, 24. Juni 2010 12:28
  • Hallo Pawel,

    auch, wenn schon Haken hinter Antworten sind ;-)
    ich will ein wenig berichtigen/klarstellen, was gesagt wurde.

    - Es ist nicht so, dass das nur über Reflection geht. Es gibt mehrere Methoden,
      mit anonymen Typen weiter zu arbeiten. Darunter u.a. DatenBinding und
      das dynamic Schlüsselwort.

    - Es ist nicht immer sinnvoll und auch nicht einfach "besser" mit Klassen
       weiterzuareiten. Meistens nur dann, wenn der Overhead der Instanziierung
       der zusätzlichen Klasse durch andere Anforderungen/Vorteile abgedeckt ist.
       Etwa die Mehrfachnutzbarkeit der Klasse. 

    Ein paar (zusätzliche) Beispiele für die Weiterverarbeitung, bei denen Du (unter anderem) sogar solche Objekte einfach an den DataSource eines DataGridView's binden kannst:

     private void Form1_Load(object sender, EventArgs e)
     {
      dc = new AdventureWorksLT2008Entities(); // Mock (1)
      var ret = GetFilesForUpload();
     
      dgv.DataSource = ret;
      MessageBox.Show(dgv[0, 0].Value.ToString()); // (2)
    
      dynamic ersterDatensatz = ret.FirstOrDefault(); // (3)
      MessageBox.Show(ersterDatensatz.FirstName);
     
      BindingSource bs = new BindingSource();  // (4) 
      bs.DataSource = ret; dynamic satz1 = bs[0];
      MessageBox.Show(satz1.FirstName); 
     }
    
     IEnumerable<object> GetFilesForUpload() // Mock-Beispiel
     {
      var custs =
       from c in dc.Customers
       where c.FirstName.StartsWith("f")
       select new { c.FirstName, c.LastName };
      return custs as IEnumerable<object>;
     }

    ciao Frank
    Dienstag, 29. Juni 2010 08:42