C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

Re[4]: SqlParameterの、sizeについて


(過去ログ 19 を表示中)

[トピック内 7 記事 (1 - 7 表示)]  << 0 >>

■7751 / inTopicNo.1)  SqlParameterの、sizeについて
  
□投稿者/ いとう (1回)-(2007/09/14(Fri) 11:34:36)

分類:[C#] 

(.NET C#) System.Data.SqlClient.SqlParameter について、

コンストラクタ (String, SqlDbType, Int32) のInt32は、パラメータの長さを指定しますが、
これは例えば、SQL Serverのデータ型がVARCHAR等の場合、テーブルの列のサイズを指定するのが妥当だと思います。
だとすると、常に列のサイズ変更の影響を受けることになり、管理が面倒な気がします。
(例)
SqlParameter nameParam = new SqlParameter("@name", SqlDbType.VarChar, 10);
nameParam.Value = "xxx";

SqlCommand cmd = new SqlCommand("INSERT INTO ...略", _sqlConnection);
cmd.Parameters.Add(nameParam);
cmd.Prepare();



パラメータの長さを指定しない場合は、コンストラクタ SqlParameter(String, SqlDbType) ですが、
可変長(VARCHAR等)のデータ型の場合、System.Data.SqlClient.SqlCommandのPrepareメソッドにおいて例外が発生します(下記)。
# System.InvalidOperationException: SqlCommand.Prepare メソッドは、可変長のパラメータは
# すべて明示的に設定された non-zero サイズを持つことを要求します。



どうも、そう書かれてあるようです。
# SqlCommand.Prepare メソッド
# http://msdn2.microsoft.com/ja-jp/library/system.data.sqlclient.sqlcommand.prepare.aspx
# 可変長データ型を指定する場合は、Size の最大値も指定する必要があります。



また他に、SqlParameter.ValueのToString().Lengthにあたるものを引数のサイズとして使用するのは、意味があるとは思えません。



テーブルの列のサイズを、プログラムで管理したくない状況もあるはずですが、
列のサイズ変更の影響を受けない、他に良いやり方があるんでしょうか?

そもそもみなさんは、どうやっているのでしょうか?
サイズの管理が面倒だと思われている方も多いのではないかと思いますが、そのあたりはどうなんでしょうか?

引用返信 編集キー/
■7766 / inTopicNo.2)  Re[1]: SqlParameterの、sizeについて
□投稿者/ はつね (273回)-(2007/09/14(Fri) 15:54:51)
はつね さんの Web サイト
No7751 (いとう さん) に返信
> (.NET C#) System.Data.SqlClient.SqlParameter について、

http://msdn2.microsoft.com/ja-jp/library/system.data.sqlclient.sqlparameter.size.aspx
↑によればSizeプロパティは省略した場合はパラメタ値から推測されます。
つまり、パラメタの入力値の時に実際に入っている値よりも短めの値にする事でDBに渡すときに自動的に切り捨てられるという機能を働かせられるという事なのではないでしょうか。で、その機能を使いたくないときは省略しなさいと。


引用返信 編集キー/
■7772 / inTopicNo.3)  Re[2]: SqlParameterの、sizeについて
□投稿者/ いとう (2回)-(2007/09/14(Fri) 16:49:42)
> http://msdn2.microsoft.com/ja-jp/library/system.data.sqlclient.sqlparameter.size.aspx
> ↑によればSizeプロパティは省略した場合はパラメタ値から推測されます。
> つまり、パラメタの入力値の時に実際に入っている値よりも短めの値にする事でDBに渡すときに自動的に切り捨てられるという機能を働かせられるという事なのではないでしょうか。で、その機能を使いたくないときは省略しなさいと。


これは実際にプログラムを動かしてみると、
可変長データ型(varchar等)の場合は指定しておかないと、例外がthrowされます。推測してくれないようです。(先に書いた例外messageと同じ)
Int32の場合などは、sizeの指定は不要でした。可変長でない為だと思われます。
引用返信 編集キー/
■7780 / inTopicNo.4)  Re[3]: SqlParameterの、sizeについて
□投稿者/ むねお (5回)-(2007/09/14(Fri) 17:34:52)
こんにちわ。
データの切捨てに関しては、SqlCommand.Prepare メソッドの使用の有無に関わらず発生するようです。
http://bbs.wankuma.com/index.cgi?mode=al2&namber=3959&KLOG=13
私も以前、パラメータクエリーでVARCHAR型の列に定義サイズ内でしたが、サイズの大きいデータをサイズ指定をしなかった場合に、適当な長さで切られた覚えがあります。

本題のサイズ指定ですが、以前、SqlDataReader.GetSchemaTable メソッドでスキーマ情報からサイズを取得して設定したことがあります。
(もっとスマートな方法があるかも知れませんが。)
http://support.microsoft.com/kb/310108/ja
引用返信 編集キー/
■7783 / inTopicNo.5)  Re[3]: SqlParameterの、sizeについて
□投稿者/ はつね (274回)-(2007/09/14(Fri) 18:46:36)
はつね さんの Web サイト
No7772 (いとう さん) に返信
> これは実際にプログラムを動かしてみると、
> 可変長データ型(varchar等)の場合は指定しておかないと、例外がthrowされます。推測してくれないようです。(先に書いた例外messageと同じ)

それってバグなんじゃ?
ODP.NETはどうだっただろう。気にした事ないから大丈夫だったような。

引用返信 編集キー/
■7792 / inTopicNo.6)  Re[4]: SqlParameterの、sizeについて
□投稿者/ いとう (3回)-(2007/09/14(Fri) 19:38:05)
> 本題のサイズ指定ですが、以前、SqlDataReader.GetSchemaTable メソッドでスキーマ情報からサイズを取得して設定したことがあります。
> (もっとスマートな方法があるかも知れませんが。)
> http://support.microsoft.com/kb/310108/ja

なるほど、以前にsizeを指定した実績があるということは、恐らくその時、sizeを指定しない方法が無かったからではないかと思います。

スキーマ情報から取ってくのは、有効な手段かもしれません。

ただ、sizeを指定しなければならないという言語仕様なら、特殊な気がしますが...そのくらい推測して処理して欲しいですよねぇ...
引用返信 編集キー/
■7793 / inTopicNo.7)  Re[4]: SqlParameterの、sizeについて
□投稿者/ いとう (4回)-(2007/09/14(Fri) 19:48:49)
> それってバグなんじゃ?
> ODP.NETはどうだっただろう。気にした事ないから大丈夫だったような。

そうですねぇ、どうやら、SELECT文ならsizeの指定は不要のようです。
ただ、INSERT・UPDATEでは、どうしても必要でした。

INSERT・UPDATEで、size指定有り
# 正常に処理可能

INSERT・UPDATEで、size指定無し
# 例外の発生
# System.InvalidOperationException: SqlCommand.Prepare メソッドは、可変長のパラメータは
# すべて明示的に設定された non-zero サイズを持つことを要求します。


説明にも、
# http://msdn2.microsoft.com/ja-jp/library/system.data.sqlclient.sqlcommand.prepare.aspx
# 可変長データ型のパラメータの場合は、Size プロパティに、必要な最大サイズを設定する必要が
# あります。これらの条件が満たされていない場合は、Prepare からエラーが返されます。


どうも、C#では簡単には済ませてもらえないようです...
引用返信 編集キー/


トピック内ページ移動 / << 0 >>

このトピックに書きこむ

過去ログには書き込み不可

管理者用

- Child Tree -