??xml version="1.0" encoding="utf-8" standalone="yes"?>亚洲av色香蕉一区二区三区蜜桃,国产综合精品久久亚洲,亚洲av无码专区在线电影天堂http://m.tkk7.com/jackybu/articles/6160.html?/dc:creator>?/author>Wed, 15 Jun 2005 06:07:00 GMThttp://m.tkk7.com/jackybu/articles/6160.htmlhttp://m.tkk7.com/jackybu/comments/6160.htmlhttp://m.tkk7.com/jackybu/articles/6160.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/6160.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/6160.htmlString url =  "jdbc:odbc:driver={Microsoft Access Driver (*.mdb)};DBQ=E:\\MS\\DB.mdb";

]]>
mysql导入导出数据?/title><link>http://m.tkk7.com/jackybu/articles/5808.html</link><dc:creator>?/dc:creator><author>?/author><pubDate>Thu, 09 Jun 2005 04:41:00 GMT</pubDate><guid>http://m.tkk7.com/jackybu/articles/5808.html</guid><wfw:comment>http://m.tkk7.com/jackybu/comments/5808.html</wfw:comment><comments>http://m.tkk7.com/jackybu/articles/5808.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://m.tkk7.com/jackybu/comments/commentRss/5808.html</wfw:commentRss><trackback:ping>http://m.tkk7.com/jackybu/services/trackbacks/5808.html</trackback:ping><description><![CDATA[用mysqldump <BR>把一个库导出C个SQL文g <BR>mysqldump db_name > /path/name.sql -uroot -p <BR>如果数据库太大,压羃导出 <BR>mysqldump db_name | gzip > /path/name.sql -u root -p <BR> <P>备䆾全部的库 <BR>mysqldump --all-databases > /path/name.sql -u root -p <BR>mysqldump --all-databases | gzip > /path/name.gz -uroot -p <BR>备䆾一个单独或者几个表 <BR>mysqldump db_name tab_name > /path/sqlname.sql -u root -p <BR>恢复数据 导入数据 <BR>mysql db_name < backup-file.sql -u root -p <BR>有一U用mysql db_name < backup-file.sql -u root -p <BR>W二U方法:(x) <BR>mysql -u root -p <BR>use db_name <BR>. /path/dbname.sql <BR>q种Ҏ(gu)保险点,因ؓ(f)有时我用 db_name < dbname.sql有问?<BR>用第二种Ҏ(gu)可以?<BR>………………………………………………………?<BR>dmysql用户mysqlname 密码为password Q赋予dbname数据库所有权?<BR>mysql> grant all on dbname.* to mysqlname@localhost identified by 'password'; <BR>mysql > grant select,insert,update,delete,create,drop on 数据库名.* to 用户(新徏)@localhost identified by '密码'; <BR>或者直接修改mysql?<BR>mysql > insert into user(host,user,password) values('%','user_name',password("you password")); <BR>mysql > set password for user_name=password("you_password") <BR>以上两种必须q行重蝲授权?./scripts/mysql_install_db) <BR>或者在shell环境?<BR>mysqladmin -u root password "you password" </P><img src ="http://m.tkk7.com/jackybu/aggbug/5808.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://m.tkk7.com/jackybu/" target="_blank">?/a> 2005-06-09 12:41 <a href="http://m.tkk7.com/jackybu/articles/5808.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>取一表前N{記錄的各种數据庫的寫法http://m.tkk7.com/jackybu/articles/5412.html?/dc:creator>?/author>Wed, 01 Jun 2005 06:39:00 GMThttp://m.tkk7.com/jackybu/articles/5412.htmlhttp://m.tkk7.com/jackybu/comments/5412.htmlhttp://m.tkk7.com/jackybu/articles/5412.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/5412.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/5412.html介紹取一表前N{記錄的各种數据庫的寫法...
1. ORACLE
SELECT * FROM TABLE1 WHERE ROWNUM<=N
2. INFORMIX
SELECT FIRST N * FROM TABLE1
3. DB2
SELECT * ROW_NUMBER() OVER(ORDER BY COL1 DESC) AS ROWNUM WHERE ROWNUM<=N
DB2
SELECT COLUMN FROM TABLE FETCH FIRST N ROWS ONLY
4. SQL SERVER
SELECT TOP N * FROM TABLE1
5. SYBASE
SELECT TOP N * FROM TABLE1

]]>
【讨论】JDBC中,如果ResultSet ?Statement 不关闭的话,?x)有什么媄?http://m.tkk7.com/jackybu/articles/1756.html?/dc:creator>?/author>Sat, 05 Mar 2005 15:10:00 GMThttp://m.tkk7.com/jackybu/articles/1756.htmlhttp://m.tkk7.com/jackybu/comments/1756.htmlhttp://m.tkk7.com/jackybu/articles/1756.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1756.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1756.html感觉上好象是只要把connectionl关闭了Q系l就能正常运行了?
那在查询或是其实操作中,如果只关闭ConnectionQ不作ResultSet ?Statement 的关闭的话,对系l性能是否?x)有影响呢。或者是其实斚w的不良媄响?BR>
如果你不使用q接池,那么没有什么问题,一旦Connection关闭Q数据库物理q接p释放Q所有相关Java资源也可以被GC回收了?
但是如果你用连接池Q那么请注意QConnection关闭q不是物理关闭,只是归还q接池,所以PreparedStatement和ResultSet都被持有Qƈ且实际占用相关的数据库的游标资源Q在q种情况下,只要长期q行Q往往׃(x)报“游标超出数据库允许的最大值”的错误Q导致程序无法正常访问数据库?BR>
补充Q其实这个要看你用的是什么数据库Q然后决定了你的JDBCQ然后呢Q决定了实现q个JDBC的方法,然后呢就军_了问题?
关闭?BR>
不用连接池的情况下,如果你直接关闭连接话,对应的Statement,ResultSet对象都应该由Driver Vendor来帮你关?即由他来q行资源的释?q个是由JDBC3.0规范中提到的.因ؓ(f)有些数据库资源可能属于GC不能释放的范?
对于q接池的实现而言,有时间我看看Oracle和Postgres的实现再下定论吧.但是我认为出C面的情况应该理解成ؓ(f)q接池vendor的一U没有按规范来实现的问题.如果用数据库自己实现的连接池应该不会(x)有这L(fng)情况出现.

使用q接池时也应该会(x)关闭PreparedStatement和ResultSetQ看qApache的DBCPQ它是会(x)关的Q不知道其他q接池是怎么L(fng)。实际上Q用不使用q接池应该对开发者透明Q都应该遵@Jdbc规范Q从q个角度Q连接池如果没有实现关闭功能应该是有问题的?/SPAN>


]]>
数据库设计过E中一些命名规?http://m.tkk7.com/jackybu/articles/1579.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:43:00 GMThttp://m.tkk7.com/jackybu/articles/1579.htmlhttp://m.tkk7.com/jackybu/comments/1579.htmlhttp://m.tkk7.com/jackybu/articles/1579.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1579.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1579.html数据库设计过E中命名规范很是重要Q命名规范合理的设计能够省去开发h员很多时间去区别数据库实体?BR>
数据库物理设计包括:(x)表设计,视图设计Q存储过E设计,用户自定义函数设计等{?/SPAN>

1?SPAN style="FONT: 7pt 'Times New Roman'">  表设计命名规范:(x)表?/SPAN>t开头最好能表Ҏ(gu)属性分cdƈ作好~号?/SPAN>

如:(x)~码表可写ؓ(f)tBM001Something  t开_(d)BMZ务类型,001cd中的W几个表something是表的名U注释?/SPAN>

2?SPAN style="FONT: 7pt 'Times New Roman'"> 视图设计命名规范Q视图设计过E中使用v开_(d)视图命名以制作视囄主表为准或是以视囄实现功能为准?/SPAN>

如:(x)上述tBM001Something Z表制作的视图 可取?/SPAN>vBM001Something

或?/SPAN>vGetSomeThingInfo{?/SPAN>

3?/SPAN>存储q程命名规范Q用戯定义存储q程使用p开头以其实现功能命?/SPAN>,

如:(x)pGetSomethingInfo

4?SPAN style="FONT: 7pt 'Times New Roman'"> 

存储q程命名规范Q用戯定义存储q程使用f开头以其实现功能命?/SPAN>,

如:(x)fGetSomethingInfo

              此外在制作视囑֭储过E用戯定义函数q程中,注意写好注释?/SPAN>

 

  注释内容包括Q名Uͼ作用Q调用,使用表,更新记录Q设计思\Q入口参?/SPAN>

/*========================================================

 存储q程名称Q?/SPAN>pro_tXT005TraceLeaderSearch

?/SPAN>                用:(x)生成日志中资源更新情늻计分?/SPAN>

 调用存储q程Q?/SPAN>pro_tXT005TraceLeaderSearch

使用表:(x)       t BM001Something。。。。。?/SPAN>

 更新记录Q?/SPAN>1?/SPAN>  cc  2004-7-15  构徏存储q程

           2?/SPAN>   cc  2005-2-6    修改存储q程Q处?/SPAN>bug   增加新的内容

设计思\Q算法描q?/SPAN>

 ?/SPAN>   ?/SPAN>   ?/SPAN>  敎ͼ(x) @startDate 开始日期,@endDate l束旉                          

--=========================================================*/



]]>
SQL Server 2000 XML之七U兵?http://m.tkk7.com/jackybu/articles/1576.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:34:00 GMThttp://m.tkk7.com/jackybu/articles/1576.htmlhttp://m.tkk7.com/jackybu/comments/1576.htmlhttp://m.tkk7.com/jackybu/articles/1576.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1576.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1576.html  兵器之一QFOR XML

  在SQL Server 2000中,标准的T-SQL SELECT语句包括F(xin)OR XML子句Q它以XML文形式q回一个查询结果。新的FOR XML子句有三U模式——RAWQAUTOQ和EXPLICITQ每个都能对XML文格式提供附加标准的控制?/P>

  下面首先介绍“FOR XML”的使用Ҏ(gu)?/P>

  Z从SQL Server提取XML格式的数据,T-SQL中加入了一个FOR XML命o(h)。在查询命o(h)中用FOR XML命o(h)使得查询l果以XML格式出现。FOR XML命o(h)有三U模式:(x)RAWQAUTO和EXPLICIT。图1所昄的SQL命o(h)讉KSQL Server提供的PubsCZ数据库。有关Pubs数据库的更多信息Q请参见MSDN说明。如果我们依ơ指定该SQL命o(h)的模式ؓ(f)三种允许的模式之一Q就可以得到各种模式所支持的不同XML输出?

【图1 ?/P>

SELECT store.stor_id as Id, stor_name as Name,

sale.ord_num as OrderNo,sale.qty as Qty

FROM stores store inner join

sales sale on store.stor_id = sale.stor_id

ORDER BY stor_name

FOR XML Q模式>

  该查询命令所生成的结果包含所有销售记录及其对应的商店Q结果以商店名称的字母升序排列。查询的最后加上了FOR XML命o(h)以及具体的模式,比如FOR XML RAW?

  理想情况下,SQL命o(h)所生成的XML文应具有如下结构:(x)

QStoresQ?/P>

QStore Id=&single;&single; Name=&single;&single;Q?/P>

Q?Sale OrderNo=&single;&single; Qty=&single;&single;Q?/P>

Q?StoreQ?/P>

