SQL Server 2016
Field1(XML(。),null)
示例数据:
<ProcessPositionOpening xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://www.hr-xml.org/3">
<ApplicationArea xmlns="http://www.openapplications.org/oagis/9">
...
</ApplicationArea>
<DataArea>
<Process xmlns="http://www.openapplications.org/oagis/9">
...
</Process>
<PositionOpening>
<DocumentID />
<PositionRequester>
...
</PositionRequester>
<PositionProfile>
...
<PositionFormattedDescription>
<ID>...</ID>
<Content />
</PositionFormattedDescription>
...
</PositionProfile>
</PositionOpening>
</DataArea>
</ProcessPositionOpening>
在此表中,Field1设置为XML,我一直在尝试查找节点Content
可能不为NULL的所有记录。不过,我已经尝试了query
和exist
的不同示例,但似乎无法使查询正确。这是我正在尝试的当前版本,但它没有返回我的预期:
SELECT *
FROM Table1
WHERE Field1.value('(/ProcessPositionOpening/DataArea/PositionOpening/PositionProfile/PositionFormattedDescription/Content)[1]','varchar(50)') <> ''
AND Message = 'Request Received';
我也尝试过:
SELECT *
FROM Table1
WHERE Message = 'Request Received'
AND Field1.exist('/ProcessPositionOpening') = 1;
我尝试了上面的查询只是为了查看查询的基本设置是否有效。它不返回任何记录。如果我删除查询的AND
部分,则此表中有超过19,000行,这些行都采用此格式。如果我在查询的1
部分中将0
更改为AND
,它会返回记录,但我认为这是错误的(根据解释的页面) exist
函数,0表示不存在)。所以,我很困惑。
我想找到Content
节点有值的所有记录,同样找到Content
没有值的所有记录。真的很感激任何帮助。谢谢!
答案 0 :(得分:0)
我希望以下提供一些模板来解决这个问题:
DECLARE @mockup TABLE(Descr VARCHAR(100),theXML XML);
INSERT INTO @mockup VALUES
('<content> exists with value','<root><content>blah</content></root>' )
,('<content> exists without value','<root><content></content></root>' ) --semantically the same as self-closed...
,('<content> exists self-closed','<root><content/></root>' )
,('<content> does not exist','<root></root>' );
--Find a Content with value
SELECT * FROM @mockup
WHERE theXML.exist('/root/content/text()')=1;
--Find a Content with or without value
SELECT * FROM @mockup
WHERE theXML.exist('/root/content')=1;
--Find a Content without value
SELECT * FROM @mockup
WHERE theXML.exist('/root/content[empty(text())]')=1;
--Find rows with no content
SELECT * FROM @mockup
WHERE theXML.exist('/root/content')=0;
答案 1 :(得分:0)
xml.exist函数对我来说并不直观,我已经 经常失败。即使文档明确说明了如何使用它,也是如此:https://docs.microsoft.com/en-us/sql/t-sql/xml/exist-method-xml-data-type?view=sql-server-ver15
但是对我来说,事先阅读文档也不是很直观:)
DECLARE @mockup TABLE(Descr VARCHAR(100),theXML XML);
INSERT INTO @mockup VALUES
('<content> exists with value','<root><content>blah</content></root>' )
,('<content> exists without value','<root><content></content></root>' ) --semantically the same as self-closed...
,('<content> exists self-closed','<root><content/></root>' )
,('<content> does not exist','<root></root>' )
,('XML is null', NULL );
SELECT *, theXML.exist('/root/content') FROM @mockup
给予
<content> exists with value <root><content>blah</content></root> 1
<content> exists without value <root><content /></root> 1
<content> exists self-closed <root><content /></root> 1
<content> does not exist <root /> 0
XML is null NULL NULL
所以我总是将条件包装在ISNULL(..,..)
SELECT *, ISNULL(theXML.exist('/root/content'),0) FROM @mockup