在SQL Server中,我们可以将十六进制表示形式的变量定义为
DECLARE @hex INT = 0xF; --This assigns value 15 to @hex
是否也可以使用二进制来定义它们
DECLARE @bin INT = 0b1111; --I have tried this, it doesn't work
这是SQL Server Constants(它们的文字术语)的完整文档。
没有提供输入作为二进制1和0的语法。他们确实有一些被称为“binary constant”的东西,但这只是你在问题中已经使用的十六进制语法。
(这也表明您的第一个示例实际上是二进制常量的示例,并且隐式转换为int
)
SQL Server没有开箱即用的读取或存储二进制文件的功能,没有。如果你要存储二进制文件,你需要在varchar
中这样做。即DECLARE @bin varchar(4) = '1111';
。
一旦将值存储为varchar
,就需要使用函数将值拆分出来。现在,您可以在SQL Server中存储的最大数字(作为整数)是9223372036854775807
,它是二进制的63位数字(因此我们将使用varchar(64)
来存储负数)。
然后我们可以创建一个表值函数来将值从二进制转换为整数:
CREATE FUNCTION dbo.BinaryToInt (@Binary varchar(64))
RETURNS TABLE WITH SCHEMABINDING AS
RETURN
WITH C0 AS(SELECT 1 AS c UNION ALL SELECT 1),
C1 AS(SELECT 1 AS c FROM C0 AS A CROSS JOIN C0 AS B),
C2 AS(SELECT 1 AS c FROM C1 AS A CROSS JOIN C1 AS B),
C3 AS(SELECT 1 AS c FROM C2 AS A CROSS JOIN C2 AS B),
N AS (
SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) AS I
FROM C3)
SELECT SUM(POWER(2, CASE B.V WHEN '-' THEN NULL ELSE N.I END -1) * B.V) * CASE WHEN MIN(B.V) = '-' THEN -1 ELSE 1 END AS IntegerValue
FROM N
CROSS APPLY (VALUES (SUBSTRING(REVERSE(@Binary), N.I, 1))) B(V)
WHERE B.V <> '';
GO
最后,我们可以声明变量并设置值:
DECLARE @Bin int;
SELECT @bin = IntegerValue
FROM dbo.BinaryToInt ('1111');
SELECT @bin;
SELECT @bin = IntegerValue
FROM dbo.BinaryToInt ('-11101');
SELECT @Bin;
希望有所帮助。
我意识到真正的二进制数字没有负数,但这只是我的简短处理。
编辑:虽然我知道Op说这不是他们(似乎?)所要求的,但是,为了完成,我做了上面签名和未签名的版本:
CREATE FUNCTION dbo.UnSignedBinaryToInt (@Binary varchar(63))
RETURNS TABLE WITH SCHEMABINDING AS
RETURN
WITH C0 AS(SELECT 1 AS c UNION ALL SELECT 1),
C1 AS(SELECT 1 AS c FROM C0 AS A CROSS JOIN C0 AS B),
C2 AS(SELECT 1 AS c FROM C1 AS A CROSS JOIN C1 AS B),
C3 AS(SELECT 1 AS c FROM C2 AS A CROSS JOIN C2 AS B),
N AS (
SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) AS I
FROM C3)
SELECT SUM(POWER(2, N.I - 1) * B.V) AS IntegerValue
FROM N
CROSS APPLY (VALUES (SUBSTRING(REVERSE(@Binary), N.I, 1))) B(V)
WHERE B.V <> ''
AND @Binary NOT LIKE '%[^01]%' --Eliminate values that aren't binary;
GO
CREATE FUNCTION dbo.SignedBinaryToInt (@Binary varchar(64))
RETURNS TABLE WITH SCHEMABINDING AS
RETURN
WITH C0 AS(SELECT 1 AS c UNION ALL SELECT 1),
C1 AS(SELECT 1 AS c FROM C0 AS A CROSS JOIN C0 AS B),
C2 AS(SELECT 1 AS c FROM C1 AS A CROSS JOIN C1 AS B),
C3 AS(SELECT 1 AS c FROM C2 AS A CROSS JOIN C2 AS B),
N AS (
SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) AS I
FROM C3),
I AS (
SELECT SUM(POWER(2, N.I - 1) * B.V) AS IntegerValue
FROM N
CROSS APPLY (VALUES (SUBSTRING(REVERSE(RIGHT(@Binary, LEN(@Binary)-1)), N.I, 1))) B(V)
WHERE B.V <> ''
AND @Binary NOT LIKE '%[^01]%' --Eliminate values that aren't binary
)
SELECT IntegerValue * CASE LEFT(@binary,1) WHEN 1 THEN -1 ELSE 1 END AS IntegerValue
FROM I;
GO
SELECT IntegerValue
FROM dbo.UnSignedBinaryToInt ('00001111');
SELECT IntegerValue
FROM dbo.SignedBinaryToInt ('10001111');
SELECT IntegerValue
FROM dbo.UnSignedBinaryToInt ('10001111');
SELECT IntegerValue
FROM dbo.UnSignedBinaryToInt ('00201111');
GO
这将分别返回值15
,-15
,143
和NULL
(由于2)。