操作用户定义的类型 (UDT) 数据

适用范围:SQL Server

Transact-SQL 在修改用户定义类型(UDT)列中的数据时,不提供 INSERTUPDATEDELETE 语句的专用语法。 Transact-SQL CASTCONVERT 函数用于将本机数据类型强制转换为 UDT 类型。

在 UDT 列中插入数据

以下 Transact-SQL 语句将三行示例数据插入 Points 表中。 Point 数据类型由作为 UDT 属性公开的 X 和 Y 整数值组成。 必须使用 CASTCONVERT 函数将逗号分隔的 X 和 Y 值强制转换为 Point 类型。 前两个语句使用 CONVERT 函数将字符串值转换为 Point 类型,第三个语句使用 CAST 函数:

INSERT INTO dbo.Points (PointValue)
VALUES (CONVERT (Point, '3,4'));

INSERT INTO dbo.Points (PointValue)
VALUES (CONVERT (Point, '1,5'));

INSERT INTO dbo.Points (PointValue)
VALUES (CAST ('1,99' AS Point));

选择数据

以下 SELECT 语句选择 UDT 的二进制值。

SELECT ID, PointValue
FROM dbo.Points;

若要查看以可读格式显示的输出,请调用 Point UDT 的 ToString 方法,该方法将值转换为其字符串表示形式。

SELECT ID, PointValue.ToString() AS PointValue
FROM dbo.Points;

下面是结果集。

ID PointValue
-- ----------
 1 3,4
 2 1,5
 3 1,99

还可以使用 Transact-SQL CASTCONVERT 函数来实现相同的结果。

SELECT ID, CAST (PointValue AS VARCHAR)
FROM dbo.Points;

SELECT ID, CONVERT (VARCHAR, PointValue)
FROM dbo.Points;

Point UDT 将其 X 和 Y 坐标公开为属性,然后你可以单独选择这些坐标。 以下 Transact-SQL 语句单独选择 X 和 Y 坐标:

SELECT ID,
       PointValue.X AS xVal,
       PointValue.Y AS yVal
FROM dbo.Points;

X 和 Y 属性将返回整数值,该值在结果集中显示。

ID xVal yVal
-- ---- ----
 1    3    4
 2    1    5
 3    1   99

使用变量

可以使用 DECLARE 语句处理变量,将变量分配给 UDT 类型。 以下语句使用 Transact-SQL SET 语句赋值,并通过对变量调用 UDT 的 ToString 方法来显示结果:

DECLARE @PointValue AS Point;

SET @PointValue = (SELECT PointValue
                   FROM dbo.Points
                   WHERE ID = 2);

SELECT @PointValue.ToString() AS PointValue;

结果集显示变量值:

PointValue
----------
-1,5

以下 Transact-SQL 语句使用 SELECT 而不是变量赋值 SET 实现相同的结果:

DECLARE @PointValue AS Point;

SELECT @PointValue = PointValue
FROM dbo.Points
WHERE ID = 2;

SELECT @PointValue.ToString() AS PointValue;

对变量赋值使用 SELECTSET 之间的区别在于,SELECT 允许在一个 SELECT 语句中分配多个变量,而 SET 语法要求每个变量赋值都有自己的 SET 语句。

比较数据

如果将 IsByteOrdered 属性设置为在定义类时 true,则可以使用比较运算符来比较 UDT 中的值。 有关详细信息,请参阅 创建用户定义的类型

SELECT ID, PointValue.ToString() AS Points
FROM dbo.Points
WHERE PointValue > CONVERT (Point, '2,2');

无论值本身是否可比较,无论 IsByteOrdered 设置如何,都可以比较 UDT 的内部值。 以下 Transact-SQL 语句选择 X 大于 Y 的行:

SELECT ID, PointValue.ToString() AS PointValue
FROM dbo.Points
WHERE PointValue.X < PointValue.Y;

