Pergunta

Embora talvez seja uma coisa bizarra de se fazer, preciso criar um Array em .Net com um limite inferior> 0.A princípio, isso parece ser possível, usando:

Array.CreateInstance(typeof(Object), new int[] {2}, new int[] {9});

Produz os resultados desejados (uma matriz de objetos com um limite inferior definido como 9).No entanto, a instância do array criado não pode mais ser passada para outros métodos esperando Object[] me dando um erro dizendo que:

System.Object[*] não pode ser lançado em um System.Object[].Qual é essa diferença nos tipos de array e como posso superar isso?

Editar:código de teste =

Object x = Array.CreateInstance(typeof(Object), new int[] {2}, new int[] {9});
Object[] y = (Object[])x;

O que falha com:"Não é possível converter objeto do tipo 'System.Object[*]' para o tipo 'System.Object[]'."

Gostaria também de salientar que esta abordagem FAZ funcionam ao usar múltiplas dimensões:

Object x = Array.CreateInstance(typeof(Object), new int[] {2,2}, new int[] {9,9});
Object[,] y = (Object[,])x;

O que funciona bem.

Outras dicas

A razão pela qual você não pode lançar de um para o outro é que isso é mau.

Digamos que você crie um array de object[5..9] e o passe para uma função F como um object[].

Como a função saberia que este é um 5..9?F está esperando um array geral, mas está ficando restrito.Você poderia dizer que é possível saber, mas isso ainda é inesperado e as pessoas não querem fazer todo tipo de verificações de limites sempre que quiserem usar um array simples.

Um array é a estrutura mais simples em programação, torná-lo muito complicado o torna inutilizável.Você provavelmente precisará de outra estrutura.

O que você deve fazer é uma classe que seja uma coleção restrita que imite o comportamento desejado.Dessa forma, todos os usuários dessa classe saberão o que esperar.

class ConstrainedArray<T> : IEnumerable<T> where T : new()
{
    public ConstrainedArray(int min, int max)
    {
        array = new T[max - min];
    }

    public T this [int index]
    {
        get { return array[index - Min]; }
        set { array[index - Min] = value; }
    }

    public int Min {get; private set;}
    public int Max {get; private set;}

    T[] array;

    public IEnumerator<T> GetEnumerator()
    {
        return array.GetEnumarator();
    }

    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
    {
        return array.GetEnumarator();
    }

}

Não sei por que isso não pode ser passado como Object[], mas não seria fácil se você apenas criasse uma classe real para agrupar um array e lidar com sua "lógica estranha" lá?

Você obteria os benefícios de usar um objeto de referência real onde pudesse adicionar "inteligência" à sua classe.

Editar:Como você está lançando seu Array, poderia postar mais algum código?Obrigado.

Basta armazenar seu limite inferior em um número inteiro const offset e subtrair esse valor de tudo o que sua fonte retorna como índice.

Também:este é um recurso antigo do VB6.Acho que pode haver um atributo para ajudar a apoiá-lo.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top