web-dev-qa-db-ja.com

データベースからnull許容のDateTimeを取得する方法

私のSQLServerデータベースにはnull許容のDateTime値が含まれています。 C#のアプリケーションでそれらをnull許容のDateTimeオブジェクトに変換するにはどうすればよいですか?

これは私がそれがどのように見えるかと思うものですが、そうではありません:

DateTime? dt = (DateTime?) sqldatareader[0];
17
pikachu

SQLnullは.NETnullと同じではありません。 System.DBNull.Valueと比較する必要があります。

_object sqlDateTime = sqldatareader[0];
DateTime? dt = (sqlDateTime == System.DBNull.Value)
    ? (DateTime?)null
    : Convert.ToDateTime(sqlDateTime);
_

あなたのコメントに答えて、ItemDataReaderプロパティのデータ型は、基礎となるデータベースタイプのデータ型です。 null以外のSQLServerデータベースの場合は_System.Data.SqlTypes.SqlDateTime_、null列の場合は_System.DBNull_、ODBCデータベースの場合は_System.Data.Odbc.OdbcTypes.SmallDateTime_、または実際には信頼できるのは、タイプがobjectであるということだけです。

これが、DateTimeに型強制の代わりにConvert.ToDateTime()を使用することを提案する理由でもあります。 ODBCまたは任意の日付列を.NETDateTimeに強制変換できるという保証はありません。コメントで「sqldatareader」とSQLServer _System.Data.SqlTypes.SqlDateTime_は確かに_System.DateTime_に強制変換できますが、元の質問ではそれはわかりませんでした。

DataReadersの使用の詳細については、 [〜#〜] msdn [〜#〜] を参照してください。

28
Dour High Arch

私は最近このトリックを見つけました、それは簡単です:

DateTime? dt = sqldatareader[0] as DateTime?;
30
pikachu

値が単なるnullではなく「DBNull」であるかどうかを確認する必要があります。ブログに小さなヘルパークラスを投稿しました: http://improve.dk/archive/2007/10/08/handling-dbnulls.aspx

クラスを実装したら、次のように使用します。

DateTime? dt = DBConvert.To<datetime?>(sqldatareader[0]);
2

少し前に、私はDataRowがこの種のダウンキャストを実行するための一連の拡張メソッドを作成しました...繰り返しの戯言を書くのは嫌だからです。使い方は簡単です:

_foreach( DataRow dr in someDataTable )
{
  DateTime? dt = dr.CastAsDateTimeNullable( "lastUpdated" ) ;
  int       id = dr.CastAsInt( "transactionID" ) ;
  // etc.
}
_

これがDateTime値の一部です。他のデータ型の実装を追加するのは非常に簡単です。 DataReaderに同じようなことをするのは、それほど難しいことではありません。

ジェネリックメソッドを考え出そうとしましたが、ジェネリックの実行方法に制限があるため、実行が困難または不可能であり、希望する動作を得ることができました(たとえば、default(T)ではなくnull値— _0_とnull... difficultを区別するSQLNULLのデフォルト値を取得します。

_public static class DataRowExtensions
{

  #region downcast to DateTime

  public static DateTime CastAsDateTime( this DataRow row , int index )
  {
    return toDateTime( row[index] ) ;
  }
  public static DateTime CastAsDateTime( this DataRow row , string columnName )
  {
    return toDateTime( row[columnName] ) ;
  }

  public static DateTime? CastAsDateTimeNullable( this DataRow row , int index )
  {
    return toDateTimeNullable( row[index] );
  }
  public static DateTime? CastAsDateTimeNullable( this DataRow row , string columnName )
  {
    return toDateTimeNullable( row[columnName] ) ;
  }

  #region conversion helpers

  private static DateTime toDateTime( object o )
  {
    DateTime value = (DateTime)o;
    return value;
  }

  private static DateTime? toDateTimeNullable( object o )
  {
    bool  hasValue = !( o is DBNull );
    DateTime? value    = ( hasValue ? (DateTime?) o : (DateTime?) null ) ;
    return value;
  }

  #endregion

  #endregion downcast to DateTime

  // ... other implementations elided .. for brevity

}
_
1
Nicholas Carey

ヘルパーメソッドを作成するのはどうですか

private static DateTime? MyDateConverter(object o)
{
    return (o == DBNull.Value || o == null) ? (DateTime?)null : Convert.ToDateTime(o);
}

使用法

MyDateConverter(sqldatareader[0])
1
Usman Ali
DateTime? dt = null;

if (sqldatareader[0] != System.DbNull.Value)
{
    dt = (DateTime)sqldatareader[0];
}
0
Paddy

使用するだけです:

System.Nullable<System.DateTime> yourVariableName;

自分で簡単にしてください:)

0
MTELab