Assume that we have a customers and an orders XML document. The examples below demonstrate grouping, aggregation and join in XQuery.
<?xml version="1.0"?> <customers> <customer custid="1"> <first-name>Bobby</first-name> <last-name>Nguyen</last-name> <phone>206-111-2222</phone> </customer> <customer custid="2"> <first-name>SonHa</first-name> <last-name>Pham</last-name> <phone>503-222-3333</phone> </customer> <customer custid="3"> <first-name>Ngan</first-name> <last-name>Le</last-name> <phone>928-464-732</phone> </customer> </customers>
<?xml version="1.0"?> <orders> <order orderid="1"> <custid>1</custid> <orderdate>2014-05-15</orderdate> <shipaddress> <address>343 2nd Ave S.</address> <city>Seattle</city> <region>WA</region> <postalcode>98142</postalcode> </shipaddress> <items> <item itemid="a1"> <quantity>1</quantity> <unitprice>10.00</unitprice> </item> </items> <subtotal>10.00</subtotal> </order> <order orderid="2"> <custid>2</custid> <orderdate>2014-06-01</orderdate> <shipaddress> <address>1000 Johnson St.</address> <city>Portland</city> <region>OR</region> <postalcode>97209</postalcode> </shipaddress> <items> <item itemid="a1"> <quantity>1</quantity> <unitprice>10.00</unitprice> </item> <item itemid="b1"> <quantity>2</quantity> <unitprice>20.00</unitprice> </item> </items> <subtotal>50.00</subtotal> </order> <order orderid="3"> <custid>2</custid> <orderdate>2014-07-01</orderdate> <shipaddress> <address>1000 Johnson St.</address> <city>Portland</city> <region>OR</region> <postalcode>97209</postalcode> </shipaddress> <items> <item itemid="a1"> <quantity>2</quantity> <unitprice>10.00</unitprice> </item> <item itemid="b1"> <quantity>1</quantity> <unitprice>20.00</unitprice> </item> </items> <subtotal>40.00</subtotal> </order> <order orderid="4"> <custid>2</custid> <orderdate>2014-07-10</orderdate> <shipaddress> <address>1000 Johnson St.</address> <city>Portland</city> <region>OR</region> <postalcode>97209</postalcode> </shipaddress> <items> <item itemid="a1"> <quantity>1</quantity> <unitprice>10.00</unitprice> </item> </items> <subtotal>10.00</subtotal> </order> </orders>
-- load xml files to SQL Server as CLOB = Character Large Object DECLARE @customers XML = (SELECT * FROM OPENROWSET(BULK 'C:\Self_Dev\XML\customers.xml', SINGLE_CLOB) AS customers); DECLARE @orders XML = (SELECT * FROM OPENROWSET(BULK 'C:\Self_Dev\XML\orders2.xml', SINGLE_CLOB) AS orders); -- Concatenate XML documents using XML PATH mode. DECLARE @customers_orders XML = (SELECT @customers, @orders FOR XML PATH(''));
--Aggregation without join. --count # of order for each customer (group by customer). SELECT @customers_orders.query( 'for $custid in distinct-values(//orders/order/custid) let $o := //orders/order[custid = $custid] return <customer_order> <custid>{$custid}</custid> <ordercount>{count($o)}</ordercount> </customer_order> ');
<customer_order> <custid>1</custid> <ordercount>1</ordercount> </customer_order> <customer_order> <custid>2</custid> <ordercount>3</ordercount> </customer_order>
--aggregation with inner join. --count # of order for each customers and list the customer name. SELECT @customers_orders.query( 'for $custid in distinct-values(//orders/order/custid) let $o := //orders/order[custid = $custid] let $c := //customers/customer[@custid = $custid] return <customer_order> <custid>{$custid}</custid> {$c/first-name} {$c/last-name} <ordercount>{count($o)}</ordercount> </customer_order> ');
<customer_order> <custid>1</custid> <first-name>Bobby</first-name> <last-name>Nguyen</last-name> <ordercount>1</ordercount> </customer_order> <customer_order> <custid>2</custid> <first-name>SonHa</first-name> <last-name>Pham</last-name> <ordercount>3</ordercount> </customer_order>
--Aggregation with outer join. --count # of order for each customers and list the customer name, -- and include customer didn't have any order. SELECT @customers_orders.query( 'for $c in //customers/customer let $o := //orders/order[custid = $c/@custid] return <customer_order> {$c/first-name} {$c/last-name} <ordercount>{count($o)}</ordercount> </customer_order> ');
<customer_order> <first-name>Bobby</first-name> <last-name>Nguyen</last-name> <ordercount>1</ordercount> </customer_order> <customer_order> <first-name>SonHa</first-name> <last-name>Pham</last-name> <ordercount>3</ordercount> </customer_order> <customer_order> <first-name>Ngan</first-name> <last-name>Le</last-name> <ordercount>0</ordercount> </customer_order>
--aggregation with outer join. --count # of order, and sum the orders amount -- for each customers and list the customer name, -- and include customer didn't have any order. SELECT @customers_orders.query( 'for $c in //customers/customer let $o := //orders/order[custid = $c/@custid] return <customer_order> {$c/first-name} {$c/last-name} <ordercount>{count($o)}</ordercount> <totalordersamount>{sum($o/subtotal)}</totalordersamount> </customer_order> ');
<customer_order> <first-name>Bobby</first-name> <last-name>Nguyen</last-name> <ordercount>1</ordercount> <totalordersamount>10</totalordersamount> </customer_order> <customer_order> <first-name>SonHa</first-name> <last-name>Pham</last-name> <ordercount>3</ordercount> <totalordersamount>100</totalordersamount> </customer_order> <customer_order> <first-name>Ngan</first-name> <last-name>Le</last-name> <ordercount>0</ordercount> <totalordersamount>0.0E0</totalordersamount> </customer_order>
No comments:
Post a Comment