Personne ne sait si il est possible de définir l'équivalent d'un "java class loader personnalisé" dans .NET?
Pour donner un peu de contexte:
Je suis dans le processus de développement d'une nouvelle programmation de la langue que les objectifs de la CLR, appelé "Liberté". Une des caractéristiques de la langue est sa capacité à définir de type "constructeurs", qui sont des méthodes qui sont exécutées par le compilateur au moment de la compilation et de générer des types de sortie. Ils sont en quelque sorte une généralisation des génériques (la langue n'est normale, les génériques), et permettre à ce type de code à écrire (dans "la Liberté" de la syntaxe):
var t as tuple<i as int, j as int, k as int>;
t.i = 2;
t.j = 4;
t.k = 5;
Où "tuple" est défini comme suit:
public type tuple(params variables as VariableDeclaration[]) as TypeDeclaration
{
//...
}
Dans cet exemple particulier, le constructeur de type "tuple" offre quelque chose de similaire pour les types anonymes en VB et C#.
Cependant, à la différence des types anonymes, "tuples" ont des noms et peut être utilisé à l'intérieur d'publique signatures de méthode.
Cela signifie que j'ai besoin d'un moyen pour le type qui finalement finit par être émis par le compilateur pour être partageable entre plusieurs assemblées. Par exemple, je veux
tuple<x as int>
défini à l'Assemblée à la fin du même type que tuple<x as int>
défini dans l'Assemblage B.
Le problème avec cela, bien sûr, est que l'Assemblage et de Montage B vont être recueillies à des moments différents, ce qui signifie qu'ils seraient tous les deux finissent par émettant leurs propres versions incompatibles de la tuple de type.
J'ai regardé dans l'aide de une sorte de type "effacement" pour ce faire, de sorte que j'aurais une bibliothèque partagée avec un tas de types comme ça (c'est la "Liberté" de la syntaxe):
class tuple<T>
{
public Field1 as T;
}
class tuple<T, R>
{
public Field2 as T;
public Field2 as R;
}
et puis il suffit de rediriger les accès à partir du i, j, et k n-uplet champs "Champ1", "Champ2", et "Field3".
Cependant ce n'est pas vraiment une option viable. Cela signifie qu'au moment de la compilation, tuple<x as int>
et tuple<y as int>
finirait par être de différents types, alors que lors de l'exécution en temps, elles seront considérées comme un même type. Que serait la cause de nombreux problèmes pour des choses comme l'égalité et le type d'identité. C'est trop percé d'une abstraction à mon goût.
Une autre option possible serait d'utiliser "état sac des objets". Cependant, à l'aide d'un état sac encontre de l'objectif d'une prise en charge de type "constructeurs" dans la langue. L'idée est de permettre à "la coutume des extensions de langage" pour générer de nouveaux types au moment de la compilation, le compilateur peut faire vérifier le type statique avec.
En Java, ce qui pourrait être fait en utilisant des chargeurs de classe. Fondamentalement, le code qui utilise tuple types pourraient être émis sans réellement définir le type de disque. Une coutume "class loader" pourrait alors être définies pour générer dynamiquement le tuple de type à l'exécution. Qui permettrait de vérifier le type statique à l'intérieur du compilateur, et permettrait d'unifier le tuple types à la compilation des limites.
Malheureusement, cependant, le CLR ne fournit pas de support pour la classe personnalisée de chargement. Le chargement dans le CLR est fait au niveau de l'assemblage. Il serait possible de définir une autre assemblée pour chaque "type construit", mais qui serait très rapidement conduire à des problèmes de performances (ayant de nombreuses assemblées avec un seul type dans entre eux utilisent trop de ressources).
Donc, ce que je veux savoir, c'est:
Est-il possible de simuler quelque chose comme Classe Java Chargeurs de .NET, où je peux émettre une référence à un non-type existant, puis de générer dynamiquement une référence de ce type à l'exécution avant que le code les besoins de l'utilisation qu'il fonctionne?
NOTE:
*En fait je connais déjà la réponse à la question, qui je fournir comme réponse ci-dessous. Cependant, il m'a fallu environ 3 jours de recherche, et un peu de IL le piratage afin de trouver une solution. J'ai pensé que ce serait une bonne idée de les consigner ici au cas où quelqu'un d'autre a couru dans le même problème. *