Autor Beitrag
frenchcancan
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 27



BeitragVerfasst: Mi 11.05.11 13:26 
Hallo!
ich habe ein dynamisches Objekt. Die Namen der Felder kenn ich erst zur Laufzeit.
Das Anlegen der Felder und deren Wert Zuweiseung geht, wenn ich es direkt mache, aber nicht mehr, wenn ich über die Methode SetValue arbeiten will.

ausblenden C#-Quelltext
1:
2:
3:
4:
using System.Dynamic; 
using System.Reflection;  
using System.Text.RegularExpressions;  // um Werte aus Text zu parsen
using MBLib.SystemTools.Dynamic;
....

zum Beispiel
dynamic obj = new Person();
obj.NachName = "Mueller";
obj.Vorname = "Anton";
obj.Alter = 23;
// das funktioniert bis hierher

Da ich aber noch nicht die Feldname kenne, möchte ich gern über die Refelction arbeiten. Und da scheine ich etwas Grundsätzliches nicht zu verstehen:
ich würde es so machen:

ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
string neuesFeld = "AnzahlKinder";  // Name des anzulegenden Feldes
int value = 2;                      // Wert, den ich zuweisen will


Type t = typeof(Person);
FieldInfo myFieldInfo = t.GetField(neuesFeld , BindingFlags.NonPublic | BindingFlags.Instance);
//Wert zuweisen
myFieldInfo.SetValue(obj,value); // funktioniert nicht, weil die Methode SetValue ein Objekt erwartet und keinen Int


und da verstehe ich nicht, warum ich als parameter ein Objekt geben soll und keinen Wert eingeben darf.
wie weise ich den Wert 2 zum Feld AnzahlKinder zu? Warum erwartet diese Methode SetValue ein Objekt?

Ich wäre dankbar, wenn jemand mir ein Beispiel geben könnte, wie ich es realisieren soll,

Vielen Dank im Voraus
frenchcancan


Moderiert von user profile iconKha: Topic aus WinForms verschoben am Mi 11.05.2011 um 17:53
Trashkid2000
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 561
Erhaltene Danke: 137



BeitragVerfasst: Mi 11.05.11 13:58 
Hallo,

ich verstehe nicht so richtig, warum Du auf Reflection zurückgreifst. Die Propertys kannst Du doch auch so abfragen, und ganz normal setzen:
ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
dynamic aPerson = new ExpandoObject();
aPerson.Name = "Mario Meir-Huber";
aPerson.Age = 25;

foreach (var property in (IDictionary<stringobject>)aPerson)
{
        
}
Aber ich persönlich finde dynamics auch irgendwie naja.
LG, Marko
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mi 11.05.11 14:01 
Zitat:
Die Namen der Felder kenn ich erst zur Laufzeit.


Eigentlich solltest du die Namen privater Felder nie kennen. Dafür sind die ja privat. Das was du da tust würde ich als Hack bezeichnen.

Zitat:
und da verstehe ich nicht, warum ich als parameter ein Objekt geben soll und keinen Wert eingeben darf.


Natürlich darfst du das. Alles ist letztlich ein Object also sollte auch Integer problemlos gehen. In diesem Fall unter der Annahme das du auch ein privates nicht statisches Feld hast das 'AnzahlKinder' heißt. Allein vom Naming her finde ich das verdächtig >99% aller Entwickler würden private Feldvariablen klein schreiben. Bist du dir sicher das AnzahlKinder nicht eher eine Property ist und kein Feld und nebenbei das die public ist und nicht private?

Edit : Beim schreiben dieser Antwort habe ich nicht berücksichtigt (weil übersehen) das dynamic verwendet wird.
Yogu
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 2598
Erhaltene Danke: 156

Ubuntu 13.04, Win 7
C# (VS 2013)
BeitragVerfasst: Mi 11.05.11 14:55 
Spricht eigentlich etwas gegen ein Dictionary<stringobject>?
frenchcancan Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 27



