看来你的困惑来自于误解
varbinary
是。
可变长度
是一个字节字符串,而不是字符。它甚至不是一个字符串,而是一个字节数组。
可变长度
可以表示为十六进制值的字符串,并且
可变长度
t-sql代码中的常量表示为十六进制字符串。每字节两个十六进制字符。
这个
SUBSTRING
T-SQL中的函数可以使用字符串(
varchar
)和字节(
可变长度
)
句法
子字符串(表达式、开始、长度)
“开始”和“长度”的值必须指定为
字符
ntext
,
char
或
瓦卡尔
数据类型和
字节
对于
text
,
image
,
binary
或
可变长度
数据类型。
所以,下面的t-sql触发器代码
declare @ctxt varbinary(128)
select @ctxt=context_info from master.dbo.sysprocesses where spid = @@spid
set @session=substring(@ctxt,1,4)
前4个字节(
不是字符
)来自
@ctxt
字节数组并将其分配给
@session
变量。什么类型
@会话
?很可能是
int
.
在ssms中运行此示例代码,您将看到一些整数的十六进制表示:
DECLARE @T TABLE (I int);
INSERT INTO @T VALUES
(0),
(1),
(3),
(19),
(255),
(256),
(512),
(768),
(4098),
(65535),
(65536),
(131072),
(1234567890),
(-1),
(-65535);
SELECT
I, CONVERT(varbinary(120), I) AS BinI
FROM @T;
结果
+------------+------------+
| I | BinI |
+------------+------------+
| 0 | 0x00000000 |
| 1 | 0x00000001 |
| 3 | 0x00000003 |
| 19 | 0x00000013 |
| 255 | 0x000000FF |
| 256 | 0x00000100 |
| 512 | 0x00000200 |
| 768 | 0x00000300 |
| 4098 | 0x00001002 |
| 65535 | 0x0000FFFF |
| 65536 | 0x00010000 |
| 131072 | 0x00020000 |
| 1234567890 | 0x499602D2 |
| -1 | 0xFFFFFFFF |
| -65535 | 0xFFFF0001 |
+------------+------------+
你在这个问题上的代码没有多大意义。两个都包装
strInt + strUser
进入之内
CONVERT(varbinary(120), N'" + strContextValue + "')
没有道理。
C代码应该构造二进制数组。T-SQL触发器代码要求此数组的前4个字节是
@会话
,接下来的4个字节是
@contextid
.
字节,而不是字符
.
所以,如果你想通过,就说,
131072
小数为
@会话
,
1234567890
小数为
语境
加上
myself$
字符串作为额外信息,应运行以下T-SQL代码:
declare @context_info varbinary(128); -- note 128 length here
set @context_info = 0x00020000;
-- note, there are no quotes around the constants, they are numbers, not strings
set @context_info = @context_info + 0x499602D2;
set @context_info = @context_info + CONVERT(varbinary(120), N'myself$');
-- note 120 length here, first 8 bytes are used by two integers
set context_info @context_info;
在SSMS中运行此代码,但将最后一行替换为
SELECT @context_info;
看看它能做什么。您将得到以下结果:
+------------------------------------------------+
| (No column name) |
+------------------------------------------------+
| 0x00020000499602D26D007900730065006C0066002400 |
+------------------------------------------------+
您可以看到两个整数的二进制表示形式以及Unicode文本字符串的二进制表示形式。
在C语言中,通过连接十六进制整数表示来构造此代码。
注意,你不应该
0x00020000
和
0x499602D2
引用或
CONVERT(varbinary, ...)
. 你应该只把
我自己
串入
转换(varbinary,…)
.
C代码应该如下所示:
string strUser = "myself$";
int iSession = 131072;
int iContextID = 1234567890;
StringBuilder sb = new StringBuilder();
sb.Append("declare @context_info varbinary(120);");
sb.Append("set @context_info = 0x");
sb.Append(iSession.ToString("X8"));
sb.Append(";");
sb.Append("set @context_info = @context_info + 0x");
sb.Append(iContextID.ToString("X8"));
sb.Append(";");
sb.Append("set @context_info = @context_info + CONVERT(varbinary(120), N'");
sb.Append(strUser);
sb.Append("');");
sb.Append("set context_info @context_info;");
string strContext = sb.ToSTring();
SqlCommand scContext = new SqlCommand(strContext, conn, tran);
scContext.ExecuteNonQuery();
也见
C# convert integer to hex and back again