第2章丨IRIS SQL —— 隐式联接(箭头语法)

写在前面

InterSystems SQL 提供了一个特殊的 –> 运算符作为从相关表获取值的简写,而在某些常见情况下,无需指定显式 JOIN 的复杂性。此箭头语法可以代替显式连接语法使用,也可以与显式连接语法结合使用。箭头语法执行左外连接

箭头语法可用于引用类的属性或父表的关系属性。其他类型的关系和外键不支持箭头语法。不能在 ON 子句中使用箭头语法 (–>)。

1. 属性引用

可以使用 –> 运算符作为从“引用的表”中获取值的简写。

1.1 定义两个类

例如,假设您定义了两个类:

Company:

Class Sample.Company Extends %Persistent [DdlAllowed]
{
/// The Company name
Property Name As %String;
}

员工:

Class Sample.Employee Extends %Persistent [DdlAllowed]
{
/// The Employee name
Property Name As %String;

/// The Company this Employee works for
Property Company As Company;
}

1.2 使用 –> 运算符

Employee 类包含一个属性,该属性是对 Company 对象的引用。在基于对象的应用程序中,可以使用点语法遵循此参考。例如,要查找员工为其工作的公司的名称,请执行以下操作:

 Set name = employee.Company.Name

您可以使用使用 OUTER JOIN 联接来联接 EmployeeCompany 表的 SQL 语句执行相同的任务:

SELECT Sample.Employee.Name, Sample.Company.Name AS CompName
FROM Sample.Employee LEFT OUTER JOIN Sample.Company
ON Sample.Employee.Company = Sample.Company.ID

使用 –> 运算符,可以更简洁地执行相同的 OUTER JOIN 操作:

SELECT Name, Company->Name AS CompName
FROM Sample.Employee

1.2 在where子句中使用 –> 运算符

您可以随时使用 –> 运算符,只要您在表中有引用列;也就是说,其值是引用表的 ID 的列(实质上是外键的特殊情况)。在本例中,Sample.Employee 的“公司”字段包含 Sample.Company 表中的记录 ID。可以在查询中使用列表达式的任何位置使用 –> 运算符。例如,在 WHERE 子句中:

SELECT Name,Company AS CompID,Company->Name AS CompName
FROM Sample.Employee
WHERE Company->Name %STARTSWITH 'G'

这等效于:

SELECT E.Name,E.Company AS CompID,C.Name AS CompName
FROM Sample.Employee AS E, Sample.Company AS C
WHERE E.Company = C.ID AND C.Name %STARTSWITH 'G'

1.3 在 GROUP BY 子句中使用 –> 运算符

可以在 GROUP BY 子句中使用 –> 运算符:

SELECT Name,Company->Name AS CompName
FROM Sample.Employee
GROUP BY Company->Name

1.4 在 ORDER BY 子句中使用 –> 运算符

您可以在 ORDER BY 子句中使用 –> 运算符:

SELECT Name,Company->Name AS CompName
FROM Sample.Employee
ORDER BY Company->Name

1.5 使用–> 运算符列的列别名

或者引用 ORDER BY 子句中 –> 运算符列的列别名:

SELECT Name,Company->Name AS CompName
FROM Sample.Employee
ORDER BY CompName

1.6 复合箭头语法

支持复合箭头语法,如下面的示例所示。在此示例中,Cinema.Review 表包括 Film 字段,该字段包含 Cinema.Film 表的行 ID。Cinema.Film 表包括“类别”字段,该字段包含 Cinema.Category 表的行 ID。因此,Film->Category->CategoryName访问这三个表,以返回具有ReviewScore的每部电影的CategoryName:

SELECT ReviewScore,Film,Film->Title,Film->Category,Film->Category->CategoryName
FROM Cinema.Review
ORDER BY ReviewScore

2. 子表引用

可以使用 –> 运算符来引用子表。例如,如果 LineItemsOrders 表的子表,则可以指定:

SELECT LineItems->amount
FROM Orders

请注意,订单中没有名为 LineItems 的属性。LineItems 是包含金额字段的子表的名称。此查询在结果集中为每个 Order 行生成多行。它等效于:

SELECT L.amount
FROM Orders O LEFT JOIN LineItems L ON O.id=L.custorder

2.1 表名有包名


SELECT Patient->PA_ScreenNo,*
		FROM DHCDoc_GCPBC_Base.Plan

3. 箭头语法权限

使用箭头语法时,您必须对两个表中引用的数据具有 SELECT 权限。您必须对引用的列具有表级 SELECT 特权或列级 SELECT 特权。使用列级权限时,您需要对被引用表的 ID 以及被引用的列具有 SELECT 权限。

以下示例演示了所需的列级特权:

SELECT Name,Company->Name AS CompanyName
FROM Sample.Employee
GROUP BY Company->Name
ORDER BY Company->Name

在上面的示例中,您必须具有列级 SELECT 特权才能 Sample.Employee.NameSample.Company.NameSample.Company.ID

  SET tStatement = ##class(%SQL.Statement).%New()
  SET privchk1="%CHECKPRIV SELECT (Name,ID) ON Sample.Company"
  SET privchk2="%CHECKPRIV SELECT (Name) ON Sample.Employee"
CompanyPrivTest
  SET qStatus = tStatement.%Prepare(privchk1)
    IF qStatus'=1 {WRITE "%Prepare failed:" DO $System.Status.DisplayError(qStatus) QUIT}
  SET rset = tStatement.%Execute()
  IF rset.%SQLCODE=0 {WRITE !,"have Company privileges",! }
  ELSE {  WRITE !,"No privilege: SQLCODE=",rset.%SQLCODE,! }
EmployeePrivTest
  SET qStatus = tStatement.%Prepare(privchk2)
    IF qStatus'=1 {WRITE "%Prepare failed:" DO $System.Status.DisplayError(qStatus) QUIT}
  SET rset = tStatement.%Execute()
  IF rset.%SQLCODE=0 {WRITE !,"have Employee privilege",! }
  ELSE {  WRITE !,"No privilege: SQLCODE=",rset.%SQLCODE }
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值