Q?StoresQ?/P>

  下面我们来看看具体的处理Ҏ(gu)?

  RAW模式

  下面是指定RAW模式时结果XML文档的一个片断?/P>

  查询l果集中每一个记录包含唯一的元素<rowQ。由于我们无法控制元素名字和文l构Q因此这U模式不是很有用。RAW模式所生成的文结构与我们所希望的不W,而且它的用途也非常有限?

  AUTO模式

  下面是指定AUTO模式时结果文的一个片断:(x)

  可以看到Q<StroeQ和QSaleQ两个元素是?子关p,形成了我们所希望的层ơ结构。这U节点关pȝ查询中表的声明次序决定,后声明的表成为前声明表的孩子?

  再参考图1Q我们可以看出查询命令所指定的别名决定了XML文中的名字。根据这一点,我们可以控制XML文档元素、属性的名字Q得这些名字符合我们所要求的命名惯例?

  可见AUTO模式能够创徏出我们所需要的XML文。不q它存在以下~点Q?

  虽然可以得到层次l构Q但q种层次l构是线性的Q即每个父节点只能有一个子节点Q反之亦然?

  通过别名指定元素名字不太方便Q而且有时候会(x)影响查询命o(h)本n的可L?

  无法在文中同时生成元素和属性。要么全部是元素Q通过ELEMENTS关键词指定)Q要么全部是属性(默认Q?EXPLICIT模式解决了上qC?


 EXPLICIT模式

  EXPLICIT模式比较复杂Q我们将用另外一U方法来表达?所昄的查询。这U方法得我们能够完全地控制查询所生成的XML文。首先我们将介绍如何改用EXPLICIT模式~写?所昄的查询,然后看看q种Ҏ(gu)如何赋予我们q远过AUTO模式的能力?

  下面是图1查询用EXPLICIT模式表达的代码:(x)

【图2 ?/P>

--商店数据
SELECT 1 as Tag,
NULL as Parent,
s.stor_id as [store!1!Id],
s.stor_name as [store!1!Name],
NULL as[sale!2!OrderNo],
NULL as [sale!2!Qty]
FROM stores s
UNION ALL
-- 销售数?BR>SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
ORDER BY [store!1!name]
FOR XML EXPLICIT

  q个查询初看h有点复杂Q其实它只是把不同的数据集(卌里的Store和SaleQ分解到了独立的SELECT语句里,然后再用UNION ALL操作W连l成一个查询?

  我们之所以要把查询写成上面的形式Q是Z让查询结果不仅包含XML文所描述的数据,而且q包含描qXML文档l构的元数据。上q查询所生成的表UCؓ(f)Universal表,sqlxml.dll生成XML文旉要这U格式。Universal表对于编写代码的人来说是透明的,但了解这个表q是很有意义的,它将有助于代码的开发和调试。下面是Universal表的一个例子:(x)

Tag Parent store!1!id store!1!name sale!2!orderno sale!2!qty
1 NULL 7066 Barnum&single;s NULL NULL
2 1 7066 Barnum&single;s A297650 50
2 1 7066 Barnum&single;s QA7442 375
1 NULL 8042 Bookbeat NULL NULL
2 1 8042 Bookbeat 423LL9 2215

  Universal表和EXPLICIT模式查询的元数据部分都以U色表示Q黑色表C数据。比较查询和表就可以扑ևsqlxml.dll生成XML文所需要的元素。我们来仔细地分析一下它们描q的是什么?

  Tag和Parent列是XML文层次l构斚w的信息,我们可以认ؓ(f)?中的每个SELECT语句代表了一个XML节点Q而Tag和Parent列让我们指定节点在文档层ơ结构中的位|。如果在W二个SELECT语句中指定Tag?、指定Parent?Q就表示些数据加上了一个gؓ(f)2的标{,而这些数据的父亲是那些标{ؓ(f)1的数据(即第一个SELECT语句Q。这׃得我们能够构造出QStoreQ和QSaleQ之间的?子关p,而且正如你可能猜惛_的,它得我们可以生成Q意合法的XML文l构。注意第一个SELECT命o(h)的parent列设|成了NULLQ这表示QStoreQ元素处于最层的位|?

  以黑色表C的数据成点的属性或元素Q例如,Store_ID通过列名提供了这斚w的信息。列名字中的?”是分隔W,d可分成四(四个参数Q,其中W四个参数是可选的。这些参数描q的是:(x)

  W一个参数描q该列所属元素的名字Q在q里是<StoreQ元素?

  W二个是标签~号Q它指定了该列信息在XML?wi)Şl构中所处位|?

  W三个参数指定XML文内的属性或元素名字。在q里名字指定为id?

  数据列默认被创徏为参?所指定节点的属性,即id成为<StoreQ节点的属性。如果要指定id是<StoreQ的一个子元素Q我们可以用第四个可选的参数Q这个参数的一个作用就是让我们把该Ҏ(gu)定ؓ(f)元素Q例如store!1!id!element?

  ׃使用了UNION ALL操作W来q结SELECT语句Qؓ(f)了保证SQL查询的合法性,所有SELECT语句的选择l果必须h相同数量的列。我们用NULL关键词来补SELECT语句Q从而避免了重复数据?

  通过EXPLICIT模式查询所生成的XML文档和通过AUTO模式生成的完全相同,那么Z么要创徏EXPLICIT模式查询呢?

  假设现在有h要求在XML文中包含商店的打折信息。查看Pubs数据库,我们得知每个商店都可以有0到n范围内的折扣率。因此,一U合理的Ҏ(gu)是在QStoreQ元素下面加上子元素QDiscountQ,q样我们得到如下XML文l构Q?

QSTORESQ?BR>QSTORE Id=&single;&single; Name=&single;&single;Q?BR>QDISCOUNT Type=&single;&single; LowQty=&single;&single; HighQty=&single;&single;Q?BR>QAMOUNTQ</AMOUNTQ?BR>Q?DISCOUNTQ?BR>QSALE OrdNo=&single;&single; Qty=&single;&single;Q?BR>Q?SALEQ?BR>Q?STOREQ?BR>Q?STORESQ?

  q里的改动包括:(x)

  要在QSaleQ元素所在的层次增加一个XML元素QDiscountQ,卻IDiscountQ是QStroeQ的子元素?

  Amount嵌套在<DiscountQ里面,但不应该是<DiscountQ元素的属性?

  在AUTO模式中是不可能实现这些改动的?

  下面是创个新XML文档的EXPLICIT模式查询Q?

【图 2A?/P>

SELECT 1 as Tag, NULL as Parent,
s.stor_id as [Store!1!id],
s.stor_name as [Store!1!name],
NULL as [Sale!2!orderno],
NULL as [Sale!2!1ty],
NULL as [Discount!3!type],
NULL as [Discount!3!lowqty],
NULL as [Discount!3!highqty],
NULL as [Discount!3!amount!element]
FROM stores s
UNION ALL
SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty,
NULL,
NULL,
NULL,
NULL
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
UNION ALL
SELECT 3, 1,
NULL,
s.stor_name,
NULL,
NULL,
d.discounttype,
d.lowqty,
d.highqty,
d.discount
FROM stores s, discounts d
WHERE s.stor_id = d.stor_id
ORDER BY [store!1!name]
For XML EXPLICIT

  Z创徏?A所昄的EXPLICIT模式查询Q我们对?的查询进行了如下修改Q?

  增加了第三个子查询提取折扣数据,通过Tag列声明这些数据的标签gؓ(f)3?

  通过指定Parent列ؓ(f)1折扣数据设|成QStoreQ元素的子元素?

  注意在第三个SELECT子查询中我们只包含了那些必需的列Qƈ用NULL补I列。这个子查询包含store_name列,虽然Discount元素q不要用到这个列Q但如果把这个列也设|ؓ(f)NULLQ则l果Universal表将不会(x)按照解析器所要求的那样以节点升序排序Q不妨自p一下看看)。Universal表的排序列也可以用Tag列替代?

  为维持结果Universal表的完整性,W一、二两个SELECT语句也用NULL补以反映ؓ(f)折扣数据增加的列?

  为指定新折扣列的元数据修改了W一个SELECT语句?

  通过在第四个参数中声明element指定Amount列ؓ(f)Discount的一个元素(element是可在第四个参数中声明的多个指o(h)之一Q?

  下面q个XML文只能用EXPLICIT模式生成Q?

  l果XML文中不?x)显C出NULL数据Q如折扣lowqty和highqty?/P>

  看来上面的介l,大家可能已经对FOR XML的语法有所了解。通过FOR XML 我们在能够在Query Analyzer 中直接返回一个XML格式的数据或者通过其他多样化表现方式将XML格式的数据显C出来,比如可以数据显C在览器上。下面这个例子就使用FOR XML和ADO数据输出到览器的例子?/P>

Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")

Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=192.168.0.160;Initial Catalog=Northwind;User ID=SA;Password=;"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open

Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn

Dim sQuery
‘定?FOR XML的查询。具体的语法在以后的章节中将详细介绍?BR>sQuery = "QROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'Q<sql:queryQSELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTOQ?sql:queryQ</ROOTQ?

‘徏立ADODB Stream 对象QADODB Stream 对象需要ADO2.5以上版本支持Q它可以记录集转换为数据流?BR>Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"

Response.write "Pushing XML to client for processing " & "QBR/Q?

adoCmd.Properties("Output Stream") = Response
‘输出XML格式的文?BR>Response.write "QXML ID=MyDataIsleQ?
adoCmd.Execute , , adExecuteStream
Response.write "Q?XMLQ?

‘通过IE的XML解析器,使用DOMҎ(gu)XML的文本{换ؓ(f)HTML
QSCRIPT language="VBScript" For="window" Event="onload"Q?/P>

Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false

Dim root, child
Set root = xmlDoc.documentElement

For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "QLIQ? & child.getAttribute("ProductName") & "Q?LIQ?
Next

Q?SCRIPTQ?

 EXPLICIT模式

  EXPLICIT模式比较复杂Q我们将用另外一U方法来表达?所昄的查询。这U方法得我们能够完全地控制查询所生成的XML文。首先我们将介绍如何改用EXPLICIT模式~写?所昄的查询,然后看看q种Ҏ(gu)如何赋予我们q远过AUTO模式的能力?

  下面是图1查询用EXPLICIT模式表达的代码:(x)

【图2 ?/P>
--商店数据
SELECT 1 as Tag,
NULL as Parent,
s.stor_id as [store!1!Id],
s.stor_name as [store!1!Name],
NULL as[sale!2!OrderNo],
NULL as [sale!2!Qty]
FROM stores s
UNION ALL
-- 销售数?BR>SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
ORDER BY [store!1!name]
FOR XML EXPLICIT

  q个查询初看h有点复杂Q其实它只是把不同的数据集(卌里的Store和SaleQ分解到了独立的SELECT语句里,然后再用UNION ALL操作W连l成一个查询?

  我们之所以要把查询写成上面的形式Q是Z让查询结果不仅包含XML文所描述的数据,而且q包含描qXML文档l构的元数据。上q查询所生成的表UCؓ(f)Universal表,sqlxml.dll生成XML文旉要这U格式。Universal表对于编写代码的人来说是透明的,但了解这个表q是很有意义的,它将有助于代码的开发和调试。下面是Universal表的一个例子:(x)

Tag Parent store!1!id store!1!name sale!2!orderno sale!2!qty
1 NULL 7066 Barnum&single;s NULL NULL
2 1 7066 Barnum&single;s A297650 50
2 1 7066 Barnum&single;s QA7442 375
1 NULL 8042 Bookbeat NULL NULL
2 1 8042 Bookbeat 423LL9 2215

  Universal表和EXPLICIT模式查询的元数据部分都以U色表示Q黑色表C数据。比较查询和表就可以扑ևsqlxml.dll生成XML文所需要的元素。我们来仔细地分析一下它们描q的是什么?

  Tag和Parent列是XML文层次l构斚w的信息,我们可以认ؓ(f)?中的每个SELECT语句代表了一个XML节点Q而Tag和Parent列让我们指定节点在文层ơ结构中的位|。如果在W二个SELECT语句中指定Tag?、指定Parent?Q就表示些数据加上了一个gؓ(f)2的标{,而这些数据的父亲是那些标{ؓ(f)1的数据(即第一个SELECT语句Q。这׃得我们能够构造出QStoreQ和QSaleQ之间的?子关p,而且正如你可能猜惛_的,它得我们可以生成Q意合法的XML文l构。注意第一个SELECT命o(h)的parent列设|成了NULLQ这表示QStoreQ元素处于最层的位|?

  以黑色表C的数据成点的属性或元素Q例如,Store_ID通过列名提供了这斚w的信息。列名字中的?”是分隔W,d可分成四(四个参数Q,其中W四个参数是可选的。这些参数描q的是:(x)

  W一个参数描q该列所属元素的名字Q在q里是<StoreQ元素?

  W二个是标签~号Q它指定了该列信息在XML?wi)Şl构中所处位|?

  W三个参数指定XML文内的属性或元素名字。在q里名字指定为id?

  数据列默认被创徏为参?所指定节点的属性,即id成为<StoreQ节点的属性。如果要指定id是<StoreQ的一个子元素Q我们可以用第四个可选的参数Q这个参数的一个作用就是让我们把该Ҏ(gu)定ؓ(f)元素Q例如store!1!id!element?

  ׃使用了UNION ALL操作W来q结SELECT语句Qؓ(f)了保证SQL查询的合法性,所有SELECT语句的选择l果必须h相同数量的列。我们用NULL关键词来补SELECT语句Q从而避免了重复数据?

  通过EXPLICIT模式查询所生成的XML文档和通过AUTO模式生成的完全相同,那么Z么要创徏EXPLICIT模式查询呢?

  假设现在有h要求在XML文档中包含商店的打折信息。查看Pubs数据库,我们得知每个商店都可以有0到n范围内的折扣率。因此,一U合理的Ҏ(gu)是在QStoreQ元素下面加上子元素QDiscountQ,q样我们得到如下XML文l构Q?

QSTORESQ?BR>QSTORE Id=&single;&single; Name=&single;&single;Q?BR>QDISCOUNT Type=&single;&single; LowQty=&single;&single; HighQty=&single;&single;Q?BR>QAMOUNTQ</AMOUNTQ?BR>Q?DISCOUNTQ?BR>QSALE OrdNo=&single;&single; Qty=&single;&single;Q?BR>Q?SALEQ?BR>Q?STOREQ?BR>Q?STORESQ?

  q里的改动包括:(x)

  要在QSaleQ元素所在的层次增加一个XML元素QDiscountQ,卻IDiscountQ是QStroeQ的子元素?

  Amount嵌套在<DiscountQ里面,但不应该是<DiscountQ元素的属性?

  在AUTO模式中是不可能实现这些改动的?

  下面是创个新XML文的EXPLICIT模式查询Q?

【图 2A?/P>
SELECT 1 as Tag, NULL as Parent,
s.stor_id as [Store!1!id],
s.stor_name as [Store!1!name],
NULL as [Sale!2!orderno],
NULL as [Sale!2!1ty],
NULL as [Discount!3!type],
NULL as [Discount!3!lowqty],
NULL as [Discount!3!highqty],
NULL as [Discount!3!amount!element]
FROM stores s
UNION ALL
SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty,
NULL,
NULL,
NULL,
NULL
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
UNION ALL
SELECT 3, 1,
NULL,
s.stor_name,
NULL,
NULL,
d.discounttype,
d.lowqty,
d.highqty,
d.discount
FROM stores s, discounts d
WHERE s.stor_id = d.stor_id
ORDER BY [store!1!name]
For XML EXPLICIT

  Z创徏?A所昄的EXPLICIT模式查询Q我们对?的查询进行了如下修改Q?

  增加了第三个子查询提取折扣数据,通过Tag列声明这些数据的标签gؓ(f)3?

  通过指定Parent列ؓ(f)1折扣数据设|成QStoreQ元素的子元素?

  注意在第三个SELECT子查询中我们只包含了那些必需的列Qƈ用NULL补I列。这个子查询包含store_name列,虽然Discount元素q不要用到这个列Q但如果把这个列也设|ؓ(f)NULLQ则l果Universal表将不会(x)按照解析器所要求的那样以节点升序排序Q不妨自p一下看看)。Universal表的排序列也可以用Tag列替代?

  为维持结果Universal表的完整性,W一、二两个SELECT语句也用NULL补以反映ؓ(f)折扣数据增加的列?

  为指定新折扣列的元数据修改了W一个SELECT语句?

  通过在第四个参数中声明element指定Amount列ؓ(f)Discount的一个元素(element是可在第四个参数中声明的多个指o(h)之一Q?

  下面q个XML文只能用EXPLICIT模式生成Q?

  l果XML文档中不?x)显C出NULL数据Q如折扣lowqty和highqty?/P>

  看来上面的介l,大家可能已经对FOR XML的语法有所了解。通过FOR XML 我们在能够在Query Analyzer 中直接返回一个XML格式的数据或者通过其他多样化表现方式将XML格式的数据显C出来,比如可以数据显C在览器上。下面这个例子就使用FOR XML和ADO数据输出到览器的例子?/P>

Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")

Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=192.168.0.160;Initial Catalog=Northwind;User ID=SA;Password=;"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open

Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn

Dim sQuery
‘定?FOR XML的查询。具体的语法在以后的章节中将详细介绍?BR>sQuery = "QROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'Q<sql:queryQSELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTOQ?sql:queryQ</ROOTQ?

‘徏立ADODB Stream 对象QADODB Stream 对象需要ADO2.5以上版本支持Q它可以记录集转换为数据流?BR>Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"

Response.write "Pushing XML to client for processing " & "QBR/Q?

adoCmd.Properties("Output Stream") = Response
‘输出XML格式的文?BR>Response.write "QXML ID=MyDataIsleQ?
adoCmd.Execute , , adExecuteStream
Response.write "Q?XMLQ?

‘通过IE的XML解析器,使用DOMҎ(gu)XML的文本{换ؓ(f)HTML
QSCRIPT language="VBScript" For="window" Event="onload"Q?/P>

Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false

Dim root, child
Set root = xmlDoc.documentElement

For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "QLIQ? & child.getAttribute("ProductName") & "Q?LIQ?
Next

Q?SCRIPTQ?

 EXPLICIT模式

  EXPLICIT模式比较复杂Q我们将用另外一U方法来表达?所昄的查询。这U方法得我们能够完全地控制查询所生成的XML文档。首先我们将介绍如何改用EXPLICIT模式~写?所昄的查询,然后看看q种Ҏ(gu)如何赋予我们q远过AUTO模式的能力?

  下面是图1查询用EXPLICIT模式表达的代码:(x)

【图2 ?/P>
--商店数据
SELECT 1 as Tag,
NULL as Parent,
s.stor_id as [store!1!Id],
s.stor_name as [store!1!Name],
NULL as[sale!2!OrderNo],
NULL as [sale!2!Qty]
FROM stores s
UNION ALL
-- 销售数?BR>SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
ORDER BY [store!1!name]
FOR XML EXPLICIT

  q个查询初看h有点复杂Q其实它只是把不同的数据集(卌里的Store和SaleQ分解到了独立的SELECT语句里,然后再用UNION ALL操作W连l成一个查询?

  我们之所以要把查询写成上面的形式Q是Z让查询结果不仅包含XML文所描述的数据,而且q包含描qXML文l构的元数据。上q查询所生成的表UCؓ(f)Universal表,sqlxml.dll生成XML文旉要这U格式。Universal表对于编写代码的人来说是透明的,但了解这个表q是很有意义的,它将有助于代码的开发和调试。下面是Universal表的一个例子:(x)

Tag Parent store!1!id store!1!name sale!2!orderno sale!2!qty
1 NULL 7066 Barnum&single;s NULL NULL
2 1 7066 Barnum&single;s A297650 50
2 1 7066 Barnum&single;s QA7442 375
1 NULL 8042 Bookbeat NULL NULL
2 1 8042 Bookbeat 423LL9 2215

  Universal表和EXPLICIT模式查询的元数据部分都以U色表示Q黑色表C数据。比较查询和表就可以扑ևsqlxml.dll生成XML文所需要的元素。我们来仔细地分析一下它们描q的是什么?

  Tag和Parent列是XML文层次l构斚w的信息,我们可以认ؓ(f)?中的每个SELECT语句代表了一个XML节点Q而Tag和Parent列让我们指定节点在文层ơ结构中的位|。如果在W二个SELECT语句中指定Tag?、指定Parent?Q就表示些数据加上了一个gؓ(f)2的标{,而这些数据的父亲是那些标{ؓ(f)1的数据(即第一个SELECT语句Q。这׃得我们能够构造出QStoreQ和QSaleQ之间的?子关p,而且正如你可能猜惛_的,它得我们可以生成Q意合法的XML文l构。注意第一个SELECT命o(h)的parent列设|成了NULLQ这表示QStoreQ元素处于最层的位|?

  以黑色表C的数据成点的属性或元素Q例如,Store_ID通过列名提供了这斚w的信息。列名字中的?”是分隔W,d可分成四(四个参数Q,其中W四个参数是可选的。这些参数描q的是:(x)

  W一个参数描q该列所属元素的名字Q在q里是<StoreQ元素?

  W二个是标签~号Q它指定了该列信息在XML?wi)Şl构中所处位|?

  W三个参数指定XML文档内的属性或元素名字。在q里名字指定为id?

  数据列默认被创徏为参?所指定节点的属性,即id成为<StoreQ节点的属性。如果要指定id是<StoreQ的一个子元素Q我们可以用第四个可选的参数Q这个参数的一个作用就是让我们把该Ҏ(gu)定ؓ(f)元素Q例如store!1!id!element?

  ׃使用了UNION ALL操作W来q结SELECT语句Qؓ(f)了保证SQL查询的合法性,所有SELECT语句的选择l果必须h相同数量的列。我们用NULL关键词来补SELECT语句Q从而避免了重复数据?

  通过EXPLICIT模式查询所生成的XML文和通过AUTO模式生成的完全相同,那么Z么要创徏EXPLICIT模式查询呢?

  假设现在有h要求在XML文中包含商店的打折信息。查看Pubs数据库,我们得知每个商店都可以有0到n范围内的折扣率。因此,一U合理的Ҏ(gu)是在QStoreQ元素下面加上子元素QDiscountQ,q样我们得到如下XML文l构Q?

QSTORESQ?BR>QSTORE Id=&single;&single; Name=&single;&single;Q?BR>QDISCOUNT Type=&single;&single; LowQty=&single;&single; HighQty=&single;&single;Q?BR>QAMOUNTQ</AMOUNTQ?BR>Q?DISCOUNTQ?BR>QSALE OrdNo=&single;&single; Qty=&single;&single;Q?BR>Q?SALEQ?BR>Q?STOREQ?BR>Q?STORESQ?

  q里的改动包括:(x)

  要在QSaleQ元素所在的层次增加一个XML元素QDiscountQ,卻IDiscountQ是QStroeQ的子元素?

  Amount嵌套在<DiscountQ里面,但不应该是<DiscountQ元素的属性?

  在AUTO模式中是不可能实现这些改动的?

  下面是创个新XML文的EXPLICIT模式查询Q?

【图 2A?/P>
SELECT 1 as Tag, NULL as Parent,
s.stor_id as [Store!1!id],
s.stor_name as [Store!1!name],
NULL as [Sale!2!orderno],
NULL as [Sale!2!1ty],
NULL as [Discount!3!type],
NULL as [Discount!3!lowqty],
NULL as [Discount!3!highqty],
NULL as [Discount!3!amount!element]
FROM stores s
UNION ALL
SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty,
NULL,
NULL,
NULL,
NULL
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
UNION ALL
SELECT 3, 1,
NULL,
s.stor_name,
NULL,
NULL,
d.discounttype,
d.lowqty,
d.highqty,
d.discount
FROM stores s, discounts d
WHERE s.stor_id = d.stor_id
ORDER BY [store!1!name]
For XML EXPLICIT

  Z创徏?A所昄的EXPLICIT模式查询Q我们对?的查询进行了如下修改Q?

  增加了第三个子查询提取折扣数据,通过Tag列声明这些数据的标签gؓ(f)3?

  通过指定Parent列ؓ(f)1折扣数据设|成QStoreQ元素的子元素?

  注意在第三个SELECT子查询中我们只包含了那些必需的列Qƈ用NULL补I列。这个子查询包含store_name列,虽然Discount元素q不要用到这个列Q但如果把这个列也设|ؓ(f)NULLQ则l果Universal表将不会(x)按照解析器所要求的那样以节点升序排序Q不妨自p一下看看)。Universal表的排序列也可以用Tag列替代?

  为维持结果Universal表的完整性,W一、二两个SELECT语句也用NULL补以反映ؓ(f)折扣数据增加的列?

  为指定新折扣列的元数据修改了W一个SELECT语句?

  通过在第四个参数中声明element指定Amount列ؓ(f)Discount的一个元素(element是可在第四个参数中声明的多个指o(h)之一Q?

  下面q个XML文档只能用EXPLICIT模式生成Q?

  l果XML文档中不?x)显C出NULL数据Q如折扣lowqty和highqty?/P>

  看来上面的介l,大家可能已经对FOR XML的语法有所了解。通过FOR XML 我们在能够在Query Analyzer 中直接返回一个XML格式的数据或者通过其他多样化表现方式将XML格式的数据显C出来,比如可以数据显C在览器上。下面这个例子就使用FOR XML和ADO数据输出到览器的例子?/P>

Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")

Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=192.168.0.160;Initial Catalog=Northwind;User ID=SA;Password=;"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open

Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn

Dim sQuery
‘定?FOR XML的查询。具体的语法在以后的章节中将详细介绍?BR>sQuery = "QROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'Q<sql:queryQSELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTOQ?sql:queryQ</ROOTQ?

‘徏立ADODB Stream 对象QADODB Stream 对象需要ADO2.5以上版本支持Q它可以记录集转换为数据流?BR>Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"

Response.write "Pushing XML to client for processing " & "QBR/Q?

adoCmd.Properties("Output Stream") = Response
‘输出XML格式的文?BR>Response.write "QXML ID=MyDataIsleQ?
adoCmd.Execute , , adExecuteStream
Response.write "Q?XMLQ?

‘通过IE的XML解析器,使用DOMҎ(gu)XML的文本{换ؓ(f)HTML
QSCRIPT language="VBScript" For="window" Event="onload"Q?/P>

Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false

Dim root, child
Set root = xmlDoc.documentElement

For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "QLIQ? & child.getAttribute("ProductName") & "Q?LIQ?
Next

Q?SCRIPTQ?

 EXPLICIT模式

  EXPLICIT模式比较复杂Q我们将用另外一U方法来表达?所昄的查询。这U方法得我们能够完全地控制查询所生成的XML文。首先我们将介绍如何改用EXPLICIT模式~写?所昄的查询,然后看看q种Ҏ(gu)如何赋予我们q远过AUTO模式的能力?

  下面是图1查询用EXPLICIT模式表达的代码:(x)

【图2 ?/P>
--商店数据
SELECT 1 as Tag,
NULL as Parent,
s.stor_id as [store!1!Id],
s.stor_name as [store!1!Name],
NULL as[sale!2!OrderNo],
NULL as [sale!2!Qty]
FROM stores s
UNION ALL
-- 销售数?BR>SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
ORDER BY [store!1!name]
FOR XML EXPLICIT

  q个查询初看h有点复杂Q其实它只是把不同的数据集(卌里的Store和SaleQ分解到了独立的SELECT语句里,然后再用UNION ALL操作W连l成一个查询?

  我们之所以要把查询写成上面的形式Q是Z让查询结果不仅包含XML文档所描述的数据,而且q包含描qXML文l构的元数据。上q查询所生成的表UCؓ(f)Universal表,sqlxml.dll生成XML文旉要这U格式。Universal表对于编写代码的人来说是透明的,但了解这个表q是很有意义的,它将有助于代码的开发和调试。下面是Universal表的一个例子:(x)

Tag Parent store!1!id store!1!name sale!2!orderno sale!2!qty
1 NULL 7066 Barnum&single;s NULL NULL
2 1 7066 Barnum&single;s A297650 50
2 1 7066 Barnum&single;s QA7442 375
1 NULL 8042 Bookbeat NULL NULL
2 1 8042 Bookbeat 423LL9 2215

  Universal表和EXPLICIT模式查询的元数据部分都以U色表示Q黑色表C数据。比较查询和表就可以扑ևsqlxml.dll生成XML文档所需要的元素。我们来仔细地分析一下它们描q的是什么?

  Tag和Parent列是XML文层次l构斚w的信息,我们可以认ؓ(f)?中的每个SELECT语句代表了一个XML节点Q而Tag和Parent列让我们指定节点在文档层ơ结构中的位|。如果在W二个SELECT语句中指定Tag?、指定Parent?Q就表示些数据加上了一个gؓ(f)2的标{,而这些数据的父亲是那些标{ؓ(f)1的数据(即第一个SELECT语句Q。这׃得我们能够构造出QStoreQ和QSaleQ之间的?子关p,而且正如你可能猜惛_的,它得我们可以生成Q意合法的XML文l构。注意第一个SELECT命o(h)的parent列设|成了NULLQ这表示QStoreQ元素处于最层的位|?

  以黑色表C的数据成点的属性或元素Q例如,Store_ID通过列名提供了这斚w的信息。列名字中的?”是分隔W,d可分成四(四个参数Q,其中W四个参数是可选的。这些参数描q的是:(x)

  W一个参数描q该列所属元素的名字Q在q里是<StoreQ元素?

  W二个是标签~号Q它指定了该列信息在XML?wi)Şl构中所处位|?

  W三个参数指定XML文档内的属性或元素名字。在q里名字指定为id?

  数据列默认被创徏为参?所指定节点的属性,即id成为<StoreQ节点的属性。如果要指定id是<StoreQ的一个子元素Q我们可以用第四个可选的参数Q这个参数的一个作用就是让我们把该Ҏ(gu)定ؓ(f)元素Q例如store!1!id!element?

  ׃使用了UNION ALL操作W来q结SELECT语句Qؓ(f)了保证SQL查询的合法性,所有SELECT语句的选择l果必须h相同数量的列。我们用NULL关键词来补SELECT语句Q从而避免了重复数据?

  通过EXPLICIT模式查询所生成的XML文和通过AUTO模式生成的完全相同,那么Z么要创徏EXPLICIT模式查询呢?

  假设现在有h要求在XML文中包含商店的打折信息。查看Pubs数据库,我们得知每个商店都可以有0到n范围内的折扣率。因此,一U合理的Ҏ(gu)是在QStoreQ元素下面加上子元素QDiscountQ,q样我们得到如下XML文档l构Q?

QSTORESQ?BR>QSTORE Id=&single;&single; Name=&single;&single;Q?BR>QDISCOUNT Type=&single;&single; LowQty=&single;&single; HighQty=&single;&single;Q?BR>QAMOUNTQ</AMOUNTQ?BR>Q?DISCOUNTQ?BR>QSALE OrdNo=&single;&single; Qty=&single;&single;Q?BR>Q?SALEQ?BR>Q?STOREQ?BR>Q?STORESQ?

  q里的改动包括:(x)

  要在QSaleQ元素所在的层次增加一个XML元素QDiscountQ,卻IDiscountQ是QStroeQ的子元素?

  Amount嵌套在<DiscountQ里面,但不应该是<DiscountQ元素的属性?

  在AUTO模式中是不可能实现这些改动的?

  下面是创个新XML文的EXPLICIT模式查询Q?

【图 2A?/P>
SELECT 1 as Tag, NULL as Parent,
s.stor_id as [Store!1!id],
s.stor_name as [Store!1!name],
NULL as [Sale!2!orderno],
NULL as [Sale!2!1ty],
NULL as [Discount!3!type],
NULL as [Discount!3!lowqty],
NULL as [Discount!3!highqty],
NULL as [Discount!3!amount!element]
FROM stores s
UNION ALL
SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty,
NULL,
NULL,
NULL,
NULL
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
UNION ALL
SELECT 3, 1,
NULL,
s.stor_name,
NULL,
NULL,
d.discounttype,
d.lowqty,
d.highqty,
d.discount
FROM stores s, discounts d
WHERE s.stor_id = d.stor_id
ORDER BY [store!1!name]
For XML EXPLICIT

  Z创徏?A所昄的EXPLICIT模式查询Q我们对?的查询进行了如下修改Q?

  增加了第三个子查询提取折扣数据,通过Tag列声明这些数据的标签gؓ(f)3?

  通过指定Parent列ؓ(f)1折扣数据设|成QStoreQ元素的子元素?

  注意在第三个SELECT子查询中我们只包含了那些必需的列Qƈ用NULL补I列。这个子查询包含store_name列,虽然Discount元素q不要用到这个列Q但如果把这个列也设|ؓ(f)NULLQ则l果Universal表将不会(x)按照解析器所要求的那样以节点升序排序Q不妨自p一下看看)。Universal表的排序列也可以用Tag列替代?

  为维持结果Universal表的完整性,W一、二两个SELECT语句也用NULL补以反映ؓ(f)折扣数据增加的列?

  为指定新折扣列的元数据修改了W一个SELECT语句?

  通过在第四个参数中声明element指定Amount列ؓ(f)Discount的一个元素(element是可在第四个参数中声明的多个指o(h)之一Q?

  下面q个XML文只能用EXPLICIT模式生成Q?

  l果XML文中不?x)显C出NULL数据Q如折扣lowqty和highqty?/P>

  看来上面的介l,大家可能已经对FOR XML的语法有所了解。通过FOR XML 我们在能够在Query Analyzer 中直接返回一个XML格式的数据或者通过其他多样化表现方式将XML格式的数据显C出来,比如可以数据显C在览器上。下面这个例子就使用FOR XML和ADO数据输出到览器的例子?/P>

Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")

Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=192.168.0.160;Initial Catalog=Northwind;User ID=SA;Password=;"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open

Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn

Dim sQuery
‘定?FOR XML的查询。具体的语法在以后的章节中将详细介绍?BR>sQuery = "QROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'Q<sql:queryQSELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTOQ?sql:queryQ</ROOTQ?

‘徏立ADODB Stream 对象QADODB Stream 对象需要ADO2.5以上版本支持Q它可以记录集转换为数据流?BR>Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"

Response.write "Pushing XML to client for processing " & "QBR/Q?

adoCmd.Properties("Output Stream") = Response
‘输出XML格式的文?BR>Response.write "QXML ID=MyDataIsleQ?
adoCmd.Execute , , adExecuteStream
Response.write "Q?XMLQ?

‘通过IE的XML解析器,使用DOMҎ(gu)XML的文本{换ؓ(f)HTML
QSCRIPT language="VBScript" For="window" Event="onload"Q?/P>

Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false

Dim root, child
Set root = xmlDoc.documentElement

For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "QLIQ? & child.getAttribute("ProductName") & "Q?LIQ?
Next

Q?SCRIPTQ?

 EXPLICIT模式

  EXPLICIT模式比较复杂Q我们将用另外一U方法来表达?所昄的查询。这U方法得我们能够完全地控制查询所生成的XML文。首先我们将介绍如何改用EXPLICIT模式~写?所昄的查询,然后看看q种Ҏ(gu)如何赋予我们q远过AUTO模式的能力?

  下面是图1查询用EXPLICIT模式表达的代码:(x)

【图2 ?/P>
--商店数据
SELECT 1 as Tag,
NULL as Parent,
s.stor_id as [store!1!Id],
s.stor_name as [store!1!Name],
NULL as[sale!2!OrderNo],
NULL as [sale!2!Qty]
FROM stores s
UNION ALL
-- 销售数?BR>SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
ORDER BY [store!1!name]
FOR XML EXPLICIT

  q个查询初看h有点复杂Q其实它只是把不同的数据集(卌里的Store和SaleQ分解到了独立的SELECT语句里,然后再用UNION ALL操作W连l成一个查询?

  我们之所以要把查询写成上面的形式Q是Z让查询结果不仅包含XML文所描述的数据,而且q包含描qXML文l构的元数据。上q查询所生成的表UCؓ(f)Universal表,sqlxml.dll生成XML文档旉要这U格式。Universal表对于编写代码的人来说是透明的,但了解这个表q是很有意义的,它将有助于代码的开发和调试。下面是Universal表的一个例子:(x)

Tag Parent store!1!id store!1!name sale!2!orderno sale!2!qty
1 NULL 7066 Barnum&single;s NULL NULL
2 1 7066 Barnum&single;s A297650 50
2 1 7066 Barnum&single;s QA7442 375
1 NULL 8042 Bookbeat NULL NULL
2 1 8042 Bookbeat 423LL9 2215

  Universal表和EXPLICIT模式查询的元数据部分都以U色表示Q黑色表C数据。比较查询和表就可以扑ևsqlxml.dll生成XML文所需要的元素。我们来仔细地分析一下它们描q的是什么?

  Tag和Parent列是XML文档层次l构斚w的信息,我们可以认ؓ(f)?中的每个SELECT语句代表了一个XML节点Q而Tag和Parent列让我们指定节点在文层ơ结构中的位|。如果在W二个SELECT语句中指定Tag?、指定Parent?Q就表示些数据加上了一个gؓ(f)2的标{,而这些数据的父亲是那些标{ؓ(f)1的数据(即第一个SELECT语句Q。这׃得我们能够构造出QStoreQ和QSaleQ之间的?子关p,而且正如你可能猜惛_的,它得我们可以生成Q意合法的XML文l构。注意第一个SELECT命o(h)的parent列设|成了NULLQ这表示QStoreQ元素处于最层的位|?

  以黑色表C的数据成点的属性或元素Q例如,Store_ID通过列名提供了这斚w的信息。列名字中的?”是分隔W,d可分成四(四个参数Q,其中W四个参数是可选的。这些参数描q的是:(x)

  W一个参数描q该列所属元素的名字Q在q里是<StoreQ元素?

  W二个是标签~号Q它指定了该列信息在XML?wi)Şl构中所处位|?

  W三个参数指定XML文内的属性或元素名字。在q里名字指定为id?

  数据列默认被创徏为参?所指定节点的属性,即id成为<StoreQ节点的属性。如果要指定id是<StoreQ的一个子元素Q我们可以用第四个可选的参数Q这个参数的一个作用就是让我们把该Ҏ(gu)定ؓ(f)元素Q例如store!1!id!element?

  ׃使用了UNION ALL操作W来q结SELECT语句Qؓ(f)了保证SQL查询的合法性,所有SELECT语句的选择l果必须h相同数量的列。我们用NULL关键词来补SELECT语句Q从而避免了重复数据?

  通过EXPLICIT模式查询所生成的XML文和通过AUTO模式生成的完全相同,那么Z么要创徏EXPLICIT模式查询呢?

  假设现在有h要求在XML文档中包含商店的打折信息。查看Pubs数据库,我们得知每个商店都可以有0到n范围内的折扣率。因此,一U合理的Ҏ(gu)是在QStoreQ元素下面加上子元素QDiscountQ,q样我们得到如下XML文l构Q?

QSTORESQ?BR>QSTORE Id=&single;&single; Name=&single;&single;Q?BR>QDISCOUNT Type=&single;&single; LowQty=&single;&single; HighQty=&single;&single;Q?BR>QAMOUNTQ</AMOUNTQ?BR>Q?DISCOUNTQ?BR>QSALE OrdNo=&single;&single; Qty=&single;&single;Q?BR>Q?SALEQ?BR>Q?STOREQ?BR>Q?STORESQ?

  q里的改动包括:(x)

  要在QSaleQ元素所在的层次增加一个XML元素QDiscountQ,卻IDiscountQ是QStroeQ的子元素?

  Amount嵌套在<DiscountQ里面,但不应该是<DiscountQ元素的属性?

  在AUTO模式中是不可能实现这些改动的?

  下面是创个新XML文的EXPLICIT模式查询Q?

【图 2A?/P>
SELECT 1 as Tag, NULL as Parent,
s.stor_id as [Store!1!id],
s.stor_name as [Store!1!name],
NULL as [Sale!2!orderno],
NULL as [Sale!2!1ty],
NULL as [Discount!3!type],
NULL as [Discount!3!lowqty],
NULL as [Discount!3!highqty],
NULL as [Discount!3!amount!element]
FROM stores s
UNION ALL
SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty,
NULL,
NULL,
NULL,
NULL
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
UNION ALL
SELECT 3, 1,
NULL,
s.stor_name,
NULL,
NULL,
d.discounttype,
d.lowqty,
d.highqty,
d.discount
FROM stores s, discounts d
WHERE s.stor_id = d.stor_id
ORDER BY [store!1!name]
For XML EXPLICIT

  Z创徏?A所昄的EXPLICIT模式查询Q我们对?的查询进行了如下修改Q?

  增加了第三个子查询提取折扣数据,通过Tag列声明这些数据的标签gؓ(f)3?

  通过指定Parent列ؓ(f)1折扣数据设|成QStoreQ元素的子元素?

  注意在第三个SELECT子查询中我们只包含了那些必需的列Qƈ用NULL补I列。这个子查询包含store_name列,虽然Discount元素q不要用到这个列Q但如果把这个列也设|ؓ(f)NULLQ则l果Universal表将不会(x)按照解析器所要求的那样以节点升序排序Q不妨自p一下看看)。Universal表的排序列也可以用Tag列替代?

  为维持结果Universal表的完整性,W一、二两个SELECT语句也用NULL补以反映ؓ(f)折扣数据增加的列?

  为指定新折扣列的元数据修改了W一个SELECT语句?

  通过在第四个参数中声明element指定Amount列ؓ(f)Discount的一个元素(element是可在第四个参数中声明的多个指o(h)之一Q?

  下面q个XML文只能用EXPLICIT模式生成Q?

  l果XML文中不?x)显C出NULL数据Q如折扣lowqty和highqty?/P>

  看来上面的介l,大家可能已经对FOR XML的语法有所了解。通过FOR XML 我们在能够在Query Analyzer 中直接返回一个XML格式的数据或者通过其他多样化表现方式将XML格式的数据显C出来,比如可以数据显C在览器上。下面这个例子就使用FOR XML和ADO数据输出到览器的例子?/P>

Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")

Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=192.168.0.160;Initial Catalog=Northwind;User ID=SA;Password=;"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open

Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn

Dim sQuery
‘定?FOR XML的查询。具体的语法在以后的章节中将详细介绍?BR>sQuery = "QROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'Q<sql:queryQSELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTOQ?sql:queryQ</ROOTQ?

‘徏立ADODB Stream 对象QADODB Stream 对象需要ADO2.5以上版本支持Q它可以记录集转换为数据流?BR>Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"

Response.write "Pushing XML to client for processing " & "QBR/Q?

adoCmd.Properties("Output Stream") = Response
‘输出XML格式的文?BR>Response.write "QXML ID=MyDataIsleQ?
adoCmd.Execute , , adExecuteStream
Response.write "Q?XMLQ?

‘通过IE的XML解析器,使用DOMҎ(gu)XML的文本{换ؓ(f)HTML
QSCRIPT language="VBScript" For="window" Event="onload"Q?/P>

Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false

Dim root, child
Set root = xmlDoc.documentElement

For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "QLIQ? & child.getAttribute("ProductName") & "Q?LIQ?
Next

Q?SCRIPTQ?


 EXPLICIT模式

  EXPLICIT模式比较复杂Q我们将用另外一U方法来表达?所昄的查询。这U方法得我们能够完全地控制查询所生成的XML文档。首先我们将介绍如何改用EXPLICIT模式~写?所昄的查询,然后看看q种Ҏ(gu)如何赋予我们q远过AUTO模式的能力?

  下面是图1查询用EXPLICIT模式表达的代码:(x)

【图2 ?/P>
--商店数据
SELECT 1 as Tag,
NULL as Parent,
s.stor_id as [store!1!Id],
s.stor_name as [store!1!Name],
NULL as[sale!2!OrderNo],
NULL as [sale!2!Qty]
FROM stores s
UNION ALL
-- 销售数?BR>SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
ORDER BY [store!1!name]
FOR XML EXPLICIT

  q个查询初看h有点复杂Q其实它只是把不同的数据集(卌里的Store和SaleQ分解到了独立的SELECT语句里,然后再用UNION ALL操作W连l成一个查询?

  我们之所以要把查询写成上面的形式Q是Z让查询结果不仅包含XML文所描述的数据,而且q包含描qXML文l构的元数据。上q查询所生成的表UCؓ(f)Universal表,sqlxml.dll生成XML文旉要这U格式。Universal表对于编写代码的人来说是透明的,但了解这个表q是很有意义的,它将有助于代码的开发和调试。下面是Universal表的一个例子:(x)

Tag Parent store!1!id store!1!name sale!2!orderno sale!2!qty
1 NULL 7066 Barnum&single;s NULL NULL
2 1 7066 Barnum&single;s A297650 50
2 1 7066 Barnum&single;s QA7442 375
1 NULL 8042 Bookbeat NULL NULL
2 1 8042 Bookbeat 423LL9 2215

  Universal表和EXPLICIT模式查询的元数据部分都以U色表示Q黑色表C数据。比较查询和表就可以扑ևsqlxml.dll生成XML文档所需要的元素。我们来仔细地分析一下它们描q的是什么?

  Tag和Parent列是XML文层次l构斚w的信息,我们可以认ؓ(f)?中的每个SELECT语句代表了一个XML节点Q而Tag和Parent列让我们指定节点在文层ơ结构中的位|。如果在W二个SELECT语句中指定Tag?、指定Parent?Q就表示些数据加上了一个gؓ(f)2的标{,而这些数据的父亲是那些标{ؓ(f)1的数据(即第一个SELECT语句Q。这׃得我们能够构造出QStoreQ和QSaleQ之间的?子关p,而且正如你可能猜惛_的,它得我们可以生成Q意合法的XML文档l构。注意第一个SELECT命o(h)的parent列设|成了NULLQ这表示QStoreQ元素处于最层的位|?

  以黑色表C的数据成点的属性或元素Q例如,Store_ID通过列名提供了这斚w的信息。列名字中的?”是分隔W,d可分成四(四个参数Q,其中W四个参数是可选的。这些参数描q的是:(x)

  W一个参数描q该列所属元素的名字Q在q里是<StoreQ元素?

  W二个是标签~号Q它指定了该列信息在XML?wi)Şl构中所处位|?

  W三个参数指定XML文档内的属性或元素名字。在q里名字指定为id?

  数据列默认被创徏为参?所指定节点的属性,即id成为<StoreQ节点的属性。如果要指定id是<StoreQ的一个子元素Q我们可以用第四个可选的参数Q这个参数的一个作用就是让我们把该Ҏ(gu)定ؓ(f)元素Q例如store!1!id!element?

  ׃使用了UNION ALL操作W来q结SELECT语句Qؓ(f)了保证SQL查询的合法性,所有SELECT语句的选择l果必须h相同数量的列。我们用NULL关键词来补SELECT语句Q从而避免了重复数据?

  通过EXPLICIT模式查询所生成的XML文和通过AUTO模式生成的完全相同,那么Z么要创徏EXPLICIT模式查询呢?

  假设现在有h要求在XML文中包含商店的打折信息。查看Pubs数据库,我们得知每个商店都可以有0到n范围内的折扣率。因此,一U合理的Ҏ(gu)是在QStoreQ元素下面加上子元素QDiscountQ,q样我们得到如下XML文l构Q?

QSTORESQ?BR>QSTORE Id=&single;&single; Name=&single;&single;Q?BR>QDISCOUNT Type=&single;&single; LowQty=&single;&single; HighQty=&single;&single;Q?BR>QAMOUNTQ</AMOUNTQ?BR>Q?DISCOUNTQ?BR>QSALE OrdNo=&single;&single; Qty=&single;&single;Q?BR>Q?SALEQ?BR>Q?STOREQ?BR>Q?STORESQ?

  q里的改动包括:(x)

  要在QSaleQ元素所在的层次增加一个XML元素QDiscountQ,卻IDiscountQ是QStroeQ的子元素?

  Amount嵌套在<DiscountQ里面,但不应该是<DiscountQ元素的属性?

  在AUTO模式中是不可能实现这些改动的?

  下面是创个新XML文的EXPLICIT模式查询Q?

【图 2A?/P>
SELECT 1 as Tag, NULL as Parent,
s.stor_id as [Store!1!id],
s.stor_name as [Store!1!name],
NULL as [Sale!2!orderno],
NULL as [Sale!2!1ty],
NULL as [Discount!3!type],
NULL as [Discount!3!lowqty],
NULL as [Discount!3!highqty],
NULL as [Discount!3!amount!element]
FROM stores s
UNION ALL
SELECT 2, 1,
s.stor_id,
s.stor_name,
sa.ord_num,
sa.qty,
NULL,
NULL,
NULL,
NULL
FROM stores s, sales sa
WHERE s.stor_id = sa.stor_id
UNION ALL
SELECT 3, 1,
NULL,
s.stor_name,
NULL,
NULL,
d.discounttype,
d.lowqty,
d.highqty,
d.discount
FROM stores s, discounts d
WHERE s.stor_id = d.stor_id
ORDER BY [store!1!name]
For XML EXPLICIT

  Z创徏?A所昄的EXPLICIT模式查询Q我们对?的查询进行了如下修改Q?

  增加了第三个子查询提取折扣数据,通过Tag列声明这些数据的标签gؓ(f)3?

  通过指定Parent列ؓ(f)1折扣数据设|成QStoreQ元素的子元素?

  注意在第三个SELECT子查询中我们只包含了那些必需的列Qƈ用NULL补I列。这个子查询包含store_name列,虽然Discount元素q不要用到这个列Q但如果把这个列也设|ؓ(f)NULLQ则l果Universal表将不会(x)按照解析器所要求的那样以节点升序排序Q不妨自p一下看看)。Universal表的排序列也可以用Tag列替代?

  为维持结果Universal表的完整性,W一、二两个SELECT语句也用NULL补以反映ؓ(f)折扣数据增加的列?

  为指定新折扣列的元数据修改了W一个SELECT语句?

  通过在第四个参数中声明element指定Amount列ؓ(f)Discount的一个元素(element是可在第四个参数中声明的多个指o(h)之一Q?

  下面q个XML文只能用EXPLICIT模式生成Q?

  l果XML文档中不?x)显C出NULL数据Q如折扣lowqty和highqty?/P>

  看来上面的介l,大家可能已经对FOR XML的语法有所了解。通过FOR XML 我们在能够在Query Analyzer 中直接返回一个XML格式的数据或者通过其他多样化表现方式将XML格式的数据显C出来,比如可以数据显C在览器上。下面这个例子就使用FOR XML和ADO数据输出到览器的例子?/P>

Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")

Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=192.168.0.160;Initial Catalog=Northwind;User ID=SA;Password=;"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open

Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn

Dim sQuery
‘定?FOR XML的查询。具体的语法在以后的章节中将详细介绍?BR>sQuery = "QROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'Q<sql:queryQSELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTOQ?sql:queryQ</ROOTQ?

‘徏立ADODB Stream 对象QADODB Stream 对象需要ADO2.5以上版本支持Q它可以记录集转换为数据流?BR>Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"

Response.write "Pushing XML to client for processing " & "QBR/Q?

adoCmd.Properties("Output Stream") = Response
‘输出XML格式的文?BR>Response.write "QXML ID=MyDataIsleQ?
adoCmd.Execute , , adExecuteStream
Response.write "Q?XMLQ?

‘通过IE的XML解析器,使用DOMҎ(gu)XML的文本{换ؓ(f)HTML
QSCRIPT language="VBScript" For="window" Event="onload"Q?/P>

Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false

Dim root, child
Set root = xmlDoc.documentElement

For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "QLIQ? & child.getAttribute("ProductName") & "Q?LIQ?
Next

Q?SCRIPTQ?

兵器之二QXPath

  W3C ?1999 q?10 ?8 日提出的 XPath 语言规范Q它是一U基于XML的查询语aQ它能在XML文挡中处理数据。SQL Server 2000 中实现的是该规范的子集。它把table和views作ؓ(f)XML的组Ӟq把columns作ؓ(f)XML属性。SQL Server 2000的XML支持IIS使用URL或者模板的方式提交到SQL Server处理Xpath查询Qƈq回XML的结果?

  支持的功?

  下表昄 SQL Server 2000 中实现的 XPath 语言的功能?/P>
功能
?/TD> attribute?B>child?B>parent ?self ?/TD>
包括q箋谓词和嵌套谓词在内的布尔D?/TD>  
所有关p运符 =, !=, Q? Q?, Q? Q?
术q算W?/TD> +, -, *, div
昑ּ转换函数 number()?B>string()?B>Boolean()
布尔q算W?/TD> AND, OR
布尔函数 true()?B>false()?B>not()
XPath 变量  

  不支持的功能

  下表昄 SQL Server 2000 中没有实现的 XPath 语言的功能?/P>
功能
?/TD> ancestor、ancestor-or-self、descendant、descendant-or-self (//)、following、following-sibling、namespace、preceding、preceding-sibling
数D?/TD>  
术q算W?/TD> mod
节点函数 ancestor、ancestor-or-self、descendant、descendant-or-self (//)、following、following-sibling、namespace、preceding、preceding-sibling
字符串函?/TD> string()、concat()、starts-with()、contains()、substring-before()、substring-after()、substring()、string-length()、normalize()、translate()
布尔函数 lang()
数字函数 sum()、floor()、ceiling()、round()
Union q算W?/TD> |

  XPath 查询是以表达式的形式指定的。位|\径是一U比较常用表辑ּQ用以选择相对于上下文节点的节炚w。位|\径表辑ּ的求值结果是节点集?

XML 文档
QrootQ?BR>  Qorder productid="Prod-28" unitprice="45.6" quantity="15"Q?BR>  QdiscountQ?.25Q?discountQ?BR>  Q?orderQ?
  Qorder productid="Prod-39" unitprice="18" quantity="21"Q?BR>  QdiscountQ?.25Q?discountQ?
  Q?orderQ?BR>  Qorder productid="Prod-46" unitprice="12" quantity="2"Q?
  QdiscountQ?.25Q?discountQ?BR>  Q?orderQ?
Q?rootQ?

  下面是查询该XML 文的XPath位置路径表达式,它的含义是返回根节点下所有<ROOTQ子元素下的ProductID属性的属性gؓ(f) "prod-39"?QorderQ?元素?/P>

  位置路径的类?/B>

  可以分ؓ(f)l对位置路径和相对位|\径?

  l对位置路径以文的根节点开始,由斜?(/) l成Q后面可以是相对位置路径。斜?(/) 选定文档的根节点?

  相对位置路径以文的上下文节点(ContextQ开始,由斜?(/) 所分开的一个或多个位置步骤序列l成。每个步骤都选定相对于上下文节点的节炚w。初始步骤序列选定相对于上下文节点的节炚w。节炚w中的每个节点都用作后l步骤的上下文节炏V由后箋步骤标识的节炚w联接在一赗例如,child::Order/child::OrderDetail 选定上下文节点的QorderQ?子元素的 QorderdetailQ?子元素?

  位置步骤 Q绝Ҏ(gu)相对Q位|\径由包含下面三部分的位置步骤l成Q?

  ?

  轴指定位|步骤选定的节点与上下文节点之间的?wi)关pRSQL Server 2000 支持 parent、child、attribute ?self 轴?

  如果在位|\径中指定 child _(d)查询选定的所有节炚w是上下文节点的子节炏V?BR>比如说要查询从当前的上下文节点中选定所?QOrderQ节点的子节?可以使用 child:: Order

  如果指定 parent _(d)选定的节点将是上下文节点的父节点?
比如说要查询从当前的上下文节点中选定所?QOrderQ节点的父节?可以使用 parent:: Order

  如果指定 attribute _(d)选定的节Ҏ(gu)上下文节点的属性?BR>比如说要查询从当前的上下文节点中选定所?QOrderQ节点的属?可以使用 attribute:: Order

  节点试

  节点试指定位置步骤选定的节点类型。每个uQchild、parent、attribute ?selfQ都h主要节点cd。对?attribute _(d)主要节点cd?QattributeQ。对?parent、child ?self _(d)主要节点cd?QelementQ?/P>

  例如Q如果位|\径指?child::OrderQ则选定上下文节点的 QOrderQ?子元素。因?child 轴以 QelementQ?为其主要节点cdQ而且如果Order?QelementQ?节点Q则节点试Order?TRUE?/P>

  选择谓词Q零个或多个Q?/B>

  谓词围绕着轴筛选节炚w。在 XPath 表达式中指定选择谓词与在 SELECT 语句中指?WHERE 子句怼。谓词在括号中指定。应用在选择谓词中指定的试对节点试q回的节点进行筛选。对于要{选的节点集中的每个节点,在对谓词表达式取值时此节点作ؓ(f)上下文节点,节炚w中的节点CZ下文大小。如果谓词表辑ּҎ(gu)节点取gؓ(f) TRUEQ则此节点将包括在最后所得到的节炚w中?/P>

  例如Q?
  1. Child::Order [attribute::ProductID="Prod-39"] 表示从当前的上下文节点中选定ProductID属性gؓ(f)Prod-39的所?QorderQ子节点?/P>

  2. Child::Order [child:: Discount] 表示从当前的上下文节点中选定包含一个或多个 QDiscountQ?子节点的所?QOrderQ?子节炏V?/P>

  3. Child::Order [not(child:: Discount)] 表示从当前的上下文节点中选定不包?QDiscountQ?子节点的所?QOrderQ?子节炏V?/P>

  位置步骤的语?/B>

  是用两个冒号 (::) 分开的u名和节点试Q后面是分别攑֜Ҏ(gu)号中的零个或多个表达式?/P>

  例如Q在 XPath 表达式(位置路径Qchild::Order[attribute::ProductID="prod-39"]中,选定上下文节点的所?QorderQ?子元素。然后将谓词中的试应用于节炚wQ将只返?ProductID属性的属性gؓ(f) "prod-39"?QorderQ?元素节点?

  ~略语法

  Sqlservr2000支持下面的位|\径羃略语?
  attribute::可以~略?@?
  比如Q[attribute::ProductID="Prod-39"] 可以~写?[@ProductID =" Prod-39"]

  child::可以在位|步骤中省略?BR>  比如Q位|\径child::ROOT/child::Orde可以~写?ROOT /Order

  self::node() 可羃略ؓ(f)一个句?(.)Q?parent::node() 可羃略两个句?(..)?/P>

  所?/child::ROOT/child::Order[attribute::ProductID="prod-39"]也可以羃写成 /ROOT/Order[@ProductID="prod-39"]



]]>
一问一{:(x)存储q程l典问题 http://m.tkk7.com/jackybu/articles/1575.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:30:00 GMThttp://m.tkk7.com/jackybu/articles/1575.htmlhttp://m.tkk7.com/jackybu/comments/1575.htmlhttp://m.tkk7.com/jackybu/articles/1575.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1575.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1575.html只涉及到一个表Qxkb_treeNode

表结构是q样Q?BR>node_id          int      //节点id
parentNode_id    int      //父节点id
node_text        varchar  //节点内容
isModule         bit      //是否叶子节点

现在保存的数据有Q?/P>

node_id  parentNode_id  node_text        isModule
   1        -1          语言与文?nbsp;          0
   2        -1            数学               0
   3        -1            技?nbsp;              0
   4         1            语文               0
   5         1            外语               0
   6         5            p               0
   7         6          初中p             0
   8         7           Ҏ(gu)?nbsp;             1
   9         4           定?             1
   10        2            试3              1


现在问题是:(x)
能否通过做一个存储过E,
Ҏ(gu)表中的isModule字段的取|取gؓ(f)1的表C最l叶子结点)Q?BR>比如“特斯塔”ؓ(f)叶子节点Q层层向上递进扑ֈ”特斯塔“的先节点Q?BR>Ҏ(gu)?〉初中英?〉英?〉外?〉语a与文?BR>即通过”特斯塔“找到”语a与文学“来

最l返回的形态ؓ(f)Q?BR>叶子节点id  父节点id      节点名称      先节点名称  先节点id
   8           7           Ҏ(gu)?nbsp;       语言与文?nbsp;      1
   9           4           定?       语言与文?nbsp;      1
   10          2           试3           数学           2

 

/////////////////////////////////////////////////////////////////////////
正确{案Q?/P>

 --生成试数据
create table xkb_treeNode(
node_id        int,
parentNode_id   int,
node_textvarchar(10),
isModulebit)


insert into xkb_treeNode select 1  ,-1,'语言与文?,0
insert into xkb_treeNode select 2  ,-1,'数学',0
insert into xkb_treeNode select 3  ,-1,'技?,0
insert into xkb_treeNode select 4  , 1,'语文',0
insert into xkb_treeNode select 5  , 1,'外语',0
insert into xkb_treeNode select 6  , 5,'p',0
insert into xkb_treeNode select 7  , 6,'初中p',0
insert into xkb_treeNode select 8  , 7,'Ҏ(gu)?        ,1
insert into xkb_treeNode select 9  , 4,'定?',1
insert into xkb_treeNode select 10 , 2,'试3',1


--创徏存储q程
create procedure sp_test
as
begin
   select
       a.node_id,
       a.parentNode_id,
       a.node_text,
       b.node_id   as ancestor_id  ,
       b.node_text as ancestor_text     
   into
       #t
   from
       xkb_treeNode a,xkb_treeNode b
   where
       a.parentNode_id = b.node_id and a.isModule = 1 
  
   while(exists(select 1 from xkb_treeNode a,#t b where a.node_id=ancestor_id and a.parentNode_id != -1))
   begin
       update #t
       set
           ancestor_id   = b.p_id,
           ancestor_text = b.p_text
       from
           #t a,
           (select
               c.node_id,
               d.node_id as p_id,
               d.node_text as p_text
            from
               xkb_treeNode c,xkb_treeNode d
            where
               c.parentNode_id = d.node_id) b
       where
           a.ancestor_id = b.node_id
   end
  
   select * from #t order by node_id
end


--执行存储q程Q结果楼主自q
exec sp_test



]]>
SQL Server联机丛书Q存储过E及其创?http://m.tkk7.com/jackybu/articles/1574.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:28:00 GMThttp://m.tkk7.com/jackybu/articles/1574.htmlhttp://m.tkk7.com/jackybu/comments/1574.htmlhttp://m.tkk7.com/jackybu/articles/1574.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1574.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1574.html存储q程可包含程序流、逻辑以及Ҏ(gu)据库的查询。它们可以接受参数、输出参数、返回单个或多个l果集以及返回倹{?

可以ZM使用 SQL 语句的目的来使用存储q程Q它h以下优点Q?

  • 可以在单个存储过E中执行一pd SQL 语句?BR>
  • 可以从自q存储q程内引用其它存储过E,q可以简化一pd复杂语句?BR>
  • 存储q程在创建时卛_服务器上q行~译Q所以执行v来比单个 SQL 语句快?

存储q程的功能取决于数据库所提供的功能?/P>

创徏存储q程

可?Transact-SQL 语句 CREATE PROCEDURE 创徏存储q程。创建存储过E前Q请考虑下列事项Q?

  • 不能?CREATE PROCEDURE 语句与其?SQL 语句l合到单个批处理中?BR>
  • 创徏存储q程的权限默认属于数据库所有者,该所有者可此权限授予其他用户?BR>
  • 存储q程是数据库对象Q其名称必须遵守标识W规则?BR>
  • 只能在当前数据库中创建存储过E?

创徏存储q程Ӟ应指定:(x)

  • 所有输入参数和向调用过E或批处理返回的输出参数?BR>
  • 执行数据库操作(包括调用其它q程Q的~程语句?BR>
  • q回臌用过E或批处理以表明成功或失败(以及p|原因Q的状态倹{?
pȝ存储q程

Microsoft] SQL Server?2000 中的许多理zd是通过一U称?!--GLOSSARY-->pȝ存储q程的特D过E执行的。系l存储过E在 master 数据库中创徏q存储,带有 sp_ 前缀。可从Q何数据库中执行系l存储过E,而无需使用 master 数据库名U来完全限定该存储过E的名称?/P>

强烈(zhn)不要创Z sp_ 为前~的存储过E。SQL Server 始终按照下列序查找?sp_ 开头的存储q程Q?

  1. ?master 数据库中查找存储q程?BR>
  2. Ҏ(gu)所提供的Q何限定符Q数据库名称或所有者)查找该存储过E?BR>
  3. 如果未指定所有者,则?dbo 作ؓ(f)所有者查找该存储q程?

因此Q虽然当前数据库中可能存在带 sp_ 前缀的用户创建的存储q程Q但M(x)先检?master 数据库(即该存储过E已用数据库名称限定Q?/P>

 重要  如果用户创徏的存储过E与pȝ存储q程同名Q则永远不执行用户创建的存储q程?/P>

分组

如果一个不同的标识可予某q程Q则可以用与现有某存储过E相同的名称创徏该过E,q样可允许将q些q程q行逻辑分组。同名的分组q程可以同时删除。在同一应用E序中用的q程一般都以该方式分组。例如,用于 my_app 应用E序的过E可能被命名?my_proc;1?B>my_proc;2 {。删?my_proc 卛_除该整个l。将q程分组后,无法删除该l内的单个过E?/P>

临时存储q程

专用和全局临时存储q程与(f)时表cMQ都可以用向该过E名U添?# ?## 前缀的方法进行创建? 表示本地临时存储q程Q?# 表示全局临时存储q程。SQL Server 关闭后,q些q程不再存在?/P>

临时存储q程在连接到 SQL Server 的早期版本时很有用,q些早期版本不支持再ơ?Transact-SQL 语句或批处理执行计划。连接到 SQL Server 2000 的应用程序应使用 sp_executesql pȝ存储q程Q而不使用临时存储q程。有x多信息,请参?FONT color=#800080>执行计划的高速缓存和重新使用?

只有创徏本地临时q程的连接才能执行该q程Q当该连接关闭(用户?SQL Server 中注销Q时Q将自动删除该过E?/P>

Mq接都可执行全局临时存储q程。只有创q程的用h用的q接关闭Qƈ且所有其它连接所用的该过E的当前执行版本q行完毕后,全局临时存储q程才不再存在。一旦用于创q程的连接关闭,不再允许启动执行该全局临时存储q程。只允许那些已启动执行该存储q程的连接完成该q程的运行?/P>

如果直接?tempdb 数据库中创徏没有 # ?## 前缀的存储过E,则由于每ơ启?SQL Server ?tempdb 都要重新创徏Q因此当关闭 SQL Server 时将自动删除该存储过E。直接在 tempdb 中创建的q程即在创q程的连接终止后也会(x)存在。与M其它对象一P可向其他用户授予、拒l和废除执行该(f)时存储过E的权限?/P>

CREATE PROCEDURE

创徏存储q程Q存储过E是保存h的可以接受和q回用户提供的参数的 Transact-SQL 语句的集合?/P>

可以创徏一个过E供怹使用Q或在一个会(x)话中临时使用Q局部(f)时过E)Q或在所有会(x)话中临时使用Q全局临时q程Q?/P>

也可以创建在 Microsoft] SQL Server?启动时自动运行的存储q程?/P>

语法

CREATE PROC [ EDURE ] procedure_name [ ; number ]
    [ { @parameter data_type }
        
[ VARYING ] [ = default ] [ OUTPUT ]
    
] [ ,...n ]

[ WITH
    { RECOMPILE | ENCRYPTION | RECOMPILE , ENCRYPTION } ]

[ FOR REPLICATION ]

AS sql_statement [ ...n ]

参数

procedure_name

新存储过E的名称。过E名必须W合标识W规则,且对于数据库及其所有者必d一。有x多信息,请参?FONT color=#800080>使用标识W?/FONT>?/P>

要创建局部(f)时过E,可以?procedure_name 前面加一个编L(fng) (#procedure_name)Q要创徏全局临时q程Q可以在 procedure_name 前面加两个编L(fng) (##procedure_name)。完整的名称Q包?# ?##Q不能超q?128 个字W。指定过E所有者的名称是可选的?/P>

;number

是可选的整数Q用来对同名的过E分l,以便用一?DROP PROCEDURE 语句卛_同l的q程一起除厅R例如,名ؓ(f) orders 的应用程序用的q程可以命名?orderproc;1?B>orderproc;2 {。DROP PROCEDURE orderproc 语句除L个组。如果名UC包含定界标识W,则数字不应包含在标识W中Q只应在 procedure_name 前后使用适当的定界符?/P>

@parameter

q程中的参数。在 CREATE PROCEDURE 语句中可以声明一个或多个参数。用户必d执行q程时提供每个所声明参数的|除非定义了该参数的默认|。存储过E最多可以有 2.100 个参数?/P>

使用 @ W号作ؓ(f)W一个字W来指定参数名称。参数名U必ȝ合标识符的规则。每个过E的参数仅用于该q程本nQ相同的参数名称可以用在其它q程中。默认情况下Q参数只能代替常量,而不能用于代替表名、列名或其它数据库对象的名称。有x多信息,请参?EXECUTE?

data_type

参数的数据类型。所有数据类型(包括 text?B>ntext ?imageQ均可以用作存储q程的参数。不q,cursor 数据cd只能用于 OUTPUT 参数。如果指定的数据cd?cursorQ也必须同时指定 VARYING ?OUTPUT 关键字。有?SQL Server 提供的数据类型及其语法的更多信息Q请参见数据cd?

说明  对于可以?cursor 数据cd的输出参敎ͼ没有最大数目的限制?/P>

VARYING

指定作ؓ(f)输出参数支持的结果集Q由存储q程动态构造,内容可以变化Q。仅适用于游标参数?/P>

default

参数的默认倹{如果定义了默认|不必指定该参数的值即可执行过E。默认值必L帔R?NULL。如果过E将对该参数使用 LIKE 关键字,那么默认g可以包含通配W(%、_、[] ?[^]Q?/P>

OUTPUT

表明参数是返回参数。该选项的值可以返回给 EXEC[UTE]。?OUTPUT 参数可将信息q回l调用过E?B>Text?B>ntext ?image 参数可用?OUTPUT 参数。?OUTPUT 关键字的输出参数可以是游标占位符?/P>

n

表示最多可以指?2.100 个参数的占位W?/P>

{RECOMPILE | ENCRYPTION | RECOMPILE, ENCRYPTION}

RECOMPILE 表明 SQL Server 不会(x)~存该过E的计划Q该q程在q行旉新编译。在使用非典型值或临时D不希望覆盖~存在内存中的执行计划时Q请使用 RECOMPILE 选项?/P>

ENCRYPTION 表示 SQL Server 加密 syscomments 表中包含 CREATE PROCEDURE 语句文本的条目。?ENCRYPTION 可防止将q程作ؓ(f) SQL Server 复制的一部分发布?/P>

说明  在升U过E中QSQL Server 利用存储?syscomments 中的加密注释来重新创建加密过E?/P>

FOR REPLICATION

指定不能在订阅服务器上执行ؓ(f)复制创徏的存储过E?使用 FOR REPLICATION 选项创徏的存储过E可用作存储q程{选,且只能在复制q程中执行。本选项不能?WITH RECOMPILE 选项一起用?/P>

AS

指定q程要执行的操作?/P>

sql_statement

q程中要包含的Q意数目和cd?Transact-SQL 语句。但有一些限制?/P>

n

是表C此q程可以包含多条 Transact-SQL 语句的占位符?/P>

注释

存储q程的最大大ؓ(f) 128 MB?/P>

用户定义的存储过E只能在当前数据库中创徏Q(f)时过E除外,临时q程L?tempdb 中创建)。在单个批处理中QCREATE PROCEDURE 语句不能与其?Transact-SQL 语句l合使用?

默认情况下,参数可ؓ(f)I。如果传?NULL 参数值ƈ且该参数?CREATE ?ALTER TABLE 语句中用,而该语句中引用的列又不允怋?NULLQ则 SQL Server ?x)生一条错误信息。ؓ(f)了防止向不允怋?NULL 的列传?NULL 参数|应向q程中添加编E逻辑或ؓ(f)该列使用默认|使用 CREATE ?ALTER TABLE ?DEFAULT 关键??/P>

在存储过E的M CREATE TABLE ?ALTER TABLE 语句中都为每列显式指?NULL ?NOT NULLQ例如在创徏临时表时。ANSI_DFLT_ON ?ANSI_DFLT_OFF 选项控制 SQL Server 为列指派 NULL ?NOT NULL Ҏ(gu)的方式Q如果在 CREATE TABLE ?ALTER TABLE 语句中没有指定的话)。如果某个连接执行的存储q程对这些选项的设|与创徏该过E的q接的设|不同,则ؓ(f)W二个连接创建的表列可能?x)有不同的?f)I性,q且表现Z同的行ؓ(f)方式。如果ؓ(f)每个列显式声明了 NULL ?NOT NULLQ那么将Ҏ(gu)有执行该存储q程的连接用相同的为空性创Z(f)时表?/P>

在创建或更改存储q程ӞSQL Server 保?SET QUOTED_IDENTIFIER ?SET ANSI_NULLS 的设|。执行存储过E时Q将使用q些原始讄。因此,所有客L(fng)?x)话?SET QUOTED_IDENTIFIER ?SET ANSI_NULLS 讄在执行存储过E时都将被忽略。在存储q程中出现的 SET QUOTED_IDENTIFIER ?SET ANSI_NULLS 语句不媄响存储过E的功能?/P>

其它 SET 选项Q例?SET ARITHABORT、SET ANSI_WARNINGS ?SET ANSI_PADDINGSQ在创徏或更改存储过E时不保存。如果存储过E的逻辑取决于特定的讄Q应在过E开头添加一?SET 语句Q以保讄正确。从存储q程中执?SET 语句Ӟ该设|只在存储过E完成之前有效。之后,讄恢复ؓ(f)调用存储q程时的倹{这使个别的客户端可以设|所需的选项Q而不?x)媄响存储过E的逻辑?/P>

说明  SQL Server 是将I字W串解释为单个空D是解释ؓ(f)真正的空字符Ԍ由兼容别设|控制。如果兼容别小于或{于 65QSQL Server 将I字W串解释为单个空根{如果兼容别等?70Q则 SQL Server 空字符串解释ؓ(f)I字W串。有x多信息,请参?B> sp_dbcmptlevel?

获得有关存储q程的信?/H6>

若要昄用来创徏q程的文本,请在q程所在的数据库中执行 sp_helptextQƈ使用q程名作为参数?

说明  使用 ENCRYPTION 选项创徏的存储过E不能?sp_helptext 查看?/P>

若要昄有关q程引用的对象的报表Q请使用 sp_depends?

若要E重命名Q请使用 sp_rename?

引用对象

SQL Server 允许创徏的存储过E引用尚不存在的对象。在创徏Ӟ只进行语法检查。执行时Q如果高速缓存中无有效的计划,则编译存储过E以生成执行计划。只有在~译q程中才解析存储q程中引用的所有对象。因此,如果语法正确的存储过E引用了不存在的对象Q则仍可以成功创建,但在q行时将p|Q因为所引用的对象不存在。有x多信息,请参?FONT color=#800080>延迟名称解析和编?/FONT>?

延迟名称解析和兼容?/H6>

SQL Server 允许 Transact-SQL 存储q程在创建时引用不存在的表。这U能力称为gq名U解析。不q,如果 Transact-SQL 存储q程引用了该存储q程中定义的表,而兼容别设|(通过执行 sp_dbcmptlevel 来设|)?65Q则在创建时?x)发告信息。而如果在q行时所引用的表不存在,返回错误信息。有x多信息,请参?sp_dbcmptlevel ?FONT color=#800080>延迟名称解析和编?/FONT>?

执行存储q程

成功执行 CREATE PROCEDURE 语句后,q程名称存储在 sysobjects pȝ表中Q?CREATE PROCEDURE 语句的文本将存储?syscomments 中。第一ơ执行时Q将~译该过E以定索数据的最佌问计划?/P>

使用 cursor 数据cd的参?/H6>

存储q程只能?cursor 数据cd用于 OUTPUT 参数。如果ؓ(f)某个参数指定?cursor 数据cdQ也必须指定 VARYING ?OUTPUT 参数。如果ؓ(f)某个参数指定?VARYING 关键字,则数据类型必L cursorQƈ且必L?OUTPUT 关键字?/P>

说明  cursor 数据cd不能通过数据?APIQ例?OLE DB、ODBC、ADO ?DB-LibraryQ绑定到应用E序变量上。因为必dl定 OUTPUT 参数Q应用程序才可以执行存储q程Q所以带?cursor OUTPUT 参数的存储过E不能通过数据?API 调用。只有将 cursor OUTPUT 变量赋值给 Transact-SQL 局?cursor 变量Ӟ才可以通过 Transact-SQL 批处理、存储过E或触发器调用这些过E?/P>

Cursor 输出参数

在执行过E时Q以下规则适用?cursor 输出参数Q?

  1. 对于只进游标Q游标的l果集中q回的行只是那些存储q程执行l束时处于或出游标位置的行Q例如:(x)
    1. 在过E中的名?RS ?100 行结果集上打开一个非滚动游标?

    2. q程提取l果?RS 的头 5 行?BR>
    3. q程q回到其调用者?BR>
    4. q回到调用者的l果?RS ?RS 的第 6 ?100 行组成,调用者中的游标处?RS 的第一行之前?
  2. 对于只进游标Q如果存储过E完成后Q游标位于第一行的前面Q则整个l果集将q回l调用批处理、存储过E或触发器。返回时Q游标将位于W一行的前面?BR>
  3. 对于只进游标Q如果存储过E完成后Q游标的位置出最后一行的l尾Q则用批处理、存储过E或触发器返回空l果集?

    说明  I结果集与空g同?/P>

  4. 对于可滚动游标,在存储过E执行结束时Q结果集中的所有行均会(x)q回l调用批处理、存储过E或触发器。返回时Q游标保留在q程中最后一ơ执行提取时的位|?BR>
  5. 对于Lcd的游标,如果游标关闭Q则空g递回调用批处理、存储过E或触发器。如果将游标指派l一个参敎ͼ但该游标从未打开q,也会(x)出现q种情况?

说明  关闭状态只有在q回时才有媄响。例如,可以在过E中关闭游标Q稍后再打开游标Q然后将该游标的l果集返回给调用批处理、存储过E或触发器?/P>

临时存储q程

SQL Server 支持两种临时q程Q局部(f)时过E和全局临时q程。局部(f)时过E只能由创徏该过E的q接使用。全局临时q程则可由所有连接用。局部(f)时过E在当前?x)话l束时自动除厅R全局临时q程在用该q程的最后一个会(x)话结束时除去。通常是在创徏该过E的?x)话l束时?/P>

临时q程?# ?## 命名Q可以由M用户创徏。创E后Q局部过E的所有者是唯一可以使用该过E的用户。执行局部(f)时过E的权限不能授予其他用户。如果创Z全局临时q程Q则所有用户均可以讉K该过E,权限不能昑ּ废除。只有在 tempdb 数据库中h昑ּ CREATE PROCEDURE 权限的用P才可以在该数据库中显式创Z(f)时过E(不用编L(fng)命名Q。可以授予或废除q些q程中的权限?

说明  频繁使用临时存储q程?x)?tempdb 中的pȝ表上产生争用Q从而对性能产生负面影响。徏议?sp_executesql 代替?B>sp_executesql 不在pȝ表中存储数据Q因此可以避免这一问题?/P>

自动执行存储q程

SQL Server 启动时可以自动执行一个或多个存储q程。这些存储过E必ȝpȝ理员创建,q在 sysadmin 固定服务器角色下作ؓ(f)后台q程执行。这些过E不能有M输入参数?

对启动过E的数目没有限制Q但是要注意Q每个启动过E在执行旉?x)占用一个连接。如果必d启动时执行多个过E,但不需要ƈ行执行,则可以指定一个过E作为启动过E,让该q程调用其它q程。这样就只占用一个连接?/P>

在启动时恢复了最后一个数据库后,卛_始执行存储过E。若要蟩q这些存储过E的执行Q请启动参数指定ؓ(f)跟踪标记 4022。如果以最低配|启?SQL ServerQ?-f 标记Q,则启动存储过E也不会(x)执行。有x多信息,请参?FONT color=#0000ff>跟踪标记?

若要创徏启动存储q程Q必M?sysadmin 固定服务器角色的成员dQƈ?master 数据库中创徏存储q程?/P>

使用 sp_procoption 可以Q?

  1. 现有存储过E指定ؓ(f)启动q程?BR>
  2. 停止?SQL Server 启动时执行过E?BR>
  3. 查看 SQL Server 启动时执行的所有过E的列表?
存储q程嵌套

存储q程可以嵌套Q即一个存储过E可以调用另一个存储过E。在被调用过E开始执行时Q嵌套񔞮增加,在被调用q程执行l束后,嵌套U将减少。如果超出最大的嵌套U,?x)整个调用q程铑֤败。可?@@NESTLEVEL 函数q回当前的嵌套?/P>

若要估计~译后的存储q程大小Q请使用下列性能监视计数器?

性能监视器对象名 性能监视计数器名U?/TH>
SQLServerQ缓冲区理?/TD> 高速缓存大(面敎ͼ
SQLServerQ高速缓存管理器 高速缓存命中率
  高速缓存页
  高速缓存对象计?

* 各种分类的高速缓存对象均可以使用q些计数器,包括Ҏ(gu) sql、准?sql、过E、触发器{?/P>

有关更多信息Q请参见 SQL Server:Buffer Manager 对象?SQL Server:Cache Manager 对象?

sql_statement 限制

除了 SET SHOWPLAN_TEXT ?SET SHOWPLAN_ALL 之外Q这两个语句必须是批处理中仅有的语句Q,M SET 语句均可以在存储q程内部指定。所选择?SET 选项在存储过E执行过E中有效Q之后恢复ؓ(f)原来的设|?

如果其他用户要用某个存储过E,那么在该存储q程内部Q一些语句用的对象名必M用对象所有者的名称限定。这些语句包括:(x)

  1. ALTER TABLE
  2. CREATE INDEX
  3. CREATE TABLE
  4. 所?DBCC 语句
  5. DROP TABLE
  6. DROP INDEX
  7. TRUNCATE TABLE
  8. UPDATE STATISTICS
权限

CREATE PROCEDURE 的权限默认授?sysadmin 固定服务器角色成员和 db_owner ?db_ddladmin 固定数据库角色成员?B>sysadmin 固定服务器角色成员和 db_owner 固定数据库角色成员可以将 CREATE PROCEDURE 权限转让l其他用戗执行存储过E的权限授予q程的所有者,该所有者可以ؓ(f)其它数据库用戯|执行权限?/P>

CZ
A. 使用带有复杂 SELECT 语句的简单过E?/H6>

下面的存储过E从四个表的联接中返回所有作者(提供了姓名)、出版的书籍以及出版C。该存储q程不用Q何参数?/P>

USE pubs
IF EXISTS (SELECT name FROM sysobjects 
         WHERE name = 'au_info_all' AND type = 'P')
   DROP PROCEDURE au_info_all
GO
CREATE PROCEDURE au_info_all
AS
SELECT au_lname, au_fname, title, pub_name
   FROM authors a INNER JOIN titleauthor ta
      ON a.au_id = ta.au_id INNER JOIN titles t
      ON t.title_id = ta.title_id INNER JOIN publishers p
      ON t.pub_id = p.pub_id
GO

au_info_all 存储q程可以通过以下Ҏ(gu)执行Q?/P>

EXECUTE au_info_all
-- Or
EXEC au_info_all

如果该过E是批处理中的第一条语句,则可使用Q?/P>

au_info_all
B. 使用带有参数的简单过E?/H6>

下面的存储过E从四个表的联接中只q回指定的作者(提供了姓名)、出版的书籍以及出版C。该存储q程接受与传递的参数_匚w的倹{?/P>

USE pubs
IF EXISTS (SELECT name FROM sysobjects 
         WHERE name = 'au_info' AND type = 'P')
   DROP PROCEDURE au_info
GO
USE pubs
GO
CREATE PROCEDURE au_info 
   @lastname varchar(40), 
   @firstname varchar(20) 
AS 
SELECT au_lname, au_fname, title, pub_name
   FROM authors a INNER JOIN titleauthor ta
      ON a.au_id = ta.au_id INNER JOIN titles t
      ON t.title_id = ta.title_id INNER JOIN publishers p
      ON t.pub_id = p.pub_id
   WHERE  au_fname = @firstname
      AND au_lname = @lastname
GO

au_info 存储q程可以通过以下Ҏ(gu)执行Q?/P>

EXECUTE au_info 'Dull', 'Ann'
-- Or
EXECUTE au_info @lastname = 'Dull', @firstname = 'Ann'
-- Or
EXECUTE au_info @firstname = 'Ann', @lastname = 'Dull'
-- Or
EXEC au_info 'Dull', 'Ann'
-- Or
EXEC au_info @lastname = 'Dull', @firstname = 'Ann'
-- Or
EXEC au_info @firstname = 'Ann', @lastname = 'Dull'

如果该过E是批处理中的第一条语句,则可使用Q?/P>

au_info 'Dull', 'Ann'
-- Or
au_info @lastname = 'Dull', @firstname = 'Ann'
-- Or
au_info @firstname = 'Ann', @lastname = 'Dull'
C. 使用带有通配W参数的单过E?/H6>

下面的存储过E从四个表的联接中只q回指定的作者(提供了姓名)、出版的书籍以及出版C。该存储q程对传递的参数q行模式匚wQ如果没有提供参敎ͼ则用预讄默认倹{?/P>

USE pubs
IF EXISTS (SELECT name FROM sysobjects 
      WHERE name = 'au_info2' AND type = 'P')
   DROP PROCEDURE au_info2
GO
USE pubs
GO
CREATE PROCEDURE au_info2
   @lastname varchar(30) = 'D%',
   @firstname varchar(18) = '%'
AS 
SELECT au_lname, au_fname, title, pub_name
FROM authors a INNER JOIN titleauthor ta
   ON a.au_id = ta.au_id INNER JOIN titles t
   ON t.title_id = ta.title_id INNER JOIN publishers p
   ON t.pub_id = p.pub_id
WHERE au_fname LIKE @firstname
   AND au_lname LIKE @lastname
GO

au_info2 存储q程可以用多U组合执行。下面只列出了部分组合:(x)

EXECUTE au_info2
-- Or
EXECUTE au_info2 'Wh%'
-- Or
EXECUTE au_info2 @firstname = 'A%'
-- Or
EXECUTE au_info2 '[CK]ars[OE]n'
-- Or
EXECUTE au_info2 'Hunter', 'Sheryl'
-- Or
EXECUTE au_info2 'H%', 'S%'
D. 使用 OUTPUT 参数

OUTPUT 参数允许外部q程、批处理或多?Transact-SQL 语句讉K在过E执行期间设|的某个倹{下面的CZ创徏一个存储过E?(titles_sum)Qƈ使用一个可选的输入参数和一个输出参数?/P>

首先Q创E:(x)

USE pubs
GO
IF EXISTS(SELECT name FROM sysobjects
      WHERE name = 'titles_sum' AND type = 'P')
   DROP PROCEDURE titles_sum
GO
USE pubs
GO
CREATE PROCEDURE titles_sum @@TITLE varchar(40) = '%', @@SUM money OUTPUT
AS
SELECT 'Title Name' = title
FROM titles 
WHERE title LIKE @@TITLE 
SELECT @@SUM = SUM(price)
FROM titles
WHERE title LIKE @@TITLE
GO

接下来,该 OUTPUT 参数用于控制语a?

说明  OUTPUT 变量必须在创和用该变量旉q行定义?/P>

参数名和变量名不一定要匚wQ不q数据类型和参数位置必须匚wQ除非?@@SUM = variable 形式Q?

DECLARE @@TOTALCOST money
EXECUTE titles_sum 'The%', @@TOTALCOST OUTPUT
IF @@TOTALCOST < 200 
BEGIN
   PRINT ' '
   PRINT 'All of these titles can be purchased for less than $200.'
END
ELSE
   SELECT 'The total cost of these titles is $' 
         + RTRIM(CAST(@@TOTALCOST AS varchar(20)))

下面是结果集Q?/P>

Title Name                                                               
------------------------------------------------------------------------ 
The Busy Executive's Database Guide
The Gourmet Microwave
The Psychology of Computer Cooking

(3 row(s) affected)

Warning, null value eliminated from aggregate.
 
All of these titles can be purchased for less than $200.
E. 使用 OUTPUT 游标参数

OUTPUT 游标参数用来存储过E的局部游标传递回调用批处理、存储过E或触发器?/P>

首先Q创Z下过E,?titles 表上声明q打开一个游标:(x)

USE pubs
IF EXISTS (SELECT name FROM sysobjects 
      WHERE name = 'titles_cursor' and type = 'P')
DROP PROCEDURE titles_cursor
GO
CREATE PROCEDURE titles_cursor @titles_cursor CURSOR VARYING OUTPUT
AS
SET @titles_cursor = CURSOR
FORWARD_ONLY STATIC FOR
SELECT *
FROM titles

OPEN @titles_cursor
GO

接下来,执行一个批处理Q声明一个局部游标变量,执行上述q程以将游标赋值给局部变量,然后从该游标提取行?/P>

USE pubs
GO
DECLARE @MyCursor CURSOR
EXEC titles_cursor @titles_cursor = @MyCursor OUTPUT
WHILE (@@FETCH_STATUS = 0)
BEGIN
   FETCH NEXT FROM @MyCursor
END
CLOSE @MyCursor
DEALLOCATE @MyCursor
GO
F. 使用 WITH RECOMPILE 选项

如果E提供的参数不是典型的参敎ͼq且新的执行计划不应高速缓存或存储在内存中QW(xu)ITH RECOMPILE 子句?x)很有帮助?/P>

USE pubs
IF EXISTS (SELECT name FROM sysobjects
      WHERE name = 'titles_by_author' AND type = 'P')
   DROP PROCEDURE titles_by_author
GO
CREATE PROCEDURE titles_by_author @@LNAME_PATTERN varchar(30) = '%'
WITH RECOMPILE
AS
SELECT RTRIM(au_fname) + ' ' + RTRIM(au_lname) AS 'Authors full name',
   title AS Title
FROM authors a INNER JOIN titleauthor ta 
   ON a.au_id = ta.au_id INNER JOIN titles t
   ON ta.title_id = t.title_id
WHERE au_lname LIKE @@LNAME_PATTERN
GO
G. 使用 WITH ENCRYPTION 选项

WITH ENCRYPTION 子句对用户隐藏存储过E的文本。下例创建加密过E,使用 sp_helptext pȝ存储q程获取关于加密q程的信息,然后试直接?B> syscomments 表中获取关于该过E的信息?/P>

IF EXISTS (SELECT name FROM sysobjects
      WHERE name = 'encrypt_this' AND type = 'P')
   DROP PROCEDURE encrypt_this
GO
USE pubs
GO
CREATE PROCEDURE encrypt_this
WITH ENCRYPTION
AS
SELECT * 
FROM authors
GO

EXEC sp_helptext encrypt_this

下面是结果集Q?/P>

The object's comments have been encrypted.

接下来,选择加密存储q程内容的标识号和文本?/P>

SELECT c.id, c.text 
FROM syscomments c INNER JOIN sysobjects o
   ON c.id = o.id
WHERE o.name = 'encrypt_this'

下面是结果集Q?/P>

说明  text 列的输出昄在单独一行中。执行时Q该信息与 id 列信息出现在同一行中?/P>

id         text                                                        
---------- ------------------------------------------------------------
1413580074 ?????????????????????????????????e?????????????????????????????????????????

(1 row(s) affected)
H. 创徏用户定义的系l存储过E?/H6>

下面的示例创Z个过E,昄表名?emp 开头的所有表及其对应的烦引。如果没有指定参敎ͼ该过E将q回表名?sys 开头的所有表Q及索引Q?/P>

IF EXISTS (SELECT name FROM sysobjects
      WHERE name = 'sp_showindexes' AND type = 'P')
   DROP PROCEDURE sp_showindexes
GO
USE master
GO
CREATE PROCEDURE sp_showindexes
   @@TABLE varchar(30) = 'sys%'
AS 
SELECT o.name AS TABLE_NAME,
   i.name AS INDEX_NAME, 
   indid AS INDEX_ID
FROM sysindexes i INNER JOIN sysobjects o
   ON o.id = i.id 
WHERE o.name LIKE @@TABLE
GO         
USE pubs
EXEC sp_showindexes 'emp%'
GO

下面是结果集Q?/P>

TABLE_NAME       INDEX_NAME       INDEX_ID 
---------------- ---------------- ----------------
employee         employee_ind     1
employee         PK_emp_id        2

(2 row(s) affected)
I. 使用延迟名称解析

下面的示例显C四个过E以及gq名U解析的各种可能使用方式。尽引用的表或列在~译时不存在Q但每个存储q程都可创徏?/P>

IF EXISTS (SELECT name FROM sysobjects
      WHERE name = 'proc1' AND type = 'P')
   DROP PROCEDURE proc1
GO
-- Creating a procedure on a nonexistent table.
USE pubs
GO
CREATE PROCEDURE proc1
AS
   SELECT *
   FROM does_not_exist
GO  
-- Here is the statement to actually see the text of the procedure.
SELECT o.id, c.text
FROM sysobjects o INNER JOIN syscomments c 
   ON o.id = c.id
WHERE o.type = 'P' AND o.name = 'proc1'
GO
USE master
GO
IF EXISTS (SELECT name FROM sysobjects
      WHERE name = 'proc2' AND type = 'P')
   DROP PROCEDURE proc2
GO
-- Creating a procedure that attempts to retrieve information from a
-- nonexistent column in an existing table.
USE pubs
GO
CREATE PROCEDURE proc2
AS
   DECLARE @middle_init char(1)
   SET @middle_init = NULL
   SELECT au_id, middle_initial = @middle_init
   FROM authors
GO  
-- Here is the statement to actually see the text of the procedure.
SELECT o.id, c.text
FROM sysobjects o INNER JOIN syscomments c 
   ON o.id = c.id
WHERE o.type = 'P' and o.name = 'proc2'
转自: http://goaler.xicp.net/ShowLog.asp?ID=515


?/a> 2005-02-28 21:28 发表评论
]]>Sql Server基本函数 http://m.tkk7.com/jackybu/articles/1573.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:25:00 GMThttp://m.tkk7.com/jackybu/articles/1573.htmlhttp://m.tkk7.com/jackybu/comments/1573.htmlhttp://m.tkk7.com/jackybu/articles/1573.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1573.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1573.html长度与分析用 

datalength(Char_expr) q回字符串包含字W数,但不包含后面的空?nbsp;

substring(expression,start,length) 不多说了,取子?nbsp;

right(char_expr,int_expr) q回字符串右边int_expr个字W?nbsp;

字符操作c?nbsp;

upper(char_expr) 转ؓ(f)大写 

lower(char_expr) 转ؓ(f)写 

space(int_expr) 生成int_expr个空?nbsp;

replicate(char_expr,int_expr)复制字符串int_expr?nbsp;

reverse(char_expr) 反{字符?nbsp;

stuff(char_expr1,start,length,char_expr2) 字W串char_expr1中的?nbsp;

start开始的length个字W用char_expr2代替 

ltrim(char_expr) rtrim(char_expr) 取掉I格 


ascii(char) char(ascii) 两函数对?取ascii?Ҏ(gu)a(chn)scii吗取字符 


字符串查?nbsp;

charindex(char_expr,expression) q回char_expr的v始位|?nbsp;

patindex("%pattern%",expression) q回指定模式的v始位|?否则? 


2.数学函数 

abs(numeric_expr) 求绝对?nbsp;

ceiling(numeric_expr) 取大于等于指定值的最整?nbsp;

exp(float_expr) 取指?nbsp;

floor(numeric_expr) 于{于指定值得最大整?nbsp;

pi() 3.1415926......... 

power(numeric_expr,power) q回powerơ方 

rand([int_expr]) 随机C生器 

round(numeric_expr,int_expr) 安int_expr规定的精度四舍五?nbsp;

sign(int_expr) Ҏ(gu)正数,0,负数,,q回+1,0,-1 

sqrt(float_expr) qx?nbsp;


3.日期函数 

getdate() q回日期 

datename(datepart,date_expr) q回名称?nbsp;June 

datepart(datepart,date_expr) 取日期一部䆾 

datediff(datepart,date_expr1.dateexpr2) 日期?nbsp;

dateadd(datepart,number,date_expr) q回日期加上 number 

上述函数中datepart?nbsp;

写法 取值和意义 

yy 1753-9999 q䆾 

qq 1-4 ?nbsp;

mm 1-12 ?nbsp;

dy 1-366 ?nbsp;

dd 1-31 ?nbsp;

wk 1-54 ?nbsp;

dw 1-7 周几 

hh 0-23 时 

mi 0-59 分钟 

ss 0-59 U?nbsp;

ms 0-999 毫秒 


日期转换 

convert() 


4.pȝ函数 

suser_name() 用户d?nbsp;

user_name() 用户在数据库中的名字 

user 用户在数据库中的名字 

show_role() 对当前用戯v作用的规?nbsp;


db_name() 数据库名 

object_name(obj_id) 数据库对象名 

col_name(obj_id,col_id) 列名 

col_length(objname,colname) 列长?nbsp;

valid_name(char_expr) 是否是有效标识符 


]]>
SQL高手?_֦SQL语句介绍 http://m.tkk7.com/jackybu/articles/1572.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:23:00 GMThttp://m.tkk7.com/jackybu/articles/1572.htmlhttp://m.tkk7.com/jackybu/comments/1572.htmlhttp://m.tkk7.com/jackybu/articles/1572.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1572.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1572.html

说明Q复制表(只复制结?源表名:(x)a 新表名:(x)b)

SQL: select * into b from a where 1<>1

说明Q拷贝表(拯数据,源表名:(x)a 目标表名Qb)

SQL: insert into b(a, b, c) select d,e,f from b;

说明Q显C文章、提交h和最后回复时?/FONT>

SQL: select a.title,a.username,b.adddate from table a,(select max(adddate) adddate from table where table.title=a.title) b

说明Q外q接查询(表名1Qa 表名2Qb)

SQL: select a.a, a.b, a.c, b.c, b.d, b.f from a LEFT OUT JOIN b ON a.a = b.c

说明Q日E安排提前五分钟提醒

SQL:  select * from 日程安排 where datediff('minute',f开始时?getdate())>5


说明Q两张关联表Q删除主表中已经在副表中没有的信?BR>SQL: 

delete from info where not exists ( select * from infobz where info.infid=infobz.infid 

说明Q?-
SQL: 

SELECT A.NUM, A.NAME, B.UPD_DATE, B.PREV_UPD_DATE
  FROM TABLE1,
    (SELECT X.NUM, X.UPD_DATE, Y.UPD_DATE PREV_UPD_DATE
        FROM (SELECT NUM, UPD_DATE, INBOUND_QTY, STOCK_ONHAND
                FROM TABLE2
              WHERE TO_CHAR(UPD_DATE,'YYYY/MM') = TO_CHAR(SYSDATE, 'YYYY/MM')) X,
            (SELECT NUM, UPD_DATE, STOCK_ONHAND
                FROM TABLE2
              WHERE TO_CHAR(UPD_DATE,'YYYY/MM') =
                    TO_CHAR(TO_DATE(TO_CHAR(SYSDATE, 'YYYY/MM') '/01','YYYY/MM/DD') - 1, 'YYYY/MM')  Y,
        WHERE X.NUM = Y.NUM Q?Q?BR>          AND X.INBOUND_QTY + NVL(Y.STOCK_ONHAND,0) <> X.STOCK_ONHAND  B
WHERE A.NUM = B.NUM

说明Q?-
SQL: 


 

select * from studentinfo where not exists(select * from student where studentinfo.id=student.id) and pdU?'"&strdepartmentname&"' and 专业名称='"&strprofessionname&"' order by 性别,生源?高考Ll?/FONT>

说明Q?BR>从数据库中去一q的各单位电(sh)话费l计(?sh)话费定额贺电(sh)化肥清单两个表来源Q?BR>SQL:

SELECT a.userper, a.tel, a.standfee, TO_CHAR(a.telfeedate, 'yyyy') AS telyear,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '01', a.factration)) AS JAN,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '02', a.factration)) AS FRI,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '03', a.factration)) AS MAR,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '04', a.factration)) AS APR,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '05', a.factration)) AS MAY,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '06', a.factration)) AS JUE,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '07', a.factration)) AS JUL,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '08', a.factration)) AS AGU,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '09', a.factration)) AS SEP,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '10', a.factration)) AS OCT,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '11', a.factration)) AS NOV,
      SUM(decode(TO_CHAR(a.telfeedate, 'mm'), '12', a.factration)) AS DEC
FROM (SELECT a.userper, a.tel, a.standfee, b.telfeedate, b.factration
        FROM TELFEESTAND a, TELFEE b
        WHERE a.tel = b.telfax) a
GROUP BY a.userper, a.tel, a.standfee, TO_CHAR(a.telfeedate, 'yyyy')

说明Q四表联查问题:(x)

SQL: select * from a left inner join b on a.a=b.b right inner join c on a.a=c.c  inner join d on a.a=d.d where .....

说明Q得到表中最的未用的ID?BR>SQL:

SELECT (CASE WHEN EXISTS(SELECT * FROM Handle b WHERE b.HandleID = 1) THEN MIN(HandleID) + 1 ELSE 1 END) as HandleID
 FROM  Handle
 WHERE NOT HandleID IN (SELECT a.HandleID - 1 FROM Handle a)


]]>
SQL的基本操?/title><link>http://m.tkk7.com/jackybu/articles/1571.html</link><dc:creator>?/dc:creator><author>?/author><pubDate>Mon, 28 Feb 2005 13:20:00 GMT</pubDate><guid>http://m.tkk7.com/jackybu/articles/1571.html</guid><wfw:comment>http://m.tkk7.com/jackybu/comments/1571.html</wfw:comment><comments>http://m.tkk7.com/jackybu/articles/1571.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://m.tkk7.com/jackybu/comments/commentRss/1571.html</wfw:commentRss><trackback:ping>http://m.tkk7.com/jackybu/services/trackbacks/1571.html</trackback:ping><description><![CDATA[1.数据cd <P>数据cd是数据的一U属性,表示数据所表示信息的类型。Q何一U计机语言都定义了自己的数据类型。当Ӟ不同的程序语a都具有不同的特点Q所定义的数据类型的各类和名U都或多或少有些不同。SQL Server 提供?25 U数据类型:(x) </P> <P>·Binary [(n)] </P> <P>·Varbinary [(n)] </P> <P>·Char [(n)] </P> <P>·Varchar[(n)] </P> <P>·Nchar[(n)] </P> <P>·Nvarchar[(n)] </P> <P>·Datetime </P> <P>·Smalldatetime </P> <P>·Decimal[(p[,s])] </P> <P>·Numeric[(p[,s])] </P> <P>·Float[(n)] </P> <P>·Real </P> <P>·Int </P> <P>·Smallint </P> <P>·Tinyint </P> <P>·Money </P> <P>·Smallmoney </P> <P>·Bit </P> <P>·Cursor </P> <P>·Sysname </P> <P>·Timestamp </P> <P>·Uniqueidentifier </P> <P>·Text </P> <P>·Image </P> <P>·Ntext </P> <P><BR>(1)二进制数据类?</P> <P>二进制数据包?Binary、Varbinary ?Image. </P> <P>Binary 数据cd既可以是固定长度?Binary),也可以是变长度的?</P> <P>Binary[(n)] ?n 位固定的二进制数据。其中,n 的取D围是?1 ?8000。其存储H的大小?n + 4 个字节?</P> <P>Varbinary[(n)] ?n 位变长度的二q制数据。其中,n 的取D围是?1 ?8000。其存储H的大小?n + 4个字节,不是 n 个字节?</P> <P>?Image 数据cd中存储的数据是以位字W串存储的,不是?SQL Server 解释的,必须由应用程序来解释。例如,应用E序可以使用 BMP、TIEF、GIF ?JPEG 格式把数据存储在 Image 数据cd中?</P> <P>(2)字符数据cd </P> <P>字符数据的类型包?CharQVarchar ?Text?</P> <P>字符数据是由M字母、符号和数字Ll合而成的数据?</P> <P>Varchar 是变长字W数据,光度不过 8KB。Char 是定长字W数据,光度最多ؓ(f) 8KB。超q?8KB 的ASCII 数据可以使用Text 数据cd存储。例如,因ؓ(f) Html 文全部都是 ASCII 字符Qƈ且在一般情况下长度过 8KBQ所以这些文可?Text 数据cd存储?SQL Server 中?</P> <P>(3)Unicode 数据cd </P> <P>Unicode 数据cd包括 Nchar,Nvarchar 和Ntext?</P> <P>?Microsoft SQL Server 中,传统的非 Unicode 数据cd允许使用q定字W集定义的字W。在 SQL Server 安装q程中,允许选择一U字W集。?Unicode 数据cdQ列中可以存储Q何由Unicode 标准定义的字W。在 Unicode 标准中,包括了以各种字符集定义的全部字符。用Unicode 数据cdQ所战胜的窨是用非 Unicode 数据cd所占用的窨大小的两倍?</P> <P>?SQL Server 中,Unicode 数据?Nchar、Nvarchar ?Ntext 数据cd存储。用这U字W类型存储的列可以存储多个字W集中的字符。当列的长度变化Ӟ应该使用 Nvarchar 字符cdQ这时最多可以存?4000 个字W。当列的长度固定不变Ӟ应该使用 Nchar 字符cdQ同Pq时最多可以存?4000 个字W。当使用 Ntext 数据cdӞ该列可以存储多于 4000 个字W?</P> <P>(4)日期和时间数据类?</P> <P>日期和时间数据类型包?Datetime ?Smalldatetime 两种cd?</P> <P>日期和时间数据类型由有效的日期和旉l成。例如,有效的日期和旉数据包括?/01/98 12:15:00:00:00 PM”和?:28:29:15:01 AM 8/17/98”。前一个数据类型是日期在前Q时间在后一个数据类型是霎时间在前,日期在后。在 Microsoft SQL Server 中,日期和时间数据类型包括Datetime ?Smalldatetime 两种cdӞ所存储的日期范围是?1753 q?1 ?1 日开始,?9999 q?2 ?31 日结?每一个D?8 个存储字?。?Smalldatetime 数据cdӞ所存储的日期范围是 1900 q?1 ?1?开始,?2079 q?12 ?31 日结?每一个D?4 个存储字??</P> <P>日期的格式可以设定。设|日期格式的命o(h)如下Q?</P> <P>Set DateFormat {format | @format _var| </P> <P>其中Qformat | @format_var 是日期的序。有效的参数包括 MDY、DMY、YMD、YDM、MYD ?DYM。在默认情况下,日期格式?MDY?</P> <P>例如Q当执行 Set DateFormat YMD 之后Q日期的格式为年 ??形式Q当执行 Set DateFormat DMY 之后Q日期的格式??月有q?形式 </P> <P>Q?Q数字数据类?</P> <P>数字数据只包含数字。数字数据类型包括正数和负数、小敎ͼ点敎ͼ和整??</P> <P>整数由正整数和负整数l成Q例?39?5?-2 ?33967。在 Micrsoft SQL Server 中,整数存储的数据类型是 IntQSmallint ?Tinyint。Int 数据cd存储数据的范围大?Smallint 数据cd存储数据的范_(d)?Smallint 据类型存储数据的范围大于 Tinyint 数据cd存储数据的范围。?Int 数据狗昔存储数据的范围是?-2 147 483 648 ?2 147 483 647Q每一个D?4个字节存储空_(d)。?Smallint 数据cdӞ存储数据的范围从 -32 768 ?32 767Q每一个D?个字节存储空_(d)。?Tinyint 数据cdӞ存储数据的范围是? ?55Q每一个D?个字节存储空_(d)?</P> <P>_娄数据?SQL Server 中的数据cd?Decimal ?Numeric。这U数据所占的存储I间Ҏ(gu)该数据的位数后的位数来确定?</P> <P>在SQL Server 中,q似数数据的数据类型是 Float ?Real。例如,三分之一q个分数C?333333Q当使用q似数据cd时能准确表示。因此,从系l中索到的数据可能与存储在该列中数据不完全一栗?</P> <P>Q?Q货币数据表C正的或者负的货币数?。在 Microsoft SQL Server 中,货币数据的数据类型是Money ?Smallmoney。Money 数据cd要求 8 个存储字节,Smallmoney 数据cd要求 4 个存储字节?</P> <P>Q?Q特D数据类?</P> <P>Ҏ(gu)数据cd包括前面没有提过的数据类型。特D的数据cd?U,?Timestamp、Bit ?Uniqueidentifier?</P> <P>Timestamp 用于表示SQL Server zd的先后顺序,以二q投q格式表示。Timestamp 数据与插入数据或者日期和旉没有关系?</P> <P>Bit ?1 或?0 l成。当表示真或者假、ON 或?OFF Ӟ使用 Bit 数据cd。例如,询问是否是每一ơ访问的客户求可以存储在q种数据cd的列中?</P> <P>Uniqueidentifier ?16 字节的十六进制数字组成,表示一个全局唯一的。当表的记录行要求唯一ӞGUID是非常有用。例如,在客h识号列用这U数据类型可以区别不同的客户?</P> <P>2.用户定义的数据类?</P> <P>用户定义的数据类型基于在 Microsoft SQL Server 中提供的数据cd。当几个表中必须存储同一U数据类型时Qƈ且ؓ(f)保证q些列有相同的数据类型、长度和可空性时Q可以用用户定义的数据cd。例如,可定义一U称?postal_code 的数据类型,它基?Char 数据cd?</P> <P>当创建用户定义的数据cdӞ必须提供三个敎ͼ(x)数据cd的名U、所Z的系l数据类型和数据cd的可I性?</P> <P>Q?Q创建用户定义的数据cd </P> <P>创徏用户定义的数据类型可以?Transact-SQL 语句。系l存储过E?sp_addtype 可以来创建用户定义的数据cd。其语法形式如下Q?</P> <P>sp_addtype {type},[,system_data_bype][,'null_type'] </P> <P>其中Qtype 是用户定义的数据cd的名U。system_data_type 是系l提供的数据cdQ例?Decimal、Int、Char {等?null_type 表示该数据类型是如何处理I值的Q必M用单引号引v来,例如'NULL'?NOT NULL'或?NONULL'?</P> <P>例子Q?</P> <P>Use cust </P> <P>Exec sp_addtype ssn,'Varchar(11)',"Not Null' </P> <P>创徏一个用户定义的数据cd ssnQ其Z的系l数据类型是变长?1 的字W,不允许空?</P> <P>例子Q?</P> <P>Use cust </P> <P>Exec sp_addtype birthday,datetime,'Null' </P> <P>创徏一个用户定义的数据cd birthdayQ其Z的系l数据类型是 DateTimeQ允许空?</P> <P>例子Q?</P> <P>Use master </P> <P>Exec sp_addtype telephone,'varchar(24),'Not Null' </P> <P>Eexc sp_addtype fax,'varchar(24)','Null' </P> <P>创徏两个数据cdQ即 telephone ?fax </P> <P>Q?Q删除用户定义的数据cd </P> <P>当用户定义的数据cd不需要时Q可删除。删除用户定义的数据cd的命令是 sp_droptype {'type'}?</P> <P>例子Q?</P> <P>Use master </P> <P>Exec sp_droptype 'ssn' </P> <P>注意Q当表中的列q正在用用户定义的数据cdӞ或者在其上面还l定有默认或者规则时Q这U用户定义的数据cd不能删除?</P> <P><BR>2.数据库的相关操作</P> <P><BR>1.如何创徏数据?</P> <P>(1).使用 Create Database 创徏数据?</P> <P><BR>Create Database 语名的语法Ş式如下:(x) </P> <P><BR>Create Database database_name </P> <P>[On </P> <P>{[Primary](Name=logical_file_name, </P> <P>Filename='os_file_name' </P> <P>[,Size=size] </P> <P>[,Maxsize=max_size] </P> <P>}[,...n] </P> <P>] </P> <P>[Log On </P> <P>}(Name=Logical_name, </P> <P>Filename='os_file_name' </P> <P>[,Size=size]) </P> <P>}[,...n] </P> <P>] </P> <P>[For Restore] </P> <P><BR>注释Q?</P> <P>PrimaryQ该选项是一个关键字Q用来指定主文gl中的文件。主文gl不公包含了数据库系l表中的全部内容Q而且q包含了没有在用h件组中包含的全部对象。一个数据库只能有一个主文g。在默认情况下,卛_没有指定Primary关键字时Q列在语句中的第一个文件就是主文g?</P> <P>NameQ该选项指定数据库的逻辑名字Q这是在SQL Server pȝ中用的名称Q是数据库在SQL Server 中标识符?</P> <P>FilenameQ该选项用来指定数据库所在文件的操作pȝ文g名称和\径。在os_file_name中的路径必须是SQL Server 所在服务器上的一个文件夹。该操作pȝ文g名称与Name 的逻辑名称是一一对应的?</P> <P>SizeQ该选项用来指定数据库操作系l文件的大小。在指定文g大小的时候,既可以用MB单位Q也可以使用KB单位。如果没有指定单位,那么pȝ默认的单位是MB。文件最是1MBQ也是_(d)数据库所在的文g不能于1MB。在默认情况下,数据库数据文件的大小?MBQ数据库日志文g的大是 1MB?</P> <P>MaxsizeQ该选项用来指定操作pȝ文g可以增长的最大尺寸。在指定文g增长寸的时候,既可以用MB单位Q也可以使用KB单位。如果没有指定单位,那么pȝ的默认单位是MB。如果没有指定文件可以增长的最大尺寸,那么pȝ的增长是没有限制的,可以占满整个盘I间?</P> <P>FielGrowthQ该选取用来指定文件的增量Q当然该选项不能与Maxsize选项有冲H。该选项指定的数据gؓ(f)零时Q表C文件不能增ѝ该选项可以用MB、KB和百分比指定?</P> <P><BR>例子Q?</P> <P>创徏一个cust数据库,该数据库的主数据文g的逻辑名称是cust_dataQ操作系l文件是cust.mdfQ大是15MBQ最大是 30MBQ以20%的速度增加Q该数据库的日志文g的逻辑名称是cust_logQ操作系l是cust.ldfQ大是3MBQ最大是10MBQ以1MB 的速度增加?</P> <P><BR>Create Database cust </P> <P>On </P> <P>Primary (Name=cust_data, </P> <P>Filename='d:cust.mdf', </P> <P>Size=15MB, </P> <P>Maxsize=30MB, </P> <P>Filegrowth=20%) </P> <P>Log On </P> <P>(Name=cust_log, </P> <P>Filename='d:cust.ldf', </P> <P>Size=3MB, </P> <P>Maxsize=10MB, </P> <P>FileGrowth=1MB) </P> <P><BR>2.如何增加数据库的大小 </P> <P>(1).使用Alter Database命o(h)来增加数据库文g的大?</P> <P>如果在创建数据库文g时没有配|文件的大小自动增长Q那么可以用Alter Database命o(h)来增加文件的大小?</P> <P><BR>例子Q?</P> <P>数据库cust的数据文件cust_data的大调整ؓ(f)50MB?</P> <P>Alter Database cust </P> <P>Modify File (Name='cust_data',Size=50) </P> <P><BR>(2).使用Add File 增加一个次要文?</P> <P>通过为数据库增加ơ要的数据文件和日志文g来增加数据库的大?</P> <P>例子Q?</P> <P>Alter Database cust </P> <P>Add File </P> <P>(Name=cust_data2,Filename='d:cust2.mdf', </P> <P>Size=5MB, </P> <P>Maxsize=10MB, </P> <P>Filegrowth=10%) </P> <P><BR>3.压羃数据库和数据文g </P> <P>(1)使用Dbcc Shrinkdatabase 命o(h)压羃整个数据?</P> <P>例子Q?</P> <P>cust数据库的大小压羃?0% </P> <P>Dbcc Shrinkdatabase (cust,10) </P> <P>(2)使用Dbcc ShrinkFile命o(h)压羃数据库中的某一个数据文?</P> <P>例子Q?</P> <P>cust数据文g的大压~到5MB </P> <P>Dbcc ShrinkFile (cust,5) </P> <P><BR>4.删除数据?</P> <P>(1)使用Drop命o(h)删除数据?</P> <P>例子Q?</P> <P>删除cust数据?</P> <P>Drop Database cust </P> <P><BR>3.表的相关操作Q?</P> <P><BR>1.创徏?</P> <P>(1)用Create Table 命o(h)创徏?</P> <P>语法Q?</P> <P>Create Table tabl_name </P> <P>({ </P> <P>}column_name As computed_column_expression </P> <P>} </P> <P>}[,...n] </P> <P>) </P> <P>[On {fiegroup | Default}] </P> <P>[Textimage_On {fiegroup | Default}] </P> <P><BR>例子Q?</P> <P>打开cust数据库,创徏一个表Q该表包含了学生的有关信息,x学号、姓名、性别、出生日期、籍贯、联pȝ(sh)话、住址和备注信息?</P> <P>Use cust </P> <P>Create Table students </P> <P>( </P> <P>number int not null, </P> <P>name varchar(10) not null, </P> <P>sex char(2) null, </P> <P>birthday datetime null, </P> <P>hometown varchar(30) null, </P> <P>telphone_no varchar(12) null, </P> <P>address varchar(30) null, </P> <P>others varchar(50) null </P> <P>) </P> <P>在这个表中number表示学生代号Q数据类型ؓ(f)intQ不允许为空Qname表示学生姓名Q数据类型ؓ(f)varcharQ长度ؓ(f)10Q不允许为空Q?sex表示学生的性别Q数据类型ؓ(f)charQ长度ؓ(f)2Q允ؓ(f)I;birthday表示学生的出生日期,数据cd为datetimeQ允ؓ(f)I; hometown表示学生的籍贯,数据cd为varcharQ长度ؓ(f)30Q允ؓ(f)I;telephone_no表示学生的联pȝ(sh)脑,数据cd?varcharQ长度ؓ(f)12Q允ؓ(f)I;address表示学生的住址Q数据类型ؓ(f)varcharQ长度ؓ(f)30Q允ؓ(f)I;others表示学生的备注信息,长度?0Q允ؓ(f)I?</P> <P><BR>2.修改表的l构 </P> <P>(1)使用T-SQL语句增加和删除一个新?</P> <P>语法Q?</P> <P>Alter Table table </P> <P>{ </P> <P>ADO </P> <P>{[] </P> <P>|colun_name As computed_column_expression </P> <P>|[] </P> <P>}[,...n] </P> <P>|Drop </P> <P>{Column column </P> <P>}[,...n] </P> <P>} </P> <P><BR>例子Q打开cust数据库,修改其中的表students的结构,增加一个新字段Q字D名为yingQ数据类型是varcharQ长度是10Q没有默认|充许为空?</P> <P>Use cust </P> <P>Alter Table students Add ying varchar(10) null </P> <P><BR>打开cust数据库,修改其中的表students的结构,删除一个字D,字段名ؓ(f)ying?</P> <P>Use cust </P> <P>Alter Table students Drop Column ying </P> <P><BR>3.向表中插入数?</P> <P>(1)?Insert 语句 </P> <P>语法如下Q?</P> <P>Insert [Into] </P> <P>{table_name|view_name}[(column_list)] </P> <P>{Values|values_list|select_statement} </P> <P>注意Q在插入数据Ӟ字符数据和日期数据要使用引号引v来?</P> <P>例子Q?</P> <P>Use cust </P> <P>Insert Into students </P> <P>Values (11,"影子","?,"1999-12-12","湖北","83779805","武汉市桥口区","VB爱好?) </P> <P>打开cust数据库,向students表中插入数据 </P> <P><BR>(2)用Default 选项 </P> <P>在插入数据时Q可以用Default选项。Default选项有两UŞ式,一UŞ式是Default ValuesQ另一U是Default?</P> <P>Default Values 形式中的某一行的所有列插入默认倹{用这UŞ式的前提条g是表中的所有列必须是这四种cd之一QIdentity属性,Timestamp数据cdQ允ؓ(f)NullQ或者有一个指定的默认倹{否则,?x)错误信息?</P> <P>例子Q?</P> <P>Use cust </P> <P>Insert Into students Default Values </P> <P>q个例子?x)出现错误,因?f)students表的number字段是设|ؓ(f)不允ؓ(f)I的?</P> <P><BR>Default 形式是ؓ(f)表中的某一列插入默认倹{要插入的该列必d备一定的条gQ即该列要么是Timestamp 数据cdQ要么是允许为NullQ要么是有一个指定的默认|否则Q会(x)出现错误信息?</P> <P>例子Q?</P> <P>Use cust </P> <P>Insert Into students Values(11,"影子",Default,Default,Default,Default,Default,Default) </P> <P>由天?个字D不能ؓ(f)I,所以要赋|否则?x)出现错误,而后面的6个字D允ؓ(f)I,因此可以调用Default默认?</P> <P><BR>(3)插入部分数据 </P> <P>在用Insert语句插入数据是,q可以插入部分数据,也就是可以ؓ(f)每一行的指定的部分列插入数据。在插入部分数据Ӟ应该注意以下三个问题Q?</P> <P>☆在 Insert 子句中,指定要插入数据的列名?</P> <P>☆在 Values 子句中,列出与列名对应的数据。列名的序和数据的序应该完全对应?</P> <P>☆在 Insert 子句中,没有列出的列应该臛_hq四U类型之一QIdenttty 属性,Timestamp 数据cdQ允ؓ(f) NullQ或者有一个指定的默认倹{否则,?x)出现错误信息?</P> <P>例子Q?</P> <P>Use cust </P> <P>Insert Into students (number,name) </P> <P>Values (110,"影子") </P> <P>打开cust数据库,向students表中插入一行数?</P> <P>注意Q如用下例语句将发生错误Q因为name字段是不允许为空的(在创建数据库时设定的Q?</P> <P>Insert Into students (number) </P> <P>Values (110) </P> <P><BR>(4)?Select 语句插入多条数据 </P> <P>Insert 语句插入数据的特Ҏ(gu)每一ơ只能插入一行数据。相反,Select 也可以用?Insert 语句中,q且可以一ơ插入多条数据。?Select 语句插入数据的语法Ş式如下:(x) </P> <P>Insert table_name </P> <P>Select column_list </P> <P>From table_list </P> <P>Where search_conditions </P> <P>在?Select 语句插入数据Ӟ应该注意下面几点Q?</P> <P>☆在 Insert 语句中?Select Ӟ他们参考的表既可以是相同的Q也可以是不同的?</P> <P>☆要插入数据的表必须已经存在?</P> <P>☆要插入数据的表必须?Select 的结果集兼容。兼容的含义是列的数量和序必须相同Q列的数据类型或者相同,或者SQL Server 可以自动转换?</P> <P>例子Q?</P> <P>Use cust </P> <P>Insert students </P> <P>Select number,name,sex,birthday,hometown,telphone_no,address,others </P> <P>From students </P> <P>注意Q?</P> <P>Select 后面的字D要输完_(d)q个例子是自己向自己插入多条数据Q自己向自己插入是被允许的) </P> <P>补充Q?</P> <P>你还可以“From students”后面加上“Where name="影子"”,只插入name{于影子的记录,可以用And ?Or 加上多个条g?</P> <P><BR>(5)使用 Select Into 插入数据C个新表中 </P> <P>带有 Into 子句?Select 语句允许用户定义一个新表ƈ且把数据插入到新表中。这U方法不同于前面讲述的那些方法。在前面的那些方法中Q一个共同的特点Q是在数据输入之前表已经存在。而?Select Into 插入数据的方法,是在插入数据的过E中建立新表?</P> <P>Select Into 语句的语法如下:(x) </P> <P>Select select_list </P> <P>Into new_table_name </P> <P>From table_list </P> <P>Where search_conditions </P> <P>在?Select Into 插入数据Ӟ要注意下面几点:(x) </P> <P>☆在某个数据库中使用 Select Into 插入数据Ӟ讄该数据库?Select Into/Bulk Copy 为真?</P> <P>☆新表不能存在,否则?x)生错误信息?</P> <P>☆新表中的列和行是基于查询结果集 </P> <P>☆要插入的数据不记录在日志中?</P> <P>☆在select_list 中出现的列应该用别名,否则Q新表中的列没有列名。没列名的表只能通过 Select * From new_table_name 的Ş式查询。因此,应该为列起个别名?</P> <P>☆这U方法多用在对列q行各种计算的情c?</P> <P>例子Q?</P> <P>Select number,name </P> <P>Into newcust1 </P> <P>From students </P> <P>创徏新的表newcust1Q插入students表中的number和name字段的所有数据?</P> <P>补充Q如果要插入所有字D늚记录Q则“Select *”,也可在“From students”后加条ӞҎ(gu)和上个例子一栗?</P> <P><BR>(6)?UPdate 语句修改表中的数?</P> <P>Update 语句用来修改表中已存在的数据。Update 语句既可以一ơ修改一行数据,也可以一ơ修改许多行Q甚臛_以一ơ修改表中的全部数据。Update 语句使用 Where 子句指定要修改的行,使用 Set 子句l出新的数据。新数据可以是常量,也可以是指定的表辑ּQ还可以是?From 子句来自其他表的数据?</P> <P>Update 语句的语法如下:(x) </P> <P>Update {table_name|view_name} </P> <P>Set {column_list}=expression [Q? . .] </P> <P>[Where clause] </P> <P>在?Update 语句Ӟ如果没有使用 Where 子句Q那么就对表中所有的行进行修攏V如果用Update 语句修改数据时与数据完整性约束有冲突Q那么修改就不会(x)发生Q整个修改事务全部滚回。例如,q种冲突可能是所输入的值是错误的数据类型,或者所输入的D背了在该列定义的规则U束Q等{?</P> <P>例子Q?</P> <P>Use cust </P> <P>Update students </P> <P>Set name=name+"007" </P> <P>Where number>100 </P> <P>打开cust数据库,修改students表,使number>100的数据的name的值全部加"007"?</P> <P><BR>4.?Delete 语句删除表中的数?</P> <P>当数据库中的数据不需要的q修可以删除。一般情况下Q删除数据?Delete 语句。Delete 语句可以一ơ从一个表中删除一条或者多条数据行?</P> <P>Delete 语句的语法如下:(x) </P> <P>Delete [From] table_name </P> <P>Where search_conditions </P> <P>?Delete 语句中如果用了 Where 子句Q那么就从指定的表中删除满 Where 子句条g的数据行?</P> <P>例子Q?</P> <P>Use cust </P> <P>Delete students </P> <P>Where number>100 </P> <P>删除 students中,number>100的数?</P> <P>补充Q?</P> <P>如果?Delete 语句中没有指?Where 子句Q那么就表中所有的记录全部删除Q即 Delete students 语句删除表中的全部记录?</P> <P>在删除表中的全部数据Ӟq可以?Truncate Table 语句。Truncate Table 语句?Delete 语句都可以将表中的全部数据删除,但是Q两条语句又有不同的特点。当用户使用 Delete 语句删除数据Ӟ被删除的数据要记录在日志中。ƈ不将Ҏ(gu)据的变化记录在日志中。因此,使用 Truncate Table students 语句删除记录的速度快于使用 Delete students 语句删除表中记录的速度?</P> <P><BR>5.?Drop Table 命o(h)删除?</P> <P>当数据库中的表不需要时可以删除。删除表可以使用 Drop Table 语句。删除表是删除表的定义以及表的全部数据、烦引、触发器、约束和指定该表的许可。当删除表时Q基于表的视图不能被删除Q必M?Drop View 语句删除视图?</P> <P>Drop Table 语句的语法如下:(x) </P> <P>Drop Table table_name </P> <P>例子Q?</P> <P>Use cust </P> <P>Drop Table students </P> <P>删除cust数据库中的students表?</P> <P>补充Q?</P> <P>不能使用 Drop Table 语句删除正在被约束参考的表,必须首先要么删除外键U束Q要么删除参考表。表的所有者可以删除表。当删除表是Ӟl定在该表上的规则或者默认则失掉了绑定,该表的约束或者触发器则自动被删除。如果重新创Q必重新绑定相应的规则和默认、重新创发器和增加必要的U束。另外,pȝ表不能删除?</P> <P>删除表的许可属于表的所有者。然而,数据所有者(DBOQ、系l管理员QSAQ和DLL理员可以删除数据库中的M对象?</P> <P><BR>4.数据的检?/P> <P><BR>1.?Select 子句索记?</P> <P>Select 子句是每一个检索数据的查询核心。它告诉数据库引擎返回什么字Dc?</P> <P>Select 子句的常见Ş式是Q?</P> <P>Select * </P> <P>该子句的意思是“返回在所指定的记录源中能扑ֈ的所有字D”。这U命令Ş式很方便Q因Z无需知道从表中检索的字段名称。然而,索表中的所有列是低效的。因此,因该只检索需要的字段Q这样可以大大的提高查询的效率?</P> <P>2.使用 From 子句指定记录?</P> <P>From 子句说明的是查询索记录的记录源;该记录源可以是一个表或另一个存储查询?</P> <P>你还能从多个表中索记录,q在后面的章节中介l?</P> <P>例子Q?</P> <P>Select * From students 索students表中的所有记?</P> <P>3.?Where 子句说明条g </P> <P>Where 子句告诉数据库引擎根据所提供的一个或多个条g限定其检索的记录。条件是一个表辑ּQ可h真假两种判断?</P> <P>例子Q?</P> <P>Select * From students Where name="影子" </P> <P>q回students中name字段为媄子的列表Q这ơ所q回的结果没有特定顺序,除非你用了 Order By 子句。该子句在后面的章节介l?</P> <P>注意QWhere 子句中的文本字符串界限符是双引号Q在VB中因改ؓ(f)单引P因ؓ(f)在VB中字W串的界定符是双引号?</P> <P>补充Q?</P> <P>使用 And ?Or 逻辑可以两个或更多的条仉接到一起以创徏更高U的 Where 子句?</P> <P>例子Q?</P> <P>Select * From students Where name="影子" And number>100 </P> <P>q回name为媄子number大于100的列表?</P> <P>例子Q?</P> <P>Select * From students Where name="影子" And (number>100 Or number<50) </P> <P>q回name为媄子,number大于100或者小?0的列表?</P> <P><BR>Where 子句中用到的操作W?</P> <P>操作W?功能 </P> <P>< 于 </P> <P><= 于或等?</P> <P>> 大于 </P> <P>>= 大于或等?</P> <P>= {于 </P> <P><> 不等?</P> <P>Between 在某个取D围内 </P> <P>Like 匚w某个模式 </P> <P>In 包含在某个值列表中 </P> <P>SQL中的{于和不{于{操作符与VB中的意义和用相?</P> <P><BR>例子Q?</P> <P>Q?Q?Between 操作W?</P> <P>Use cust </P> <P>Select * From students </P> <P>Where number Between 1 and 100 </P> <P>Between 操作W返回的是位于所说明的界限之内的所有记录倹{这个例子就q回 number 字段 1 ?100 之间的全部记录?</P> <P><BR>Q?Q? Like 操作W和通配W?</P> <P>Use cust </P> <P>Select * From students </P> <P>Where name Like "%?" </P> <P>Like 操作W把记录匚wC说明的某个模式。这个例子是q回含“媄”的L字符丌Ӏ?</P> <P><BR>四种通配W的含义 </P> <P>通配W?描述 </P> <P>% 代表零个或者多个Q意字W?</P> <P>_Q下划线Q?代表一个Q意字W?</P> <P>[] 指定范围内的L单个字符 </P> <P>[^] 不在指定范围内的L单个字符 </P> <P><BR>全部CZ子如下:(x) </P> <P>Like "BR%" q回?BR"开始的L字符?</P> <P>Like "br%" q回?Br"开始的L字符?</P> <P>Like "%een" q回?een"l束的Q意字W串 </P> <P>Like "%en%" q回包含"en"的Q意字W串 </P> <P>Like "_en" q回?en"l束的三个字W串 </P> <P>Like "[CK]%" q回?C"或?K"开始的L字符?</P> <P>Like "[S-V]ing" q回长ؓ(f)四个字符的字W串Q结是"ing"Q开始是从S到V?</P> <P>Like "M[^c]%" q回?M"开始且W二个字W不?c"的Q意字W串?</P> <P><BR>4. 使用 Order By 对结果排?</P> <P>Order By 子句告诉数据库引擎对其检索的记录q行排序。可以对M字段排序Q或者对多个字段排序Qƈ且可以以升序或隆序进行排序?</P> <P>在一个正式的 Select 查询之后包含一?Order By 子句Q后跟想排序的字D(可以有多个)便可以说明一个排序顺序?</P> <P>例子Q?</P> <P>Use cust </P> <P>Select * From students </P> <P>Where name Like "%?" </P> <P>Order By number </P> <P>对返回的l果?number q行排序?</P> <P><BR>以降序排?</P> <P>如要以隆序排序,只需在排序的字段之后使用 Desc 关键字?</P> <P>例子Q?</P> <P>Use cust </P> <P>Select * From students </P> <P>Where name Like "%?" </P> <P>Order By number Desc </P> <P><BR>5. 使用 Top 昄某个范围的第一个记录或最后一个记录?</P> <P>使用 Top 关键字可以只昄一个大记录前面或后面的数几个记录。在查询中,Top 关键字与排序子句一hl果集限制ؓ(f)数几个记录或按某个癑ֈ比显C整个结果记录集合中的一部分?</P> <P>例子Q?</P> <P>Select Top 3 * From students q回 students 表中的前3条记?</P> <P>Select Top 10 Percent * From students q回 students 表中前面?0%个记?</P> <P>Select Top 3 * From students Order By number desc q回 students 表中 number 最大的Q最后)?条记?</P> <P><BR>6. ?As 对字D名q行别名?</P> <P>Z么在查询中对字段命以别名Q或重新命名Q这样做的原因有两个Q?</P> <P>☆所涉及的表的字D名很长Q想使字D在l果集中更易处理一些?</P> <P>☆创建的查询产生了某些计或合计列,需要对之进行命名?</P> <P>不管是什么原因对字段命以别名Q在 SQL 中都可以Ҏ(gu)C?As 子句做得?</P> <P>例子Q?</P> <P>Select number As 学号 ,name As 姓名 From students </P> <P><BR>7. 合ƈ查询 </P> <P>合ƈ查询Q?Union Query Q用于合q具有相同字D늻构的两个表的内容Q如果想在一个结果集中显C多个记录源中的不相关的记录Ӟq十分有用?</P> <P>例子Q?</P> <P>Select * </P> <P>From students </P> <P>Union </P> <P>Select * </P> <P>From students1 </P> <P>该查询结果集?students ?students1 中的记录合ƈC个结果中Q其输出和原表归之前一模一栗?</P> <P>注意Q缺省情况下Q合q查询不?x)返回重复记录(如果记录归pȝ在把记录拷到归表中后不相应的记录删除Q这时该功能有用了Q,可以加上 All 关键字而让合ƈ查询昄重复记录?</P> <P>例子Q?</P> <P>Select * </P> <P>From students </P> <P>Union All </P> <P>Select * </P> <P>From students1 </P> <P>该合q查询显C?students 表和 students1 表的内容Ӟ没有寚w复记录进行处?</P> <P>补充Q?</P> <P>Union q算W允许把两个或者多个查询结果合q到一个查询结果集中。如果比?Union ?Join 两咱q算W,那么 Union q算W增加行的数量,?Join q算W增加列的数量。?Union 时应该注意,两个l果中的列的l构必须匚wQ数据类型必d容等{?</P> <P>Union q算W的语法形式如下Q?</P> <P>Select select_list </P> <P>From clause </P> <P>Where clause </P> <P>Group By clause </P> <P>Having clause </P> <P>Union [All] </P> <P>Select select_list </P> <P>From clause </P> <P>Where clause </P> <P>Group By clause </P> <P>Having clause </P> <P>Order By clause </P> <P>Compute clause </P> <P>对于 Union q算W,有下列几炚w要说明:(x) </P> <P>·在默认情况下QUnion q算W删除全部冗余行。如果用All 选项Q那么冗余行不删除?</P> <P>·?Union 语句中的全部 select_list 必须有相同数量的列、兼容的数据cdq且按照同样的顺序出现?</P> <P>·在结果集中,列名来自W一?Select 语句?</P> <P></P> <P>8.q接查询 </P> <P>在实际用过E中l常需要同时从两个表或者两个以上表中检索数据。连接就是允许同时从两个表或者两个以上表中检索数据,指定q些表中某个或者某些列作ؓ(f)q接条g。在 SQL Server 中,可以使用两种q接语法形式Q一U是 Ansi q接语法形式Q这是连接用?From 子句中,另外一U是 SQL Server q接语句形式Q这是连接用?Where 子句中?</P> <P>Ansi q接语法形式如下Q?</P> <P>Select table_name.column_name,table_name.column_name,... </P> <P>From {table_name [join_type] Join table_name On search_conditions} </P> <P>Where [search_conditions] </P> <P>?Ansi 语法形式中,可以 Ansi q接关键字来定使用的连接Ş式。例如:(x) </P> <P>☆?Inner Join 关键字,l果集中仅包含满x件的行?</P> <P>☆?Cross Join 关键字,l果集中包含两个表中所有行的组合?</P> <P>☆?Outer Join 关键字,l果集中既包含那些满x件的行,q包含那些其中某个表的全部行?</P> <P>SQL Server q接语法形式如下所C:(x) </P> <P>Select table_name.column_name,table_name.column_name,... </P> <P>From [table_name,tab</P><img src ="http://m.tkk7.com/jackybu/aggbug/1571.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://m.tkk7.com/jackybu/" target="_blank">?/a> 2005-02-28 21:20 <a href="http://m.tkk7.com/jackybu/articles/1571.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>我的W一个存储过E??http://m.tkk7.com/jackybu/articles/1570.html?/dc:creator>?/author>Mon, 28 Feb 2005 13:06:00 GMThttp://m.tkk7.com/jackybu/articles/1570.htmlhttp://m.tkk7.com/jackybu/comments/1570.htmlhttp://m.tkk7.com/jackybu/articles/1570.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1570.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1570.html存储q程学习(fn)记录1
我的W一个存储过E?BR>
该存储过E的功能是去完成在多个无关系数据表中执行联合查询和计,最后生成一个统计表?BR>
q个存储q程中包括了Q参C递,存储q程间相互调用ƈq回l果集到临时表中Q用sp_executesql执行动态生成的Sql语句Q(f)时表的创Z及?BR>
==============================================================

CREATE procedure sp_MakeCond
 @FdName nvarchar(20),
 @FdRecord nvarchar(250),
 @CXZT int,
 @GSBM nvarchar(10),
 @Cond nvarchar(250) output
as

 /*
 功能Q?BR>  Ҏ(gu)@CXZT的状态,对于字段@FdNameq行内容@FdRecord的匹配?BR>  当@FdRecord中有内容的时候,q行匚w
  当@GSBM中有内容的时候,dGSBM的条?BR> 输入:
  @FdName 字段名称
  @FdRecord    字段内容
  @GSBM 
  @CXZT      查询状?0-表示_Q?-表示模糊Q?-表示
      该状态仅对KHMC起作?BR> 输出Q?BR>  @Cond   条g语句 例如: 
    输入   dwmc,'上v',1,'RRL'
    输出 dwmc like '上v%' and gsbm='RRL' 
 */
 
 /*
 创徏人:(x) 
 创徏日期Q?BR> --对于改存储过E的版本更新记录在这个地?/P>

 */
 declare @HaveFdRecord as int

 Set @HaveFdRecord = 0
 Set @Cond = ''

 /* dFdRecord */
 if len(rtrim(ltrim(@FdRecord)))>0
 begin
 select @Cond=
  case @CXZT
   when 0 then
    @Cond + @FdName + N'=''' + @FdRecord + ''''
   when 1 then
    @Cond + @FdName + N' like ''' + @FdRecord + '%'''
   when 2 then
    @Cond + @FdName + N' like ''%' + @FdRecord + '%'''
   end
  set @HaveFdRecord = 1
 end

 /* dGSBM */
 if len(rtrim(ltrim(@GSBM)))>0
 begin
  if @HaveFdRecord=1
  begin
   Set @Cond = @Cond + ' and '
  end
  set @Cond = @Cond + ' gsbm=''' + @GSBM + ''''
 end
GO


==============================================================

CREATE Procedure sp_Math_KHYE
 @KHMC nvarchar(250),
 @JZRQ datetime,
 @CXZT int,
 @GSBM nvarchar(10)
as
 /*
 功能Q?BR> 输入Q?BR>  @KHMC  客户名称
  @CXZT 查询状?0-表示_Q?-表示模糊Q?-表示
    该状态仅对KHMC起作?BR>  @JZRQ  截至日期
  @GSBM 
 输出Q?BR>  @ReturnKHYE  Ҏ(gu)条g计算出来的客户余?BR> 说明Q在调用该过E前Q需按照如下语句定义一个命名ؓ(f)#KHYEReturn的(f)时表
 Create Table #KHYEReturn
  (dwmc nvarchar(250),khye decimal(15,6))
 在用完?KHYEReturn后,应该立刻使用下列语句释放该(f)时表
 delete from #KHYEReturn
 drop Table #KHYEReturn
 */

 /*
 实现Ҏ(gu)Q?BR>  
 */

 /*
 创徏人:(x) 
 创徏日期Q?/P>

 --对于改存储过E的版本更新记录在这个地?/P>

 */
 
 Declare @SqlString nvarchar(1000)
 Declare @Cond nvarchar(250)

-- 制作查询条gQ存入@Cond 
EXECUTE sp_MakeCond 'dwmc',@KHMC,@CXZT,@GSBM,@Cond output
 
 /*  */
 set @SqlString = 'select dwmc,sum(xhsl*hsj) as xsje from xsdda where xsrq<=@vJZRQ and ' + @Cond
 set @SqlString = @SqlString + ' group by dwmc'

 Create table #sp_Math_KHYE_XSJE(dwmc nvarchar(250),xsje decimal(15,6))
 
 Declare @ParmDefinition nvarchar(100)
 set @ParmDefinition = '@vKHMC nvarchar(250),@vJZRQ datetime'

-- q个地方是调用sp_executesql来执行动态SqlStringq将l果q回C张(f)时表里面

-- 在这里,曄试图结果返回到游标中间Q但是没有成功?BR>-- Ҏ(gu)资料 insert ?exec 是不能够嵌套执行的,不过在这个地Ҏ(gu)较奇怪,q两个可以嵌套执行?BR>-- 需要注意的地方Q@ParmDefnition是用来定义在sp_executesql中间要用的变量的?BR>-- 曄试验q个地方直接传一个字W串Q不使用变量传递,l果报错。不知道有没有其它的人成功过
-- 在@ParmDefinition后面p传递一个变量列表,按照我的理解Q?BR>-- 是在这个地方给sp_executesqlq程中要使用的变量(也就是Sql语句的变量)赋?BR>
 insert into #sp_Math_KHYE_XSJE EXECUTE sp_executesql  @SqlString,   
      @ParmDefinition,
      @vKHMC=@KHMC,
       @vJZRQ=@JZRQ

 /*  */
 set @SqlString = ''
 set @SqlString = 'select dwmc,sum(bcsk+ysk) as fkje from xhskdda where skrq<=@vJZRQ and ' + @Cond
 set @SqlString = @SqlString + ' group by dwmc'

 Create table #sp_Math_KHYE_FKJE(dwmc nvarchar(250),fkje decimal(15,6))
 
 set @ParmDefinition=''
 set @ParmDefinition = '@vKHMC nvarchar(250),@vJZRQ datetime'
 insert into #sp_Math_KHYE_FKJE EXECUTE sp_executesql  @SqlString,
      @ParmDefinition,
      @vKHMC=@KHMC,
       @vJZRQ=@JZRQ
 
 Create Table #sp_Math_KHYE_Result(
  dwmc nvarchar(250),khye decimal(15,6))

-- 比较单的Sql语句了,左联双QBT的需求,只能用BT的写?/P>

 insert into #sp_Math_KHYE_Result
 select distinct T1.dwmc as dwmc,(T1.fkje-T1.xsje) as khye from
 (
 select
  #sp_Math_KHYE_XSJE.dwmc as dwmc,
  isnull(#sp_Math_KHYE_XSJE.xsje,0) as xsje,
  isnull(#sp_Math_KHYE_FKJE.fkje,0) as fkje
 from #sp_Math_KHYE_XSJE,#sp_Math_KHYE_FKJE
 where #sp_Math_KHYE_XSJE.dwmc*=#sp_Math_KHYE_FKJE.dwmc
 union
 select
  #sp_Math_KHYE_XSJE.dwmc as dwmc,
  isnull(#sp_Math_KHYE_XSJE.xsje,0) as xsje,
  isnull(#sp_Math_KHYE_FKJE.fkje,0) as fkje
 from #sp_Math_KHYE_XSJE,#sp_Math_KHYE_FKJE
 where #sp_Math_KHYE_FKJE.dwmc*=#sp_Math_KHYE_XSJE.dwmc
 ) as T1

 insert into #KHYEReturn select * from #sp_Math_KHYE_Result
GO


==================================================================


CREATE Procedure sp_KHYEXYTJ
 @StartDate datetime,
 @EndDate datetime,
 @KHMC nvarchar(250),
 @CXZT int,
 @GSBM nvarchar(100)
as
 /*
 功能Q?BR> 输入:
  @StartDate 开始日?BR>  @EndDate    截至日期
  @KHMC 客户名称
  @CXZT      查询状?0-表示_Q?-表示模糊Q?-表示
      该状态仅对KHMC起作?BR>  @GSBM 
 输出Q?BR>  
  表结构:(x)
   dwmc ncye  ssye  bqxs  qmye  khxye  cxye
 */
 
 /*
 创徏人:(x) 
 创徏日期Q?/P>

 --对于改存储过E的版本更新记录在这个地?/P>

 */

  -- q个地方求了一堆ؕ七八p的数据Q是需要用来输出的?/P>

 -- 求得?sp_KHYEXYTJ_QMKHYE
 Create Table #sp_KHYEXYTJ_QMKHYE
  (dwmc nvarchar(250),QMkhye decimal(15,6))
 Create Table #KHYEReturn
  (dwmc nvarchar(250),khye decimal(15,6))
 execute sp_Math_KHYE @KHMC,@EndDate,@CXZT,@GSBM
 insert into #sp_KHYEXYTJ_QMKHYE(dwmc,QMKHYE) select * from #KHYEReturn
 delete from #KHYEReturn

 -- 求得?sp_KHYEXYTJ_QMKHYE
 Declare @NowDate datetime
 set @NowDate = GetDate()
 Create Table #sp_KHYEXYTJ_KHYE
  (dwmc nvarchar(250),khye decimal(15,6))
 execute sp_Math_KHYE @KHMC,@NowDate,@CXZT,@GSBM
 insert into #sp_KHYEXYTJ_KHYE select * from #KHYEReturn
 delete from #KHYEReturn

 -- 求得?sp_KHYEXYTJ_NCYE
 Create Table #sp_KHYEXYTJ_NCYE
  (dwmc nvarchar(250),ncye decimal(15,6))
 Set @NowDate=cast(str(year(GetDate()))+'-01-01 00:00:00' as datetime)
 execute sp_Math_KHYE @KHMC,@NowDate,@CXZT,@GSBM
 insert into #sp_KHYEXYTJ_NCYE select * from #KHYEReturn
 delete from #KHYEReturn
 drop table #KHYEReturn

 --
 Declare @SqlString nvarchar(500)
 Declare @Cond nvarchar(100)

-- q里也是求查询条件的地方
 EXECUTE sp_MakeCond 'dwmc',@KHMC,@CXZT,@GSBM,@Cond output

 set @SqlString = 'select dwmc,sum(xhsl*hsj) as xsje from xsdda where xsrq<=@vEndDate and xsrq>=@vStartDate and ' + @Cond
 set @SqlString = @SqlString + ' group by dwmc'

 Create table #sp_KHYEXYTJ_XSJE(dwmc nvarchar(250),xsje decimal(15,6))
 
 Declare @ParmDefinition nvarchar(100)
 set @ParmDefinition = '@vKHMC nvarchar(250),@vEndDate datetime,@vStartDate datetime'
 insert into #sp_KHYEXYTJ_XSJE EXECUTE sp_executesql  @SqlString,
      @ParmDefinition,
      @vKHMC=@KHMC,
       @vEndDate=@EndDate,
      @vStartDate=@StartDate

 -- 制作输出?BR> Create Table #sp_KHYEXYTJ_ReslutTable
  (dwmc nvarchar(250),
  ncye decimal(15,6),
  ssye decimal(15,6),
  bqxs decimal(15,6),
  qmye decimal(15,6),
  khxye decimal(15,6),
  cxye decimal(15,6))

  -- 下面是一堆ؕ七八p的东西了。本来是数据放到游标中去,然后Ҏ(gu)标进行@环处?BR>  --  不过好像速度却很慢,一共是3张数据表Q三章表数据分别?k,4k,2WQ?BR>  -- 用游标处理,最l返回统计表600条数据用?7U,一个比较让人发?c)旉?BR>  -- 可能是我写的不好吧,但是q个旉也确实太长了
  -- 所以,又换成按照临时表来处理Q分别将各个需要统计的数据分开l计Q?BR>  -- 然后攑օC同的临时表里面,最后再所有的数据Ҏ(gu)dwmcq个字段q行兌Q一赯出?BR>  -- 最l查询结果,同样数据量,用时2U钟?BR>  -- 对于q个旉来说Q我q是比较满意的。因为算的数据比较多了,而且和前面用游标用了27s
  -- Ҏ(gu)׃是一个等量。不好坏,先可以拿出来见h了?/P>

 -- 写入输出?q生成统计列?BR> insert into #sp_KHYEXYTJ_ReslutTable(dwmc,bqxs)
  select dwmc,xsje from #sp_KHYEXYTJ_XSJE

 -- 写入输出?BR> update #sp_KHYEXYTJ_ReslutTable
  set #sp_KHYEXYTJ_ReslutTable.ssye = #sp_KHYEXYTJ_KHYE.khye
  from #sp_KHYEXYTJ_KHYE
  where #sp_KHYEXYTJ_ReslutTable.dwmc = #sp_KHYEXYTJ_KHYE.dwmc

 --写入输出?BR> update #sp_KHYEXYTJ_ReslutTable
  set #sp_KHYEXYTJ_ReslutTable.qmye = #sp_KHYEXYTJ_QMKHYE.QMkhye
  from #sp_KHYEXYTJ_QMKHYE
  where #sp_KHYEXYTJ_ReslutTable.dwmc = #sp_KHYEXYTJ_QMKHYE.dwmc

 -- 写入输出?BR> update #sp_KHYEXYTJ_ReslutTable
  set #sp_KHYEXYTJ_ReslutTable.ncye = #sp_KHYEXYTJ_NCYE.ncye
  from #sp_KHYEXYTJ_NCYE
  where #sp_KHYEXYTJ_ReslutTable.dwmc = #sp_KHYEXYTJ_NCYE.dwmc

 -- 计算
 update #sp_KHYEXYTJ_ReslutTable
  set #sp_KHYEXYTJ_ReslutTable.khxye = isnull(xhkhda.khxye,0),
       #sp_KHYEXYTJ_ReslutTable.cxye = abs(#sp_KHYEXYTJ_ReslutTable.ssye)-isnull(xhkhda.khxye,0)
  from xhkhda
  where #sp_KHYEXYTJ_ReslutTable.dwmc = xhkhda.dwmc

 --最l输出结果了Q因为都是算得金额了Qؓ(f)了减误差,在计的时?BR> -- 全部使用6位小敎ͼ在输出的时候,取了两位数来输?/P>

 -- 输入?BR> select
  rtrim(ltrim(dwmc)) as dwmc,
  cast(round(isnull(ncye,0),2) as decimal(15,2)) as ncye,
  cast(round(isnull(ssye,0),2) as decimal(15,2)) as ssye,
  cast(round(isnull(bqxs,0),2) as decimal(15,2)) as bqxs,
  cast(round(isnull(qmye,0),2) as decimal(15,2)) as qmye,
  cast(round(isnull(khxye,0),2) as decimal(15,2)) as khxye,
  cast(round(isnull(
  case
   when cxye<= 0 then 0
   when cxye>0 then cxye
  end,0),2) as decimal(15,2)) as cxye

 from #sp_KHYEXYTJ_ReslutTable
GO

q三个存储过E写的比较ؕ啦,毕竟是我的第一个存储过E嘛。可以谅解的。不q以后就不能写这么ؕ的存储过E了Q否则不可饶恕?BR>
在这三个存储q程中有一些地方写的还是不h意,比方_(d)存储q程A调用存储q程BQ而存储过EB需要返回一个结果集供A使用。虽然用了一个(f)时表来作为存储用Q可是L象写OO一P把(f)时表或者结果集象对象一栯回出厅R记得在写这个地方的前一天偶然看了资料,可以把结果集攑ֈ游标中output出去。不q写的时候忘C在什么地方看到的了,又犯了懒Q所以干脆就直接使用一个(f)时表Q反正游标返回出来后Q也是要攑ֈ临时表里面去的嘛?/P>

]]>
快速上?MySQL Q-囑Ş化操作详?http://m.tkk7.com/jackybu/articles/1419.html?/dc:creator>?/author>Tue, 22 Feb 2005 04:41:00 GMThttp://m.tkk7.com/jackybu/articles/1419.htmlhttp://m.tkk7.com/jackybu/comments/1419.htmlhttp://m.tkk7.com/jackybu/articles/1419.html#Feedback0http://m.tkk7.com/jackybu/comments/commentRss/1419.htmlhttp://m.tkk7.com/jackybu/services/trackbacks/1419.html 
 1、下载介l?/STRONG>
 
    MySQL怿大家一定听说过Q如果不知道它是q什么的Q可以去google一下?/DIV>
    MySQL的大本营Q?A >http://www.mysql.com/
    MySQL的下载地址Q?A >http://dev.mysql.com/downloads/   因ؓ(f)要从q个地址下蝲不少东东Q所以详l分析一下这个网c?nbsp; 
   
 
?关于镜像|站Q没有大陆的Q有香港和台湄。选择它,是ؓ(f)了加快下载速度Q不q也不是l对的,我经常就从北的镜像下蝲Q速度反而更快些?nbsp;
 
?MySQL数据库服务器  q里我选择MySQL 4.1版本。版本太低,许多新特性用不上Q太高,试q没有完善,Ҏ(gu)出Bug。这里选择它推荐的?/DIV>
 
   点击q个链接Q进入下载页面,可以看到Q当前版本是4.1.8。找到?STRONG>Windows downloads”,如图Q因为我使用的是Windowsq_。这里我选择?STRONG>Without installer (unzip in C:\)?/STRONG>q个版本Q因为我喜欢不需要安装的软gQ用的不高兴Q随时可以直接删除,当然需要自己配|一下才能用?/DIV>
   点击“Pick a mirror?q入一个页面,那里的表格可以不填,直接选择一个链接下载它?yu)可以了。下载后的文件名是“mysql-4.1.8-win-noinstall.zip”,大小?5.2M?/DIV>
 
 
?关于?STRONG>Graphical clients?囑Ş界面的客L(fng)Q选择一个吧Q可以进行图形化操作Q何乐而不为?只不q以前我一直用“MySQL Control Center”的Q现在却不开发了。选择“MySQL Administrator”吧Q下载后的文件名是“mysql-administrator-1.0.19-win-noinstall.zip”(q里我选择的是不需要安装版本)Q大是4.5M?/DIV>
 
   同样也选择“MySQL Query Browser”,它是来查询的。下载后的文件名是“mysql-query-browser-1.1.5-win-noinstall.zip”(不需要安装版本)Q大是4.5M?/DIV>
 
   关于q方面的软g比较多,如:(x)MySQL-FrontQEMS MySQL Manager{,比较好用Q不q它们是要Money的?/DIV>
 
??STRONG>Application Programming Interfaces (APIs) ?应用E序接口  ׃我主要是面向Java应用Q所以这里就选择?STRONG>MySQL Connector/J ”,版本选择“MySQL Connector/J 3.0”,因ؓ(f)它是“Procdution”版本。下载后的文件名是“mysql-connector-java-3.0.16-ga.zip”,大小?.2M?/DIV>
 
 
2、安装MySQL
 
  · 扑ֈ下蝲后的mysql-4.1.8-win-noinstall.zipQ解压到D盘,是一个“mysql-4.1.8-win”文件夹Q这里我把它改名为“mysql”,因ؓ(f)我不喜欢带版本号。即q时是“D:\mysql”目录,q个目录下有一个“data”目录,q里是存放数据的地斏Vؓ(f)了方便备份和升Q最好把它放在其它地斏V这里我在D盘新Z个目录“mysql-data”,然后把“D:\mysql”目录下的“data”子目录剪切到“D:\mysql-data”目录中?/DIV>
  
  ·新徏一个“my.ini”文Ӟ注意后缀名是“ini”。内容如下:(x)       
E:\WINDOWS\my.ini
[WinMySQLAdmin]
   Server=D:/mysql/bin/mysqld-nt.exe
  
[mysqld]
   basedir=D:/mysql
   datadir=D:/mysql-data/data
  上面“Server”指?FONT size=4>MySQL的执行主E序Q“basedir”指向MySQL的安装目录,“datadir”指向MySQL的数据存攄录(因ؓ(f)我改变了它,所以需要特别指定)?/FONT>
  然后把这个文件移动到Windows的系l安装目?/STRONG>下,我这里是“E:\WINDOWS”?/DIV>
 
  · 打开MS-DOSH口Q切换到“D:\mysql\bin”目录;或者把“D:\mysql\bin”添加到“环境变量”的“Path”变量中Q这样可以避免切换到“D:\mysql\bin”目录?/DIV>
 
  ·加入到Windows XP的服务中Q?/DIV>
       D:\mysql\bin> mysqld-nt  -install  
   Q这时打开“控刉李?>理工具->服务Q可以看到服务列表中存在“MySQL”服务,如果不希望它自动执行Q可以改为手动,不用它的时候可以节省点内存Q?/FONT>

   · 启动和停止mysql服务
       D:\mysql\bin>net  start mysql
       D:\mysql\bin>net  stop  mysql
 
         
   · Udmysql服务
         mysqld-nt --remove
   Q如果你不再需要MySQL了,先停止MySQL服务Q然后再UdMySQL服务Q最后删除MySQL安装目录卛_Q?/FONT>
 
 
 
二、基本操?/FONT>  
 
?准备工作
 
  在D盘徏立一个mysql-software的目录,把刚才下载的 mysql-administrator-1.0.19-win-noinstall.zip 复制到这个子目录中,解压Q得C?MySQL Administrator 1.0 的目录?/DIV>
  同样如此操作 mysql-query-browser-1.1.5-win-noinstall.zipQ得C?MySQL Query Browser 1.1 的目录?/DIV>
  
 
?启动服务Q?/DIV>
 
· 双击D:\mysql-software\MySQL Administrator 1.0 目录下的 MySQLSystemTrayMonitor.exeQ这时会(x)在Q务栏右侧出现一个图标。点几ZStart Instance?q行MySQL?/DIV>
 
· 然后双击 D:\mysql-software\MySQL Administrator 1.0 目录中的 MySQLAdministrator.exeQ或者直接点M面右键菜单中的“MySQL Administrator ”:(x)
 
· 创徏一个连接名Q可以随便填Q这里是“mxj”,用户名:(x)rootQ密码空着。这是因为mysql默认有一个没有密码的root帐号。点几ZOK”,出现理H口Q?/DIV>
q没什么好说的Q英文也很简单。只谈谈上面N的两项?/DIV>
 
?更改密码
好了Q我的root帐号的密码设|ؓ(f)Qjavamxj   最后,点击“Apply Change”?/DIV>
 
?初始的数据库
  上图可以看到Q初始有两个数据库,mysql库中含有各种配置信息Q不要在q个库中q行表操作?/DIV>
test库初始是I的?EM>另外Q徏立表Ӟ不要和mysql库中的表名取名相同,以免冲突?/DIV>
 
 
?数据创徏与查询(D谈字W编码)
 
·现在来到查询览器,q是叛_右下角“MySQL System Tray Monitor”图标,从中选择“MySQL Query Browser”,因ؓ(f)已经更改qroot的密码,所以要填入新密码?/DIV>
 
· q入ȝ面,叛_test数据库,创徏一个新表?/DIV>
 
 
·  如下单创Z个表
 
· 切换到“Table Options”:(x)
   如果了解数据库的话,q些应该是很熟?zhn)的,不多说了。注意字W设|默认是“Latin1”(保存改变Q再ơ切换到q一栏,p看到了)?/DIV>
 
· 填入一些测试数据:(x)
 
 
· 关闭“MySQL Query Browser”,再重新打开它,切换到testtable表,看到了没有?刚才输入的中文变成了“?Q?Q?Q”,Z么呢Q?再次切换到“Table Options”:(x)
 知道Z么了吧,原来默认字符是“latin1”,因ؓ(f)MySQL是瑞怸家公司的产品。中国h看来要努力了Q?/DIV>
 
 
?解决Ҏ(gu)Q?/DIV>
 
· 停止MySql服务Q关闭所有与MySql相关的程序,打开Windows的系l安装目?/STRONG>下的 my.ini 文gQ如下修改:(x)
E:\WINDOWS\my.ini
[WinMySQLAdmin]
   Server=D:/mysql/bin/mysqld-nt.exe
  
[mysqld]
   basedir=D:/mysql
   datadir=D:/mysql-data/data
   default-character-set=gbk
  
[client]
   default-character-set=gbk
d的两条语句的含义是在客户端和服务端都使用GBK字符集进行编码?/DIV>
 
保存后,重新Ȁz?MySql 服务Q打开“MySQL Query Browser”,再次创徏一个表Q输入中文,一切OKQ?/DIV>
 
 
 
 
后记  
 
   关于在DOS端如何用命o(h)行进?MySQL 的操作,q里׃谈了Q网上这斚w的资料很多。图形界面进?MySQL 操作的Y件还有很多,不过大多数是需要破费的。自q着用吧?/DIV>
   至于 mysql-connector-java-3.0.16-ga.zip q个文gQ在以后开?EJB 的时候会(x)用到的,到时再说?/DIV>

]]> վ֩ģ壺 ޹˾þۺҰ| þþȹ͵ۺ| һ߹ۿ| ٸѾƷ| òƵѸ| ޹ƷƬþ | ɫƵ߹ۿ| ߹ۿĶ | պƬӰ| 18Ůˬˬˬҹվ| һƵ| ˿ҳ | þۺϾƷ| һȫٸɫƬ| x8| ձҺ| רAAAAAAƵ| һɫþۺ޾Ʒ| ޾Ʒ91ר| ŮˬƵȫ| ޹ƷۺϾþ| 㽶һ| þ޸ۿ| eeussӰԺ92242| va߹ۿ| MM1313޹Ʒ| Ů˱Ū߳Ƶ| һ| 99þ޾Ʒһ| ަvþþ| þѹƷ| ŮҼxx00Ƶ| ŮſȵͰƵ| ˳ַ߿| ޻ɫѹۿ| ٸ69XXX| 99þѿƷ| ޸Ůһ| ɫɫۺվ| ޹Ʒ˾þ| ߹͵Ʒѿ|