BeitragVerfasst: Mi 11.05.11 15:19 
Zitat:
Bist du dir sicher das AnzahlKinder nicht eher eine Property ist und kein Feld und nebenbei das die public ist und nicht private?
in

Vielleicht leigen die problem tatsächlich daran, dass das Objekt dynamisch ist.
Wenn ich folgendes schreibe:

ausblenden C#-Quelltext
1:
2:
3:
dynamic obj = new simpleObject();
obj.Name = "Mueller";
obj.Vorname = "Anton";

erzeuge ich 2 neue Properties denke ich und weise ihnen den Wert "Mueller", bzw. "Anton" zu.

Komplizierter ist es, weil das Object dynamisch ist und aus einer Textdatei heraus gebildet wird , deswegen weiss ich nicht wie die Propertynamen sind, also z. "AnzahlKinder", den ich auf "2" setzen will
Wie würde ich das denn machen?

Könnt ihr mir ein Beispiel geben?


Danke im Voraus
Kha
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 3803
Erhaltene Danke: 176

Arch Linux
Python, C, C++ (vim)
BeitragVerfasst: Mi 11.05.11 15:39 
Ich schließe mich Yogu an: Wenn immer nur dynamisch per String zugegriffen wird, wozu dann überhaupt Properties?

_________________
>λ=
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Mi 11.05.11 20:09 
Zitat:
erzeuge ich 2 neue Properties denke ich und weise ihnen den Wert "Mueller", bzw. "Anton" zu.


Nein. Du erzeugst Code der so aussieht als hättest du 2 Properties erzeugt. Ist aber reine Compilermagie. Letztlich ist dieser Dynamic Datentyp den du da an der Hand hast nur ein Dictionary und der Compiler täuscht dir vor es wären Properties. Reflection läuft da also ins leere. Solltest dir den Code vielleicht einfach mal im Reflector ansehen da wird es offensichtlich das das nicht funktionieren kann. Am besten die hier eh nicht hilfreiche Compilerilussion weglassen und, wie hier mehrfach empfohlen, gleich ein echtes Dictionary nehmen.
frenchcancan Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 27



BeitragVerfasst: Do 12.05.11 11:12 
Ja, also offensichtlich gehe ich das falsch an.

Wie würdet ihr das machen, wenn ihr eine Textdatei hättet, in der zum Beispiel "Name;Mueller;" oder "Vorname;Anton;" oder "Alter;24;" steht, um daraus automatisch ein Objekt zu erstellen in der die Werte zugewiesen sind.

Gibt es nicht ein kleines Beispiel, damit ich weiß, wie ich anfangen soll?
Vielen Dank im Voraus
frenchcancan
Ralf Jansen
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 4708
Erhaltene Danke: 991


VS2010 Pro, VS2012 Pro, VS2013 Pro, VS2015 Pro, Delphi 7 Pro
BeitragVerfasst: Do 12.05.11 12:30 
ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
Dictionary<stringstring> person = new Dictionary<stringstring>();

foreach (var line in File.ReadAllLines("MeinLiebenDaten.csv"))
{
    string[] keyValuePair = line.Split(new char[] {';'}, 2, StringSplitOptions.RemoveEmptyEntries);
    if (keyValuePair.Length != 2
        throw new Exception("Bäng");
    person[keyValuePair[0]] = keyValuePair[1];
}

if (person.ContainsKey("Name"))
    Console.WriteLine("Name = " + person["Name"]);


Beispiel mit der Annahme das deine Datei je Zeile 2 durch ein Semikolon separierte Strings enthält. Also etwa

ausblenden Quelltext
1:
2:
3:
Name;Mueller
Vorname;Anton
Alter;24
frenchcancan Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 27



BeitragVerfasst: Do 12.05.11 14:03 
Vielen Dank!
ich kann es leider erst montag probieren aber es hilft mir weiter
frenchcancan