2011-02-07 8 views
5

Estoy usando System.Data.SQLite, seleccionando de una tabla de base de datos sqlite donde la columna tiene tipo 'entero', y cuando hago algo como esto:Cuando selecciono de la columna sqlite del tipo 'int' puedo convertir a .net int pero cuando selecciono de la columna 'integer' no puedo

int x = (int)reader["myColumn"]; 

falla. El problema no es que el valor sea nulo; la columna no puede contener nulos. Si cambio el tipo de datos de la columna a 'int', entonces funciona bien. Los valores en la columna son '2', '3', '4', etc .; nada muy grande.

¿Alguien sabe si esto es comportamiento esperado?

Respuesta

10

Como el otro que se menciona, el entero SQLite se almacena en 1, 2, 3, 4, 6 u 8 bytes. Sin embargo, no obtendrá excepciones de desbordamiento o fuera de rango.

En ese contexto, (int) es un elenco, no una conversión. Si reader[] no devolvió un objeto de tipo entero, si está devolviendo un tipo numérico diferente, obtendrá una excepción de conversión, independientemente del valor que contenga.

Según el rango de valores válidos para el entero SQLite, supongo que devuelve el valor como un entero de 64 bits, long. Para verificarlo, intente esto:

object x = reader["myColumn"]; 
Debug.WriteLine(x.GetType().Name); 
+1

Estaba volviendo a esta pregunta para responderla yo mismo después de descubrir que, de hecho, 'long x = (long) reader [" myColumn "];' funciona bien. Tienes toda la razón, fue un Int64, así que usar variables largas me funcionará. En cuanto a por qué el comportamiento funciona de manera diferente para INT e INTEGER, todavía me resulta extraño. Puedo repetir el éxito/fracaso de la conversión desde INT/INTEGER, para los mismos valores de datos en la tabla, y también puedo replicar el problema en otra tabla. Presumiblemente solo una ligera inconsistencia en el controlador. – Rory

2

La excepción se produce porque datareader.Item[] vuelve object.

El problema se debe al boxeo/unboxing. No tiene nada que ver con la propia base de datos ...

salidas
long a = 1; 
int b = 2; 
object objectA = a; 
object objectB = b; 
Console.WriteLine((int)a); 
Console.WriteLine((long)b); 
Console.WriteLine((int)objectA); 
Console.WriteLine((long)objectB); 

de la consola 2, entonces 1, pero será una excepción en el elenco de objectA, objectB. Esta es una característica de .NET que no tiene nada que ver con los controladores ODBC.

Cuestiones relacionadas