还可以将比较运算符与变量一起使用,如此查询中所示,用于搜索匹配 PointValue

DECLARE @ComparePoint AS Point;
SET @ComparePoint = CONVERT (Point, '3,4');

SELECT ID, PointValue.ToString() AS MatchingPoint
FROM dbo.Points
WHERE PointValue = @ComparePoint;

调用 UDT 方法

还可以调用 Transact-SQL 中 UDT 中定义的方法。 Point 类包含三种方法:DistanceDistanceFromDistanceFromXY。 有关定义这三种方法的代码列表,请参阅 创建具有 ADO.NET的用户定义类型。

以下 Transact-SQL 语句调用 PointValue.Distance 方法:

SELECT ID,
       PointValue.X AS [Point.X],
       PointValue.Y AS [Point.Y],
       PointValue.Distance() AS DistanceFromZero
FROM dbo.Points;

结果显示在 Distance 列中:

ID X  Y  Distance
-- -- -- ----------------
 1  3  4                5
 2  1  5 5.09901951359278
 3  1 99 99.0050503762308

DistanceFrom 方法采用 Point 数据类型的参数,并显示从指定点到 PointValue的距离:

SELECT ID,
       PointValue.ToString() AS Pnt,
       PointValue.DistanceFrom(CONVERT (Point, '1,99')) AS DistanceFromPoint
FROM dbo.Points;

结果显示表中每一行 DistanceFrom 方法的结果:

ID Pnt DistanceFromPoint
-- --- -----------------
 1 3,4  95.0210502993942
 2 1,5                94
 3 1,9                90

DistanceFromXY 方法将点单独用作参数:

SELECT ID,
       PointValue.X AS X,
       PointValue.Y AS Y,
       PointValue.DistanceFromXY(1, 99) AS DistanceFromXY
FROM dbo.Points;

结果集与 DistanceFrom 方法相同。

更新 UDT 列中的数据

若要更新 UDT 列中的数据,请使用 Transact-SQL UPDATE 语句。 还可以使用 UDT 的方法以更新对象的状态。 以下 Transact-SQL 语句更新表中的单个行:

UPDATE dbo.Points
SET PointValue = CAST ('1,88' AS Point)
WHERE ID = 3;

还可以单独更新 UDT 元素。 以下 Transact-SQL 语句仅更新 Y 坐标:

UPDATE dbo.Points
SET PointValue.Y = 99
WHERE ID = 3;

如果使用字节排序设置为 true定义 UDT,Transact-SQL 可以在 WHERE 子句中计算 UDT 列。

UPDATE dbo.Points
SET PointValue = '4,5'
WHERE PointValue = '3,4';

更新限制

不能使用 Transact-SQL 一次性更新多个属性。 例如,以下 UPDATE 语句失败并出现错误,因为一个 UPDATE 语句中不能使用相同的列名两次。

UPDATE dbo.Points
SET PointValue.X = 5, PointValue.Y = 99
WHERE ID = 3;

若要单独更新每个点,需要在 Point UDT 程序集中创建一个 mutator 方法。 然后,可以调用 mutator 方法以更新 Transact-SQL UPDATE 语句中的对象,如以下示例所示:

UPDATE dbo.Points
SET PointValue.SetXY(5, 99)
WHERE ID = 3;

删除 UDT 列中的数据

若要删除 UDT 中的数据,请使用 Transact-SQL DELETE 语句。 以下语句删除表中与 WHERE 子句中指定的条件匹配的所有行。 如果在 DELETE 语句中省略 WHERE 子句,则将删除表中的所有行。

DELETE dbo.Points
WHERE PointValue = CAST ('1,99' AS Point);

如果要删除 UDT 列中的值,同时保留其他行值不变,请使用 UPDATE 语句。 此示例将 PointValue 设置为 null。

UPDATE dbo.Points
SET PointValue = NULL
WHERE ID = 2;