ITPub博客

首页 > 数据库 > SQL Server > sql---for xml 三种模式

sql---for xml 三种模式

原创 SQL Server 作者:us_yunleiwang 时间:2010-06-29 17:12:09 0 删除 编辑

         很多人对Xpath可能比较熟悉,但不知道有没有直接操作过数据库,我们都知道 在Sql2005里公支持的几种查询有Raw,Auto模式,页并没有Path和Elements用法等,如果在2000里使用过 Raw模式的朋友应该知道,是不容易处理查询结果的,那么在2005里对这一块做了很好的提升

        我先来介绍一下什么是Sql For Xml吧,我们大多时候都会有这种情况,想把表里的数据转化成Xml格式的,通常我们会使用c#或是Vb程序来转公,使用Xpath或是XmlDocument等对象来完成,当然这样是可以的,不过这样处理起来就会出现很多问题,比如说数据库变化,如果只有数据变化那方便,写一个通用的类,每次查询前更新Xml文件就可以了,但如果出现数据库结构的变化就会很吃力了,那么有没有一种方法,把数据在调出数据库之前就转化为Xml的呢,这个是当然的,就是我们的For Xml,大家在查询分析器里做表结果查询的时候一般是这样写的

  

   我们给大家展示一下我所用到的两个表吧

   第一个表班级信息表ClassInfo(班级信息表一共三个字段CID 本表ID,Cnumber 班级人数,CName 班级名称)

  

 第二个表 生信息表 Students (CID 班级表外键,SID学生信息表ID学生的学号就是,SName)

<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->SELECT CID,Cnumber,CName FROM ClassInfo WHERE CName='博客园一班'

 

 结果为:

通常是这种方法,或是再加上个Order BY 什么的,或是像inner join 等查询的东东,其实我们只要在这条语句上少量的改动一下就可以得到我们想要的Xml数据了,也许 有朋友已经想到了是 For Xml 对就是这样的

SELECT CID,Cnumber,CName FROM ClassInfo WHERE CName='博客园一班'   FOR xml raw
<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->

 这样查询得到的结果如下:

我们如果想看的更清楚的话只要单击一个就可以得到相应的Xml文件的形式了

这里应该就是我们想要的Xml文件的形式了,其实就是这么简单的,我们可以通过Ado的方式 把他查询得到UI直接使用就OK了,

我们可以看到我们得到的信息并不完整,没有学生信息,我们要吧使用一个连接的形式来完成看下面的Sql语句

 

<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->SELECT ClassInfo.CID,ClassInfo.Cnumber,ClassInfo.CName,Students.SID,Students.SName
FROM ClassInfo  JOIN dbo.Students ON Students.CID=dbo.ClassInfo.CID 
ORDER BY CID FOR xml raw 

 

这里我们是查询所有的学生和所在班级的信息

结果为:

raw 的形式是以属性的方法来显示字段的,我们还可以使用Auto,Auto是自动 ,它的意思 不用我多说看例子,(字体检查相关项目)

我们把上面的代码修改一下

<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->
SELECT ClassInfo.CID,ClassInfo.Cnumber,ClassInfo.CName,Students.SID,Students.SName
FROM ClassInfo  JOIN dbo.Students ON Students.CID=dbo.ClassInfo.CID 
ORDER BY CID FOR xml auto 

 

这样就能得到更为合理的数据,返回的结果如下

代码
<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ --><ClassInfo CID="1" Cnumber="100" CName="博客园一班">
  
<dbo.Students SID="1" SName="苏飞" />
  
<dbo.Students SID="2" SName="金色海洋" />
ClassInfo>
<ClassInfo CID="2" Cnumber="10" CName="博客园二班">
  
<dbo.Students SID="3" SName="赵劼" />
  
<dbo.Students SID="4" SName="DUDU" />
ClassInfo>
<ClassInfo CID="3" Cnumber="5" CName="博客园二班">
  
