2009-04-02 8 views
7

Zostałem osiodłany za pomocą wewnętrznej biblioteki dostępu do danych, która jest skutecznie XML przekazywane do procedury przechowywanej, która zwraca XML. Nic nie mogę na to poradzić. Próbowałem zatwierdzić ActiveRecord, ale moja prośba została odrzucona. Jednakże, używając doskonałego kodu podanego pod numerem http://blog.bodurov.com/Post.aspx?postID=27, dodałem metodę rozszerzenia do IEnumerable, która konwertuje pary klucz-wartość, które wykonuję z niewyrównanego XML, powracającego do silnie wpisanych obiektów, wraz z nazwami właściwości!Jak dołączyć metodę do dynamicznie tworzonego typu C# w środowisku wykonawczym?

to:

dict["keyName1"] 

staje

MyObject.keyName1 

Teraz interfejs obsługuje wiązania z danymi! Całkiem fajne! Chciałbym jednak pójść o krok dalej. Chcę, aby emitowane obiekty posiadały również metody Save(), dzięki czemu będę mógł korzystać z wzorca ActiveRecord i dostarczać moim użytkownikom WWW intuicyjną warstwę obiektów do użycia z ASP.net.

Jak napisać metodę w Visual Studio, w kodzie źródłowym i dołączyć ją w czasie wykonywania do emitowanych obiektów? Nie jestem zainteresowany (lub kwalifikuję się do) pisaniem zgromadzeń lub IL. Chciałbym to zrobić w języku C#. To jest moje pierwsze pytanie dotyczące StackOverflow i zamieszczam to za pomocą IE6 z upoważnieniem firmy, więc proszę, bądźcie łagodni.

Odpowiedz

2

Z tego, co wiem o tym artykule, tworzę anonimowe typy dla ciebie i używasz ich, by uzyskać wartości. Jeśli tak jest, nie ma łatwego sposobu dodawania metod do tych obiektów. Jeśli jednak struktura XML będzie taka sama za każdym razem, gdy SP będzie wykonywany, może nie utworzyć konkretnej klasy, która ma wszystkie potrzebne właściwości, i zapełnić kolekcję tych obiektów samodzielnie przy pomocy XML. W ten sposób można łatwo dodawać żadnych metod musisz bezpośrednio do klasy ...

EDIT: Na podstawie naszej dyskusji w komentarzach, oto myśl:

W tam kodu, gdy budujesz typ, którego używasz: ModuleBuilder.DefineType. Występuje przeciążenie DefineType, które wymaga rozszerzenia typu. Link.. Dlatego utwórz interfejs (nie musi on zawierać żadnych metod), a gdy dynamicznie budujesz typ, rozszerz ten interfejs, wykorzystując przeciążenie, do którego cię przyłączyłem. Następnie utwórz metodę rozszerzenia na tym interfejsie, który wykonuje Save().

Jest inny przeciążenia, które mogą być interesujące, że trwa typu rozszerzyć i interfejsy:

http://msdn.microsoft.com/en-us/library/f53tx4x8.aspx

EDIT2: przykładowy kod:

Najpierw należy utworzyć interfejs:

public interface ISaveExtentable //I suck at naming stuff :-p 
{ 

} 

Następnie, w kodzie, który lubiłeś w tej witrynie, znajdziesz metodę o nazwie: GetTypeBuilder. Zmień go na:

 private static TypeBuilder GetTypeBuilder(string typeSigniture) 
     { 
      AssemblyName an = new AssemblyName("TempAssembly" + typeSigniture); 
      AssemblyBuilder assemblyBuilder = 
       AppDomain.CurrentDomain.DefineDynamicAssembly(
        an, AssemblyBuilderAccess.Run); 
      ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("MainModule"); 

      TypeBuilder tb = moduleBuilder.DefineType("TempType" + typeSigniture 
           , TypeAttributes.Public | 
           TypeAttributes.Class | 
           TypeAttributes.AutoClass | 
           TypeAttributes.AnsiClass | 
           TypeAttributes.BeforeFieldInit | 
           TypeAttributes.AutoLayout 
           , typeof(object), new Type[] {typeof(ISaveExtentable)}); 
      return tb; 
     } 

Następnie należy utworzyć metodę rozszerzenia na tym interfejsie zrobić to zapisać:

public static class SaveExtendableExtensions 
    { 
      public static void Save(this ISaveExtentable ise) 
      { 
       //implement save functionality. 
      } 
    } 

Będziesz najprawdopodobniej trzeba użyć odbicie w sposobie Zapisz się, aby wszystkie właściwości, ponieważ typ został utworzony dynamicznie.

+0

"jeśli struktura XML będzie taki sam za każdym razem, SP wykonuje" uzyskać BRD 1245 RFW 3456 Nazwa projektu! itd. o różnych atrybutach za każdym razem :( –

+0

Tak, ale jestem pewien, że istnieje lista atrybutów dostępnych do wyboru. Umieść wszystkie te atrybuty w klasie jako pola zerowalne (jeśli są to typy wartości) i zapełniać tylko te, które otrzymujesz, nie sądzę, że musisz użyć jakiegoś szalonego rozwiązania, aby dynamicznie budować typ ... – BFree

+0

XML jest generowany dynamicznie i nie chcę mieć biblioteki konkretnych klas dla każdej permutacji –

1

Myślę, że to się nazywa mieszanki, które nie są bezpośrednio lub łatwo dostępne w .net. Jak jednak rozumiem, jest to jeden z głównych powodów, dla których zaprojektowano framework LinFu.

Powiązane problemy