2010-08-30 34 views
7

J'ai un object o qui est connu pour être une boîte int ou uint:Unboxing uint/int sans savoir ce qui est dans la boîte

object o = int.MinValue 
object o = (uint)int.MinValue // same bytes as above 

Je ne sais pas ce qui est dans la boîte, tout ce que je me soucie de est qu'il y a 4 octets là-bas que je veux contraindre à un int ou uint. Cela fonctionne très bien dans un contexte unchecked quand j'ai des valeurs (au lieu de boîtes):

unchecked 
{ 
    int a = (int)0x80000000u; // will be int.MinValue, the literal is a uint 
    uint b = (uint)int.MinValue; 
} 

Note: Par défaut, tout en C# est décochée, le contexte non contrôlée est seulement nécessaire ici car nous avons affaire à littéraux et le compilateur veut savoir si nous voulons vraiment nous tirer dans le pied.

Le problème est maintenant que je ne sais pas ce qui est à l'intérieur de la boîte (en plus de 4 octets), mais le temps d'exécution quand je tente de décoder le mauvais type je reçois un InvalidCastException. Je sais que c'est un comportement d'exécution raisonnable, mais dans ce cas, je sais ce que je fais et je veux un "unbox décochée". Est-ce que quelque chose comme ça existe?

Je sais que je pourrais catch et réessayer, donc cela ne compte pas comme une réponse.

Répondre

4

Vous pouvez utiliser Convert.ToInt32 pour convertir n'importe quel objet en un int si possible, bien qu'il effectue également une conversion ou une analyse de sorte qu'il soit plus lent que vous le souhaitez.

Si vous savez qu'il est un int ou uint, vous pouvez le faire:

int x = (o is int) ? (int)o : (int)(uint)o; 
+0

Convert soulève des exceptions de débordement (j'ai besoin de coercition sans contrôle). La vérification du contenu de la boîte est une bonne idée, espérant toujours qu'il existe une meilleure solution. –

+0

@Johannes: Vous pouvez faire 'unchecked ((uint) Convert.ToInt64 (o))' pour contourner l'exception en convertissant à une taille plus grande, bien que si vous deviez travailler sur des entiers 64 bits, vous n'auriez pas une taille plus grande pour le faire avec. – Quartermeister