<dbo.Students SID="5" SName="李永京" />
ClassInfo>

 

我们可以看到这里没有根结点,当然我们要吧通过Root属性来完成

修改Sql语句

 

代码
<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ -->SELECT ClassInfo.CID,ClassInfo.Cnumber,ClassInfo.CName,Students.SID,Students.SName
FROM ClassInfo  JOIN dbo.Students ON Students.CID=dbo.ClassInfo.CID 
ORDER BY CID FOR xml auto ,root('studentInfo')

 

返回结果

 

代码
<!-- Code highlighting produced by Actipro CodeHighlighter (freeware) http://www.CodeHighlighter.com/ --><studentInfo>
  
<ClassInfo CID="1" Cnumber="100" CName="博客园一班">
    
<dbo.Students SID="1" SName="苏飞" />
    
<dbo.Students SID="2" SName="金色海洋" />
  
ClassInfo>
  
<ClassInfo CID="2" Cnumber="10" CName="博客园二班">
    
<dbo.Students SID="3" SName="赵劼" />
    
<dbo.Students SID="4" SName="DUDU" />
  
ClassInfo>
  
<ClassInfo CID="3" Cnumber="5" CName="博客园二班">
    
<dbo.Students SID="5" SName="李永京" />
  
ClassInfo>
studentInfo>

 

我们发现和我们平时常的Xml文档的格式还是不一样,我们再加上一个Elements属性试试


代码
<!--Code highlighting produced by Actipro CodeHighlighter (freeware)http://www.CodeHighlighter.com/-->SELECT ClassInfo.CID,ClassInfo.Cnumber,ClassInfo.CName,Students.SID,Students.SName
FROM ClassInfo  JOIN dbo.Students ON Students.CID=dbo.ClassInfo.CID 
ORDER BY CID FOR xml auto ,root('studentInfo'),Elements
 

  返回的结果如下

 

代码
<!--Code highlighting produced by Actipro CodeHighlighter (freeware)http://www.CodeHighlighter.com/--><studentInfo>
  
<ClassInfo>
    
<CID>1CID>
    
<Cnumber>100Cnumber>
    
<CName>博客园一班CName>
    
<dbo.Students>
      
<SID>1SID>
      
<SName>苏飞SName>
    
dbo.Students>
    
<dbo.Students>
      
<SID>2SID>
      
<SName>金色海洋SName>
    
dbo.Students>
  
ClassInfo>
  
<ClassInfo>
    
<CID>2CID>
    
<Cnumber>10Cnumber>
    
<CName>博客园二班CName>
    
<dbo.Students>
      
<SID>3SID>
      
<SName>赵劼SName>
    
dbo.Students>
    
<dbo.Students>
      
<SID>4SID>
      
<SName>DUDUSName>
    
dbo.Students>
  
ClassInfo>
  
<ClassInfo>
    
<CID>3CID>
    
<Cnumber>5Cnumber>
    
<CName>博客园二班CName>
    
<dbo.Students>
      
<SID>5SID>
      
<SName>李永京SName>
    
dbo.Students>
  
ClassInfo>
studentInfo>

 

 基本是我们想要的数据了吧,我们还可以使用这样两个语句来完成,我们前面提到过Path 和Raw,其它在这里只要换成其中的一个就行结果是一样的
我们可看一下修改后的代码

代码
<!--Code highlighting produced by Actipro CodeHighlighter (freeware)http://www.CodeHighlighter.com/-->SELECT ClassInfo.CID,ClassInfo.Cnumber,ClassInfo.CName,Students.SID,Students.SName
FROM ClassInfo  JOIN dbo.Students ON Students.CID=dbo.ClassInfo.CID 
ORDER BY CID FOR xml raw ,root('studentInfo'),Elements

 

看结果吧

 

代码
<!--Code highlighting produced by Actipro CodeHighlighter (freeware)http://www.CodeHighlighter.com/--><studentInfo>
  
