Frage

Ich habe viele, viele Versionen von diesem auf SO gesehen, aber keiner von ihnen scheinen ziemlich Arbeit für meine Bedürfnisse.

kommt Meine Daten von einem Anbieter-Datenbank, die null für Datetime-Felder ermöglicht. Zunächst ziehe ich meine Daten in eine Datentabelle.

using (SqlCommand cmd = new SqlCommand(sb.ToString(), conn))
using (SqlDataAdapter da = new SqlDataAdapter(cmd))
{
    da.Fill(dt);
}

Ich bin ein Datatable in eine Liste konvertieren <> für die Verarbeitung.

var equipment = from i in dt.AsEnumerable()
    select new Equipment()
    {
        Id = i.Field<string>("ID"),
        BeginDate = i.Field<DateTime>("BeginDate"),
        EndDate = i.Field<DateTime>("EndDate"),
        EstimatedLife = i.Field<double>("EstimatedLife")
    }

Also, wie kann ich überprüfen, für DBNull in diesem Fall? Ich habe versucht, ein Verfahren zu schreiben.

    public DateTime CheckDBNull(object dateTime)
    {
        if (dateTime == DBNull.Value)
            return DateTime.MinValue;
        else
            return (DateTime)dateTime;
    }
War es hilfreich?

Lösung

Eine mögliche Option ist speichern Sie es als eine Nullable-Datum Zeit mit der Syntax DateTime?

Hier ist ein Link auf die MSDN über die Verwendung von Nullable Types

Andere Tipps

Verwenden Sie IsDBNull()

System.Convert.IsDBNull(value);

oder wenn Sie eine SqlDataReader

reader.IsDBNull(ordinal);

Und Ihre DateTime Eigenschaften machen nullable (DateTime?) und Set null bei DBNull sein. Field<T>() wird dies automatisch tun.

Hier ist ein Beispiel für einige Codes verwende ich Datetime lesen

Ich bin sicher, es könnte besser werden geschrieben, aber läuft gut für mich

   public DateTime? ReadNullableDateTimefromReader(string field, IDataRecord data)
    {

        var a = data[field];
        if (a != DBNull.Value)
        {
            return Convert.ToDateTime(a);
        }
        return null;
    }

    public DateTime ReadDateTimefromReader(string field, IDataRecord data)
    {
        DateTime value;
        var valueAsString = data[field].ToString();
        try
        {
            value = DateTime.Parse(valueAsString);
        }
        catch (Exception)
        {
            throw new Exception("Cannot read Datetime from reader");
        }

        return value;
    }

Ich habe festgestellt, dass der einfachste Weg, dies zu handhaben ist, das Feld als Datentyp wirft das „als“ Schlüsselwort. Dies funktioniert gut für Datenbankfelder, die null sein kann, und ist schön und einfach.

Hier ist ausführlicher auf diese: Angießen vs ‚als‘ Operator

Beispiel:

    IDataRecord record = FromSomeSqlQuerySource;
    string nullableString;
    DateTime? nullableDateTime;

    nullableString = record["StringFromRecord"] as string;
    nullableDateTime = record["DateTimeFromRecord"] as DateTime?;

Sie sollten DataRow["ColumnName"] is DBNull verwenden Datetime null zu vergleichen.

Z. B:.

 if(studentDataRow["JoinDate"] is DBNull) { // Do something here }

Ich schrieb eine generische Erweiterung Methode, die ich in all meinen Projekten verwenden:

public static object GetValueSafely<T>(this System.Data.DataTable dt, string ColumnName, int index)
{
    if (typeof(T) == typeof(int))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return 0;
    }
    else if (typeof(T) == typeof(double))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return 0;
    }
    else if (typeof(T) == typeof(decimal))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return 0;
    }
    else if (typeof(T) == typeof(float))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return 0;
    }
    else if (typeof(T) == typeof(string))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return string.Empty;
    }
    else if (typeof(T) == typeof(byte))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return 0;
    }
    else if (typeof(T) == typeof(DateTime))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return DateTime.MinValue;
    }
    else if (typeof(T) == typeof(bool))
    {
        if (dt.Rows[index][ColumnName] != DBNull.Value)
            return dt.Rows[index][ColumnName];
        else
            return false;
    }
    if (dt.Rows[index][ColumnName] != DBNull.Value)
        return dt.Rows[index][ColumnName];
    else
        return null;
}

Anwendungsbeispiel:

private void Example()
{
    DataTable dt = GetDataFromDb() // get data from database...
    for (int i = 0; i < dt.Rows.Count; i++)
    {
        Console.WriteLine((DateTime)dt.GetValueSafely<DateTime>("SomeDateColumn", i));
        Console.WriteLine((int)dt.GetValueSafely<int>("SomeIntColumn", i));
        Console.WriteLine((string)dt.GetValueSafely<string>("SomeStringColumn", i));
    }
}
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top