<?xml version="1.0" encoding="UTF-8" ?>
<rss version="2.0">
<channel>
<title><![CDATA[向东博客 专注WEB应用 构架之美 --- 构架之美，在于尽态极妍 | 应用之美，在于药到病除]]></title> 
<link>http://jackxiang.com/index.php</link> 
<description><![CDATA[赢在IT，Playin' with IT,Focus on Killer Application,Marketing Meets Technology.]]></description> 
<language>zh-cn</language> 
<copyright><![CDATA[向东博客 专注WEB应用 构架之美 --- 构架之美，在于尽态极妍 | 应用之美，在于药到病除]]></copyright>
<item>
<link>http://jackxiang.com/post//</link>
<title><![CDATA[MySql中delimiter的作用是什么?]]></title> 
<author>jack &lt;xdy108@126.com&gt;</author>
<category><![CDATA[WEB2.0]]></category>
<pubDate>Thu, 09 Sep 2010 06:56:22 +0000</pubDate> 
<guid>http://jackxiang.com/post//</guid> 
<description>
<![CDATA[ 
	MYSQL导出一个SQL后: <br/>DELIMITER $$ <br/>DROP TRIGGER IF EXISTS `updateegopriceondelete`$$ <br/>CREATE <br/>&nbsp;&nbsp;&nbsp;&nbsp;TRIGGER `updateegopriceondelete` AFTER&nbsp;&nbsp;DELETE ON&nbsp;&nbsp;`customerinfo` <br/>&nbsp;&nbsp;&nbsp;&nbsp;FOR EACH ROW BEGIN <br/>DELETE FROM egoprice&nbsp;&nbsp;WHERE customerId=OLD.customerId; <br/>&nbsp;&nbsp;&nbsp;&nbsp;END$$ <br/>DELIMITER ; <br/><br/>其中DELIMITER 定好结束符为&quot;$$&quot;, 然后最后又定义为&quot;;&quot;, MYSQL的默认结束符为&quot;;&quot;. <br/><br/><br/><br/>详细解释: <br/>&lt;br/&gt; <br/>其实就是告诉mysql解释器，该段命令是否已经结束了，mysql是否可以执行了。 <br/>默认情况下，delimiter是分号;。在命令行客户端中，如果有一行命令以分号结束， <br/>那么回车后，mysql将会执行该命令。如输入下面的语句 <br/>mysql&gt; select * from test_table; <br/>然后回车，那么MySQL将立即执行该语句。 <br/><br/>但有时候，不希望MySQL这么做。在为可能输入较多的语句，且语句中包含有分号。 <br/>如试图在命令行客户端中输入如下语句 <br/>mysql&gt; CREATE FUNCTION `SHORTEN`(S VARCHAR(255), N INT) <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; RETURNS varchar(255) <br/>mysql&gt; BEGIN <br/>mysql&gt; IF ISNULL(S) THEN <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; RETURN &#039;&#039;; <br/>mysql&gt; ELSEIF N&lt;15 THEN <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; RETURN LEFT(S, N); <br/>mysql&gt; ELSE <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; IF CHAR_LENGTH(S) &lt;=N THEN <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp;RETURN S; <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; ELSE <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp;RETURN CONCAT(LEFT(S, N-10), &#039;...&#039;, RIGHT(S, 5)); <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; END IF; <br/>mysql&gt; END IF; <br/>mysql&gt; END; <br/>默认情况下，不可能等到用户把这些语句全部输入完之后，再执行整段语句。 <br/>因为mysql一遇到分号，它就要自动执行。 <br/>即，在语句RETURN &#039;&#039;;时，mysql解释器就要执行了。 <br/>这种情况下，就需要事先把delimiter换成其它符号，如//或$$。 <br/>mysql&gt; delimiter // <br/>mysql&gt; CREATE FUNCTION `SHORTEN`(S VARCHAR(255), N INT) <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; RETURNS varchar(255) <br/>mysql&gt; BEGIN <br/>mysql&gt; IF ISNULL(S) THEN <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; RETURN &#039;&#039;; <br/>mysql&gt; ELSEIF N&lt;15 THEN <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; RETURN LEFT(S, N); <br/>mysql&gt; ELSE <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; IF CHAR_LENGTH(S) &lt;=N THEN <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp;RETURN S; <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; ELSE <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp;RETURN CONCAT(LEFT(S, N-10), &#039;...&#039;, RIGHT(S, 5)); <br/>mysql&gt;&nbsp;&nbsp;&nbsp;&nbsp; END IF; <br/>mysql&gt; END IF; <br/>mysql&gt; END;// <br/>这样只有当//出现之后，mysql解释器才会执行这段语句 <br/><br/><br/>例子： <br/><br/>mysql&gt; delimiter // <br/><br/>mysql&gt; CREATE PROCEDURE simpleproc (OUT param1 INT) <br/>-&gt; BEGIN <br/>-&gt; SELECT COUNT(*) INTO param1 FROM t; <br/>-&gt; END; <br/>-&gt; // <br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>mysql&gt; delimiter ; <br/><br/>mysql&gt; CALL simpleproc(@a); <br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>mysql&gt; SELECT @a; <br/>+------+ <br/>&#124; @a &#124; <br/>+------+ <br/>&#124; 3 &#124; <br/>+------+ <br/>1 row in set (0.00 sec) <br/><br/><br/><br/><br/><br/><br/>本文代码在 MySQL 5.0.41-community-nt 下运行通过。 <br/><br/>编写了个统计网站访问情况（user agent）的 MySQL 存储过程。就是下面的这段 SQL 代码。 <br/><br/>drop procedure if exists pr_stat_agent; <br/><br/>-- call pr_stat_agent (&#039;2008-07-17&#039;, &#039;2008-07-18&#039;) <br/><br/>create procedure pr_stat_agent <br/>( <br/>&nbsp;&nbsp; pi_date_from&nbsp;&nbsp;date <br/>&nbsp;&nbsp;,pi_date_to&nbsp;&nbsp;&nbsp;&nbsp;date <br/>) <br/>begin <br/>&nbsp;&nbsp; -- check input <br/>&nbsp;&nbsp; if (pi_date_from is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;set pi_date_from = current_date(); <br/>&nbsp;&nbsp; end if; <br/><br/>&nbsp;&nbsp; if (pi_date_to is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;set pi_date_to = pi_date_from; <br/>&nbsp;&nbsp; end if; <br/><br/>&nbsp;&nbsp; set pi_date_to = date_add(pi_date_from, interval 1 day); <br/><br/>&nbsp;&nbsp; -- stat <br/>&nbsp;&nbsp; select agent, count(*) as cnt <br/>&nbsp;&nbsp;&nbsp;&nbsp; from apache_log <br/>&nbsp;&nbsp;&nbsp;&nbsp;where request_time &gt;= pi_date_from <br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;and request_time &lt;&nbsp;&nbsp;pi_date_to <br/>&nbsp;&nbsp;&nbsp;&nbsp;group by agent <br/>&nbsp;&nbsp;&nbsp;&nbsp;order by cnt desc; <br/>end; <br/><br/>我在 EMS SQL Manager 2005 for MySQL 这个 MySQL 图形客户端下可以顺利运行。但是在 SQLyog MySQL GUI v5.02 这个客户端就会出错。最后找到原因是没有设置好 delimiter 的问题。默认情况下，delimiter “;” 用于向 MySQL 提交查询语句。在存储过程中每个 SQL 语句的结尾都有个 “;”，如果这时候，每逢 “;” 就向 MySQL 提交的话，当然会出问题了。于是更改 MySQL 的 delimiter，上面 MySQL 存储过程就编程这样子了： <br/><br/>delimiter //;&nbsp;&nbsp;&nbsp;&nbsp; -- 改变 MySQL delimiter 为：“//” <br/><br/>drop procedure if exists pr_stat_agent // <br/><br/>-- call pr_stat_agent (&#039;2008-07-17&#039;, &#039;2008-07-18&#039;) <br/><br/>create procedure pr_stat_agent <br/>( <br/>&nbsp;&nbsp; pi_date_from&nbsp;&nbsp;date <br/>&nbsp;&nbsp;,pi_date_to&nbsp;&nbsp;&nbsp;&nbsp;date <br/>) <br/>begin <br/>&nbsp;&nbsp; -- check input <br/>&nbsp;&nbsp; if (pi_date_from is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;set pi_date_from = current_date(); <br/>&nbsp;&nbsp; end if; <br/><br/>&nbsp;&nbsp; if (pi_date_to is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;set pi_date_to = pi_date_from; <br/>&nbsp;&nbsp; end if; <br/><br/>&nbsp;&nbsp; set pi_date_to = date_add(pi_date_from, interval 1 day); <br/><br/>&nbsp;&nbsp; -- stat <br/>&nbsp;&nbsp; select agent, count(*) as cnt <br/>&nbsp;&nbsp;&nbsp;&nbsp; from apache_log <br/>&nbsp;&nbsp;&nbsp;&nbsp;where request_time &gt;= pi_date_from <br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;and request_time &lt;&nbsp;&nbsp;pi_date_to <br/>&nbsp;&nbsp;&nbsp;&nbsp;group by agent <br/>&nbsp;&nbsp;&nbsp;&nbsp;order by cnt desc; <br/>end; // <br/><br/>delimiter ; //&nbsp;&nbsp; -- 改回默认的 MySQL delimiter：“;” <br/><br/>当然，MySQL delimiter 符号是可以自由设定的，你可以用 “/” 或者“$$” 等。但是 MySQL 存储过程中比较常见的用法是 “//” 和 “$$”。上面的这段在 SQLyog 中的代码搬到 MySQL 命令客户端（MySQL Command Line Client）却不能执行。 <br/><br/>mysql&gt; delimiter //;&nbsp;&nbsp;&nbsp;&nbsp; -- 改变 MySQL delimiter 为：“//” <br/>mysql&gt; <br/>mysql&gt; drop procedure if exists pr_stat_agent // <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; -- call pr_stat_agent (&#039;2008-07-17&#039;, &#039;2008-07-18&#039;) <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; create procedure pr_stat_agent <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; ( <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;pi_date_from&nbsp;&nbsp;date <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp; ,pi_date_to&nbsp;&nbsp;&nbsp;&nbsp;date <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; ) <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; begin <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;-- check input <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;if (pi_date_from is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; set pi_date_from = current_date(); <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;end if; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;if (pi_date_to is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; set pi_date_to = pi_date_from; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;end if; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;set pi_date_to = date_add(pi_date_from, interval 1 day); <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;-- stat <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;select agent, count(*) as cnt <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from apache_log <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp; where request_time &gt;= pi_date_from <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; and request_time &lt;&nbsp;&nbsp;pi_date_to <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp; group by agent <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp; order by cnt desc; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; end; // <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; delimiter ; //&nbsp;&nbsp; -- 改回默认的 MySQL delimiter：“;” <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; // <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; // <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; // <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; ; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; ; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/><br/>真是奇怪了！最后终于发现问题了，在 MySQL 命令行下运行 “delimiter //; ” 则 MySQL 的 delimiter 实际上是 “//;”，而不是我们所预想的 “//”。其实只要运行指令 “delimiter //” 就 OK 了。 <br/><br/>mysql&gt; delimiter //&nbsp;&nbsp;&nbsp;&nbsp; -- 末尾不要符号 “;” <br/>mysql&gt; <br/>mysql&gt; drop procedure if exists pr_stat_agent // <br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>mysql&gt; <br/>mysql&gt; -- call pr_stat_agent (&#039;2008-07-17&#039;, &#039;2008-07-18&#039;) <br/>mysql&gt; <br/>mysql&gt; create procedure pr_stat_agent <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; ( <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;pi_date_from&nbsp;&nbsp;date <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp; ,pi_date_to&nbsp;&nbsp;&nbsp;&nbsp;date <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; ) <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; begin <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;-- check input <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;if (pi_date_from is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; set pi_date_from = current_date(); <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;end if; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;if (pi_date_to is null) then <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; set pi_date_to = pi_date_from; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;end if; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;set pi_date_to = date_add(pi_date_from, interval 1 day); <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;-- stat <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;select agent, count(*) as cnt <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from apache_log <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp; where request_time &gt;= pi_date_from <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; and request_time &lt;&nbsp;&nbsp;pi_date_to <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp; group by agent <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt;&nbsp;&nbsp;&nbsp;&nbsp; order by cnt desc; <br/>&nbsp;&nbsp;&nbsp;&nbsp;-&gt; end; // <br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>mysql&gt; <br/>mysql&gt; delimiter ;&nbsp;&nbsp;-- 末尾不要符号 “//” <br/>mysql&gt; <br/><br/>顺带一提的是，我们可以在 MySQL 数据库中执行在文件中的 SQL 代码。例如，我把上面存储过程的代码放在文件 d:&#92;pr_stat_agent.sql 中。可以运行下面的代码建立存储过程。 <br/><br/>mysql&gt; source d:&#92;pr_stat_agent.sql <br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>source 指令的缩写形式是：“&#92;.” <br/><br/>mysql&gt; &#92;. d:&#92;pr_stat_agent.sql <br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>Query OK, 0 rows affected (0.00 sec) <br/><br/>最后，可见 MySQL 的客户端工具在有些地方是各自为政，各有各的一套。
]]>
</description>
</item><item>
<link>http://jackxiang.com/post//#blogcomment</link>
<title><![CDATA[[评论] MySql中delimiter的作用是什么?]]></title> 
<author> &lt;user@domain.com&gt;</author>
<category><![CDATA[评论]]></category>
<pubDate>Thu, 01 Jan 1970 00:00:00 +0000</pubDate> 
<guid>http://jackxiang.com/post//#blogcomment</guid> 
<description>
<![CDATA[ 
	
]]>
</description>
</item>
</channel>
</rss>