<row>
    
<CID>1CID>
    
<Cnumber>100Cnumber>
    
<CName>博客园一班CName>
    
<SID>1SID>
    
<SName>苏飞SName>
  
row>
  
<row>
    
<CID>1CID>
    
<Cnumber>100Cnumber>
    
<CName>博客园一班CName>
    
<SID>2SID>
    
<SName>金色海洋SName>
  
row>
  
<row>
    
<CID>2CID>
    
<Cnumber>10Cnumber>
    
<CName>博客园二班CName>
    
<SID>3SID>
    
<SName>赵劼SName>
  
row>
  
<row>
    
<CID>2CID>
    
<Cnumber>10Cnumber>
    
<CName>博客园二班CName>
    
<SID>4SID>
    
<SName>DUDUSName>
  
row>
  
<row>
    
<CID>3CID>
    
<Cnumber>5Cnumber>
    
<CName>博客园二班CName>
    
<SID>5SID>
    
<SName>李永京SName>
  
row>
studentInfo>


我相信这样的数据我们查询和处理起来就方便多了,
如果大家想要这样的数据其实要吧直接使用Path模式,这样会更方法
看代码

代码
<!--Code highlighting produced by Actipro CodeHighlighter (freeware)http://www.CodeHighlighter.com/-->SELECT ClassInfo.CID,ClassInfo.Cnumber,ClassInfo.CName,Students.SID,Students.SName
FROM ClassInfo  JOIN dbo.Students ON Students.CID=dbo.ClassInfo.CID 
ORDER BY CID FOR xml path ,root('studentInfo')

---测试案例

求一sql语句!~请高手进!~

表:AA
id  name   pwd
1    aa     A
2    aa     B
3    aa     C
4    bb     F
5     bb    K

想要的结果:
name pwd
aaa A,B,C
bbb F,K


表脚本:
create table aa(
id int,
name varchar(10) not null,
pwd varchar(10)
)

insert into aa values(1,'aaa','A');
insert into aa values(2,'aaa','B');
insert into aa values(3,'aaa','C');
insert into aa values(4,'bbb','F');
insert into aa values(5,'bbb','K');


------------------

SQL:CODE<


WITH  data
AS
(
SELECT DISTINCT name FROM aa
)
        
SELECT  name,
                col2= STUFF(REPLACE(REPLACE(CAST((SELECT pwd
                                                FROM aa
                                                WHERE name=a.name
                                                FOR XML PATH(''),TYPE ) AS nvarchar(max))
                                        ,'',',')
                         ,'
',''),1,1,'')
FROM data a


select distinct rtrim(substring(replace(replace

            (cast((SELECT n.pwd   FROM aa n where n.name=a.name

                  for xml path(''),type) as varchar(max)),

            '',','),'',''),2,100)) from aa a

      结果和上面的是完全一样的,也就是说这里不用再加上Elements属性也是一样的,也是我们最常用的一种方式
结果就不再贴了,相信简单的知道 这些以后已经能帮助不少对这块不怎么理解的朋友解决一部分问题了,因为基本的查询也就是这么多,我们在使用的时候只要返回结果集的第一行第一列就行了,然后怎么处理就是c#代码怎么处理Xml文档的问题了,

总结一下这几个东东吧,

    Path 是以数据基本结构也就是以字段为结点的形式返回Xml文档(这样说不专业可能容易理解)

    Raw 是把数据里所有的字段以属性的方式显示出Xml文档

    Auto  自动关连到相应的项目,和Raw一样在不加Elements属性时以这种方式返回数据

 

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/23490154/viewspace-666611/ ,如需转载,请注明出处,否则将追究法律责任。

下一篇: 指环王-onlie
请登录后发表评论 登录
全部评论

注册时间:2010-03-15

  • 博文量
    198
  • 访问量
    1393178