4

我目前有一个响应 HTTP 请求的 C# 应用程序。HTTP 请求 (XML) 的正文被传递到 SQL Server,此时数据库引擎执行正确的指令。其中一条指令用于使用客户的 id (InvoiceLoad) 加载有关发票的信息:

<InvoiceLoad ControlNumber="12345678901">
   <Invoice>
      <CustomerID>johndoe@gmail.com</CustomerID>
   </Invoice>
</InvoiceLoad>  

我需要对发票表(包含关联的电子邮件地址)执行 SELECT 操作。

我试过使用:

SELECT 'Date', 'Status', 'Location' 
FROM Invoices 
WHERE Email_Address = Invoice.A.value(.)  

using an xml.nodes('InvoiceLoad/Invoice/CustomerId') Invoice(A)

命令。

但是,由于此查询每分钟可能运行数千次,因此我希望使其尽可能快。我听说这样做的一种方法可能是使用 CROSS APPLY (我从未使用过)。那是解决方案吗?如果没有,我将如何尽可能快地进行此查询?非常感谢任何和所有建议!

4

1 回答 1

1

我不明白你为什么需要调用.nodes()- 据我了解,每个 XML 片段只有一个条目 - 对吧?

所以给定这个 XML:

<InvoiceLoad ControlNumber="12345678901">
   <Invoice>
      <CustomerID>johndoe@gmail.com</CustomerID>
   </Invoice>
</InvoiceLoad>  

您可以使用此 SQL 来获取<CustomerID>节点的值:

DECLARE @xmlvar XML

SET @xmlvar = '<InvoiceLoad ControlNumber="12345678901">
   <Invoice>
      <CustomerID>johndoe@gmail.com</CustomerID>
   </Invoice>
</InvoiceLoad>'

SELECT 
   @xmlvar.value('(/InvoiceLoad/Invoice/CustomerID)[1]', 'varchar(100)') 

您可以将其加入您的客户表或您需要做的任何事情。

<CustomerID>如果您将XML 存储在一个中,并且您总是需要从然后使用方便加入。这需要做一些工作——一个将XML输入作为输入的存储函数——但它确实是一种从 XML 中“显示”某些重要数据片段的好方法。

第 1 步:创建您的函数

CREATE FUNCTION dbo.ExtractCustomer (@input XML)
RETURNS VARCHAR(255)
WITH SCHEMABINDING
AS BEGIN
    DECLARE @Result VARCHAR(255)

    SELECT 
        @Result = @Input.value('(/InvoiceLoad/Invoice/CustomerID)[1]', 'varchar(255)') 

    RETURN @result
END

因此,给定您的 XML,您将获得一个<CustomerID>节点并提取其“内部文本”并将其作为VARCHAR(255).

第 2 步:向您的表中添加一个计算的、持久的列

ALTER TABLE dbo.YourTableWithTheXML
ADD CustomerID AS dbo.ExtractCustomer(YourXmlColumnHere) PERSISTED

现在,具有 XML 列的表有一个新列 -CustomerID它将自动<CustomerID>包含VARCHAR(255). 该值是持久的,即只要 XML 不改变,就不必重新计算。您可以像使用表中的任何其他列一样使用该列,甚至可以对其编制索引以加速其上的任何连接!

于 2012-06-20T19:00:22.123 回答