Pergunta

Antes de começar a atirar em mim, não estou procurando fazer isso, mas alguém em Outro post disse que era possível. Como isso é possível? Eu nunca ouvi falar de herdar de nada usando a reflexão. Mas eu vi algumas coisas estranhas ...

Foi útil?

Solução

Sem as funções virtuais para substituir, não há muito sentido na subclassificação de uma classe selada.

Se você tentar escrever uma classe selada com uma função virtual, você receberá o seguinte erro do compilador:

// error CS0549: 'Seal.GetName()' is a new virtual member in sealed class 'Seal'

No entanto, você pode obter funções virtuais em classes seladas, declarando -as em uma classe base (como essa),

public abstract class Animal
{
    private readonly string m_name;

    public virtual string GetName() { return m_name; }

    public Animal( string name )
    { m_name = name; }
}

public sealed class Seal : Animal
{
    public Seal( string name ) : base(name) {}
}

O problema ainda permanece, porém, não consigo ver como você pode passar pelo compilador para permitir que você declare uma subclasse. Eu tentei usar o IronRuby (Ruby é o mais hackear de todos os idiomas hackety), mas mesmo isso não me deixou.

A parte 'selada' é incorporada ao MSIL, então eu acho que o próprio CLR realmente aplica isso. Você teria que carregar o código, dissipar -o, remover o bit 'selado', depois remontá -lo e carregar a nova versão.

Outras dicas

Sinto muito por postar suposições incorretas no outro tópico, não me lembrei corretamente. Usando o exemplo a seguir, usando o reflexo.emit, mostra como derivar de outra classe, mas falha no tempo de execução jogando uma typeLoadexception.

sealed class Sealed
{
   public int x;
   public int y;
}

class Program
{
   static void Main(string[] args)
   {
      AppDomain ad = Thread.GetDomain();
      AssemblyName an = new AssemblyName();
      an.Name = "MyAssembly";
      AssemblyBuilder ab = ad.DefineDynamicAssembly(an, AssemblyBuilderAccess.Run);
      ModuleBuilder mb = ab.DefineDynamicModule("MyModule");
      TypeBuilder tb = mb.DefineType("MyType", TypeAttributes.Class, typeof(Sealed));

      // Following throws TypeLoadException: Could not load type 'MyType' from
      // assembly 'MyAssembly' because the parent type is sealed.
      Type t = tb.CreateType();
   }
}

Isto PODERIA (aumentaria o tamanho se eu pudesse). De acordo com os caras do Freenode, envolveria modificar o código de bytes, usar o reflexo.emit e entregar ao JIT um novo conjunto de código de byte.

Não que eu CONHECER Como ... era exatamente o que eles pensavam.

O outro pôster pode ter pensado mais na linha de reflexão. Em vez das APIs de reflexão somente leitura mais usuais.

No entanto, ainda não é possível (pelo menos de acordo com Este artigo). Mas certamente é possível aparafusar algumas coisas com reflexão. Emotes que não estão presas até você tentar executar o código emitido.

Crie uma nova classe chamada GenericKeyValuebase

Coloque isso nele

  public class GenericKeyValueBase<TKey,TValue>
    {
        public TKey Key;
        public TValue Value;

        public GenericKeyValueBase(TKey ItemKey, TValue ItemValue)
        {
            Key = ItemKey;
            Value = ItemValue;
        }
    }

E herdem a partir disso, você pode adicionar métodos de extensão adicionais para adicionar/remover (addat e remover) à sua nova classe derivada (e torná -lo uma coleção/dicionário) se estiver se sentindo muito legal.

Um exemplo simples de implicação em que você usaria um sistema normal.Collection.Genic.KeyValuepair para uma base, mas pode usar o código acima

  class GenericCookieItem<TCookieKey, TCookieValue> : GenericKeyValueBase<TCookieKey,TCookieValue>
    {
        public GenericCookieItem(TCookieKey KeyValue, TCookieValue ItemValue) : base(KeyValue, ItemValue)
        {
        }
    }
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top