gpt4 book ai didi

c# - 返回字符串时,Database.AddOutParameter 中的 Size 参数使用什么?

转载 作者:太空狗 更新时间:2023-10-29 17:39:26 30 4
gpt4 key购买 nike

我得到一个字符串作为输出参数,并且需要知道在调用 AddOutParameter 时为 Size 参数设置什么。

我知道我可以只使用一些巨大的数字,例如 int.MaxValue,但想了解最佳实践。

在SQL Server中,列实际上是一个uniqueidentifier类型。正在执行的 T-SQL 语句插入一条记录,然后将一些输出变量设置为新插入记录的 ID 和 GUID。这是我正在使用的实际代码,但变量名称已更改。

database.AddOutParameter(cmd, "@someInt", DbType.Int32, 0);
database.AddOutParameter(cmd, "@someString", DbType.String, 0);

database.ExecuteNonQuery(cmd);

someInt = (int)database.GetParameterValue(cmd, "@someInt");
someString = database.GetParameterValue(cmd, "@someString").ToString();

执行时,出现以下错误...

System.InvalidOperationException: String[2]: Size 属性的大小为 0 无效。

所以对我来说很明显,您不能只使用大小为 0 的字符串输出参数。您可以使用 Int32 输出参数来做到这一点,但我想字符串需要有效的大小。那么设置大小的最佳做法是什么?它可以是一个巨大的尺寸而不影响性能吗?我可以将它设置为 int.MaxValue 或其他吗?有没有可以在这里使用的常量; (没有看到任何 String.MaxValue - 您可能可以看出我是 C# 的新手,具有 Java 背景)。

我是否应该找出 uniqueidentifier 列的最大大小并将大小设置为该大小?如果我对 VARCHAR 或 NVARCHAR 列做同样的事情呢?

我希望框架能为我做这件事;我不想为作为输出获得的每个字符串指定大小。有人在这里对最佳实践有任何建议吗?

我已经阅读了下面的帖子以及 MSDN 文档,但我还没有找到真正的最佳实践答案。

AddOutParameter - non-magic number way of finding length of DBType.Int32

Read VARBINARY(MAX) from SQL Server to C#

最佳答案

我们发现您使用了错误的 UniqueIdentifer 类型。您应该使用 DbType.Guid 而不是字符串,但是您在评论中提出了我无法在评论中回答的其他问题,我不确定所以我需要测试。

他们是

  • 您应该将不同字符串输出参数的大小设置为多少?
  • 它是 Nvarchar 还是 varchar 重要吗?
  • 如果你让它太大或太小会怎样?

我首先使用 SqlCommandBuilder.DeriveParameters 找出 ADO.NET 和 SQL Server 认为它应该是什么,然后执行存储过程以查看我们的返回值是什么。

Sql Type     | DbType                | Size | Returned string.Length()
----------------------------------------------------------------
Varchar(10) | AnsiString | 10 | 9
Char(10) | AnsiStringFixedLength | 10 | 10
Nvarchar(10 | String | 10 | 9
Varchar(max) | AnsiString | -1 | 20,480
NVarchar(max)| String | -1 | 20,480

正如预期的那样,导出的大小与所有字符类型的长度字段相匹配,除了最大值和预期长度的返回值。然而,在查看最大类型和 DbTypes 时,我们对前三个问题产生了一些新问题。

  • AnsiString 类型有什么问题?如果我们将其设置为 DbType.String,如果我们保持相同的大小,它会影响输出吗? 回答:不,不是,可能是因为 .NET 字符串是 unicode

  • 增加 Paramater.Size 会影响任何非最大值吗? 回答:是的,但仅限于 char(10)。它通过添加空格来增加输出大小。

  • 减小 Paramater.Size 会影响任何非最大值吗? 是的,它会截断返回值

  • 大小为 -1 是魔法吗? 回答:是的,如果您将大小设置为 -1,它将返回值,就像您已正确设置它们一样

测试代码.NET 4.0 SQL Server 2008

SQL 代码

CREATE PROCEDURE SomeOutput( 
@tenVC varchar(10) output,
@tenC char(10) output,
@tenNVC nvarchar(10) output,
@maxVC varchar(max) output,
@maxNVC nvarchar(max) output,
@Indentifier uniqueidentifier output)
AS


SELECT @tenC = '123456789',
@tenVC = '123456789',
@tenNVC = '123456789',
@Indentifier = NEWID(),
@maxVC = '',
@maxNVC = ''



SELECT
@maxVC = @maxVC + '1234567890',
@maxNVC = @maxNVC + '1234567890'
FROM
master..spt_values
WHERE
type= 'P'

C#代码

static void Main(string[] args)
{

using (SqlConnection cnn = new SqlConnection("Server=.;Database=Test;Trusted_Connection=True;"))
{
SqlCommand cmd = new SqlCommand("SomeOutput", cnn);
cmd.CommandType = CommandType.StoredProcedure;
cnn.Open();
SqlCommandBuilder.DeriveParameters(cmd);

Printparams(cmd.Parameters, "Derived");

foreach (SqlParameter param in cmd.Parameters)
{
//By default output parameters are InputOutput
//This will cause problems if the value is both null
if (param.Direction == ParameterDirection.InputOutput )
param.Direction = ParameterDirection.Output;

}


cmd.ExecuteNonQuery();

Printparams(cmd.Parameters ,"Executed");


cmd.Parameters["@tenVC"].DbType = DbType.String;
cmd.Parameters["@tenNVC"].DbType = DbType.AnsiString;

cmd.ExecuteNonQuery();

Printparams(cmd.Parameters, "DbType change");



foreach (SqlParameter param in cmd.Parameters)
{
if (param.DbType != DbType.Int32
&& param.DbType != DbType.Guid
&& param.Size != -1)
{
param.Size = param.Size * 2;

}
}

cmd.ExecuteNonQuery();

Printparams(cmd.Parameters, "Mangeled sizes up");


foreach (SqlParameter param in cmd.Parameters)
{
if (param.DbType != DbType.Int32
&& param.DbType != DbType.Guid
&& param.Size != -1)
{
param.Size = param.Size / 4;

}
}

cmd.ExecuteNonQuery();

Printparams(cmd.Parameters, "Mangeled sizes down");

cmd.Parameters["@maxVC"].Size = Int32.MaxValue;
cmd.Parameters["@maxNVC"].Size = Int32.MaxValue;

cmd.ExecuteNonQuery();

Printparams(cmd.Parameters, "Fixed max sizes");

foreach (SqlParameter param in cmd.Parameters)
{
if (param.DbType != DbType.Int32
&& param.DbType != DbType.Guid)
{
param.Size = -1;

}
}

cmd.ExecuteNonQuery();

Printparams(cmd.Parameters, "is negative one magic");

}
}

输出

Derived
@RETURN_VALUE : Int32 : 0 : ReturnValue : 0 :
@tenVC : AnsiString : 10 : InputOutput : 0 :
@tenC : AnsiStringFixedLength : 10 : InputOutput : 0 :
@tenNVC : String : 10 : InputOutput : 0 :
@maxVC : AnsiString : -1 : InputOutput : 0 :
@maxNVC : String : -1 : InputOutput : 0 :
@Indentifier : Guid : 0 : InputOutput : 0 :

Executed
@RETURN_VALUE : Int32 : 0 : ReturnValue : 1 : 0
@tenVC : AnsiString : 10 : Output : 9 : 123456789
@tenC : AnsiStringFixedLength : 10 : Output : 10 : 123456789
@tenNVC : String : 10 : Output : 9 : 123456789
@maxVC : AnsiString : -1 : Output : 20480 : 123456789012345678901234567
@maxNVC : String : -1 : Output : 20480 : 123456789012345678901234567
@Indentifier : Guid : 0 : Output : 36 : eccc3632-4d38-44e8-9edf-031

DbType change
@RETURN_VALUE : Int32 : 0 : ReturnValue : 1 : 0
@tenVC : String : 10 : Output : 9 : 123456789
@tenC : AnsiStringFixedLength : 10 : Output : 10 : 123456789
@tenNVC : AnsiString : 10 : Output : 9 : 123456789
@maxVC : AnsiString : -1 : Output : 20480 : 123456789012345678901234567
@maxNVC : String : -1 : Output : 20480 : 123456789012345678901234567
@Indentifier : Guid : 0 : Output : 36 : 94cb0039-8587-4357-88fb-25c

Mangeled sizes up
@RETURN_VALUE : Int32 : 0 : ReturnValue : 1 : 0
@tenVC : String : 20 : Output : 9 : 123456789
@tenC : AnsiStringFixedLength : 20 : Output : 20 : 123456789
@tenNVC : AnsiString : 20 : Output : 9 : 123456789
@maxVC : AnsiString : -1 : Output : 20480 : 123456789012345678901234567
@maxNVC : String : -1 : Output : 20480 : 123456789012345678901234567
@Indentifier : Guid : 0 : Output : 36 : 4de88f14-9963-4a78-b09b-bb6

Mangeled sizes down
@RETURN_VALUE : Int32 : 0 : ReturnValue : 1 : 0
@tenVC : String : 5 : Output : 5 : 12345
@tenC : AnsiStringFixedLength : 5 : Output : 5 : 12345
@tenNVC : AnsiString : 5 : Output : 5 : 12345
@maxVC : AnsiString : -1 : Output : 20480 : 123456789012345678901234567
@maxNVC : String : -1 : Output : 20480 : 123456789012345678901234567
@Indentifier : Guid : 0 : Output : 36 : 5e973e72-14e5-4b75-9cff-e88

Fixed max sizes
@RETURN_VALUE : Int32 : 0 : ReturnValue : 1 : 0
@tenVC : String : 5 : Output : 5 : 12345
@tenC : AnsiStringFixedLength : 5 : Output : 5 : 12345
@tenNVC : AnsiString : 5 : Output : 5 : 12345
@maxVC : AnsiString : 2147483647 : Output : 20480 : 123456789012345678901234567
@maxNVC : String : 2147483647 : Output : 20480 : 123456789012345678901234567
@Indentifier : Guid : 0 : Output : 36 : 6cab2b41-d4ba-42d2-a93a-e59

is negative one magic
@RETURN_VALUE : Int32 : 0 : ReturnValue : 1 : 0
@tenVC : String : -1 : Output : 9 : 123456789
@tenC : AnsiString : -1 : Output : 10 : 123456789
@tenNVC : AnsiString : -1 : Output : 9 : 123456789
@maxVC : AnsiString : -1 : Output : 20480 : 123456789012345678901234567
@maxNVC : String : -1 : Output : 20480 : 123456789012345678901234567
@Indentifier : Guid : 0 : Output : 36 : 0d69ed57-fab7-49c8-b03a-d75

关于c# - 返回字符串时,Database.AddOutParameter 中的 Size 参数使用什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10855366/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com