<?xml version="1.0" encoding="UTF-8"?>
<!-- generator="wordpress/2.2.2" -->
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	>

<channel>
	<title>PHP CookBook 中文翻译 :)</title>
	<link>http://blog.phpman.info</link>
	<description></description>
	<pubDate>Sun, 23 Dec 2007 11:06:16 +0000</pubDate>
	<generator>http://wordpress.org/?v=2.2.2</generator>
	<language>en</language>
			<item>
		<title>12.12阅读RSS和Atom Feeds</title>
		<link>http://blog.phpman.info/archives/211</link>
		<comments>http://blog.phpman.info/archives/211#comments</comments>
		<pubDate>Sun, 23 Dec 2007 11:06:16 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/211</guid>
		<description><![CDATA[12.12.1问题
You want to retrieve RSS and Atom feeds and look at the items. This allows you to incorporate newsfeeds from
multiple web sites into your application.
你想要找回RSS和Atom feeds和考虑在这个items. 它允许你合并newsfeeds从多种web sites到你的应用程序
12.12.2解答
Use the MagpieRSS parser. Here&#8217;s an example that reads the RSS feed for the php.announce mailing list:
使用这个MagpieRss 剖析器。这里是一个例子阅读Rss feed到这个php.annouce邮件发送清单

?php
require 'rss_fetch.inc';
$feed = 'http://news.php.net/group.php?group=php.announce&#38;format=rss';
$rss = fetch_rss( $feed );
print "&#60;ul&#62;\n";
foreach ($rss-&#62;items [...]]]></description>
			<content:encoded><![CDATA[<p>12.12.1问题<br />
You want to retrieve RSS and Atom feeds and look at the items. This allows you to incorporate newsfeeds from</p>
<p>multiple web sites into your application.</p>
<p>你想要找回RSS和Atom feeds和考虑在这个items. 它允许你合并newsfeeds从多种web sites到你的应用程序</p>
<p>12.12.2解答<br />
Use the MagpieRSS parser. Here&#8217;s an example that reads the RSS feed for the php.announce mailing list:</p>
<p>使用这个MagpieRss 剖析器。这里是一个例子阅读Rss feed到这个php.annouce邮件发送清单</p>
<p><code><br />
?php<br />
require 'rss_fetch.inc';<br />
$feed = 'http://news.php.net/group.php?group=php.announce&amp;format=rss';<br />
$rss = fetch_rss( $feed );<br />
print "&lt;ul&gt;\n";<br />
foreach ($rss-&gt;items as $item) {<br />
    print '&lt;li&gt;&lt;a href="' . $item['link'] . '"&gt;' . $item['title'] . "&lt;/a&gt;&lt;/li&gt;\n";<br />
}<br />
print "&lt;/ul&gt;\n";<br />
</code></p>
<p>12.12.3讨论</p>
<p>RSS (RDF Site Summary) is an easy-to-use headline or article syndication format written in XML.[] Many news</p>
<p>web sites, such as the New York Times and the Washington Post, provide RSS feeds that update whenever new</p>
<p>stories are published. Weblogs have also embraced RSS and having an RSS feed for your blog is a standard</p>
<p>feature. The PHP web site also publishes RSS feeds for most PHP mailing lists.<br />
RSS(RDF主要摘要)是一个很容易使用和表达syndication 格式在XML.[]很多的新的web sites 。例如纽约时间和华盛顿时间</p>
<p>。规定RSS feeds 修正无论新的存储内容是pubished,博客同样经常使用RSS和蚩尤一个RSS feed在你的bolg是一个标准的特</p>
<p>质。这个PHP web站点同样订阅RSS feeds在更多的PHP mailing lists</p>
<p><code><br />
[] RDF stands for Resource Definition Framework. RSS also stands for Rich Site Summary.<br />
</code></p>
<p>Atom is a similar XML syndication format. It extends many of the concepts in RSS, including a way to read and</p>
<p>write Atom data. It also attempts to provide a more well-defined syntax for syndication than RSS, as the RSS</p>
<p>specification doesn&#8217;t always clearly enumerate exactly what is or isn&#8217;t permissible in a feed.<br />
Atom 是一个相似的XML syndication格式。它延展更多观念到RSS .包括一个办法去阅读和写Atom 数据。它同样尝试规定一</p>
<p>个更多的well-defined语法在syndication比RSS. 当作RSS规范不能明显的列举正确的</p>
<p>Using MagpieRSS, retrieving and parsing RSS and Atom feeds are simple:<br />
使用MagpieRss。找回分解RSS和Atom feeds是简单的</p>
<p><code><br />
?php<br />
$feed = 'http://news.php.net/group.php?group=php.announce&amp;format=rss';<br />
$rss = fetch_rss($feed);<br />
</code></p>
<p>This example reads in the RSS feed for the php.announce mailing list. The feed is then parsed by fetch_rss( )</p>
<p>and stored internally within $rss.<br />
这个例子阅读在这个RSS feed在这个php.announce mailing list 。这个feed是分解fetch_rss()和存储到$rss内</p>
<p>While this feed is RSS 0.93, there&#8217;s no need to specify this to MagpieRSS. Its fetch_rss( ) function detects</p>
<p>the syndication format, including Atom, and formats the document accordingly.<br />
使用这个feed是RSS 0.93 ，它不需要指定这些到MagpieRSS .它的fetch_rss()函数发现这个syndication格式。包括Atom 和</p>
<p>这个格式<br />
Each RSS item is then retrieved as an associative array using the items property:</p>
<p>每个RSS消息重新找回当作一个联合数组使用items 特质<br />
<code><br />
?php<br />
print "&lt;ul&gt;\n";<br />
foreach ($rss-&gt;items as $item) {<br />
    print '&lt;li&gt;&lt;a href="' . $item['link'] . '"&gt;' . $item['title'] . "&lt;/a&gt;&lt;/li&gt;\n";<br />
}<br />
print "&lt;/ul&gt;\n";<br />
</code></p>
<p>This foreach loop creates an unordered list of items with the item title linking back to the URL associated</p>
<p>with the complete article, as shown in Figure 12-1. Besides the required title and link fields, an item can</p>
<p>have an optional description field that contains a brief write-up about the item.<br />
这个foreach循环创造一个无序目录消息在这个item字幕背景到联合URL和全部文章。例如在图像12-1.除此之外必须的标题和</p>
<p>链接域。一个item可以有一个可选择的描写 field包含一个主要write-up这个item</p>
<p>Each channel also has an entry with information about the feed, as shown in Figure 12-2. To retrieve that</p>
<p>data, call access the channel attribute:<br />
每个channel同样有一个入口和这个feed的信息。例如在图像12-2,去重新找回那个数据调用访问这个频道的特质<br />
<code><br />
?php<br />
$feed = 'http://news.php.net/group.php?group=php.announce&amp;format=rss';<br />
$rss = fetch_rss($feed);<br />
print "&lt;ul&gt;\n";<br />
foreach ($rss-&gt;channel as $key =&gt; $value) {<br />
    print "&lt;li&gt;$key: $value&lt;/li&gt;\n";<br />
}<br />
print "&lt;/ul&gt;\n";<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/211/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.11处理编码内容</title>
		<link>http://blog.phpman.info/archives/209</link>
		<comments>http://blog.phpman.info/archives/209#comments</comments>
		<pubDate>Sat, 22 Dec 2007 03:28:44 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/209</guid>
		<description><![CDATA[12.11.1问题
PHP XML extensions use UTF-8, but your data is in a different content encoding.
PHP的XML延展名使用UTF-8。但是你的数据在一个不同的内容编码
12.11.2解答
Use the iconv library to convert it before passing it into an XML extension:
使用这个iconv library去转换它，到一个XML延展名

$utf_8 = iconv('ISO-8859-1', 'UTF-8', $iso_8859_1);

Then convert it back when you are finished:
然后转换它当你完成
12.11.3讨论
Character encoding is a major PHP 5 weakness. Fortunately, Unicode support is the major driver behind PHP [...]]]></description>
			<content:encoded><![CDATA[<p>12.11.1问题<br />
PHP XML extensions use UTF-8, but your data is in a different content encoding.</p>
<p>PHP的XML延展名使用UTF-8。但是你的数据在一个不同的内容编码</p>
<p>12.11.2解答</p>
<p>Use the iconv library to convert it before passing it into an XML extension:</p>
<p>使用这个iconv library去转换它，到一个XML延展名</p>
<p><code><br />
$utf_8 = iconv('ISO-8859-1', 'UTF-8', $iso_8859_1);<br />
</code></p>
<p>Then convert it back when you are finished:<br />
然后转换它当你完成</p>
<p>12.11.3讨论<br />
Character encoding is a major PHP 5 weakness. Fortunately, Unicode support is the major driver behind PHP 6.</p>
<p>Since PHP 6 is still under development, in the meantime, you can run into problems if you&#8217;re trying to use</p>
<p>XML extensions with arbitrary encoded data.</p>
<p>创造编码是PHP5的主要弱点、幸运的是。统一编码支持主驱动器在PHP6.之后。从PHP6之前一直不完善，同时，你可以运行它</p>
<p>的问题如果你尝试去使用XML延展名和任意编码数据</p>
<p>For simplicity, the XML extensions all exclusively use the UTF-8 character encoding. That means they all</p>
<p>expect data in UTF-8 and output all data in UTF-8. If your data is ASCII, then you don&#8217;t need to worry, UTF-8</p>
<p>is a superset of ASCII. However, if you&#8217;re using other encodings, then you will run into trouble sooner or</p>
<p>later.</p>
<p>对于简单的。这个XML延展名所有专用使用这个UTF-8编码。意思是所有的数据在UTF-8输出数据在UTF-8.如果你的数据是</p>
<p>ASCII, 然后你不需要担心。 UTF-8是扩展集，尽管如果你使用其他编码 然后当你运行故障或者更迟<br />
 <br />
To work around this issue, use the iconv extension to manually encode data back and forth between your</p>
<p>character sets and UTF-8. For example, to convert from ISO-8859-1 to UTF-8:</p>
<p>去运行这个issue。 使用这个图标的延长部分手动编辑数据来回鱼你的字符集和UTF-8。例如转换ISO-8859到UTF-8</p>
<p><code><br />
$utf_8 = iconv('ISO-8859-1', 'UTF-8', $iso_8859_1);<br />
</code></p>
<p>The iconv function supports two special modifiers for the destination encoding: //TRANSLIT and //IGNORE. The</p>
<p>first option tells iconv that whenever it cannot exactly duplicate a character in the destination encoding,</p>
<p>it should try to approximate it using a series of other characters. The other option makes iconv silently</p>
<p>ignore any unconvertible characters.</p>
<p>这个图标函数支持两个特殊的修正目的文件的编辑://TRANSLIT和//IGNORE。这第一个选项告诉iconv不能正确的复制一个特</p>
<p>性在目的文件编辑，你应该尝试接近它使用一脸产的其他特质。这个其他选项会默默的忽视一些不能转换的特质</p>
<p>For example, the string $geb holds the text Gödel, Escher, Bach. A straight conversion to ASCII produces an</p>
<p>error:</p>
<p>例如。这个字符串$geb保存这个正文 Gödel,Escher, Bach.，一个整齐的变化到ASCII录制一个错误<br />
<code><br />
echo iconv('UTF-8', 'ASCII', $geb);<br />
PHP Notice:  iconv(): Detected an illegal character in input string...<br />
</code></p>
<p><code><br />
echo iconv('UTF-8', 'ASCII//IGNORE', $geb);<br />
</code><br />
However, the output isn&#8217;t nice, because the ö is missing:</p>
<p>尽管。这个输出不是最精密的。因为这个&#8221;ö&#8221;丢失</p>
<p><code><br />
Gdel, Escher, Bach<br />
</code><br />
The best solution is to use //trANSLIT:</p>
<p>这个最好的解答办法就是使用//trANSLIT</p>
<p><code><br />
echo iconv('UTF-8', 'ASCII//TRANSLIT', $geb);<br />
</code></p>
<p>This produces a better-looking string:</p>
<p>它产生更好的字符串<br />
<code><br />
Gdel, Escher, Bach<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/209/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.10确认XML文件</title>
		<link>http://blog.phpman.info/archives/208</link>
		<comments>http://blog.phpman.info/archives/208#comments</comments>
		<pubDate>Thu, 20 Dec 2007 12:20:45 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/208</guid>
		<description><![CDATA[12.10.1问题
You want to make sure your XML document abides by a schema, such as XML Schema, RelaxNG, and DTDs.
你想要确认你的XML文件坚持一个计划。例如XML计划。RelaxNG.和DTDs
12.10.2解答
Use the DOM extension
使用这个DOM延展名
With existing DOM objects, call DOMDocument::schemaValidate( ) or DOMDocument::relaxNGValidate( ):
使用现有的DOM对象。调用DOMDocument::schemaVlidate()或者DOMDOcument::relaxNGValidate()

$file = 'address-book.xml';
$schema = 'address-book.xsd';
$ab = new DOMDocument
$ab-&#62;load($file);
if ($ab-&#62;schemaValidate($schema)) {
    print "$file is valid.\n";
} else {
    print "$file is invalid.\n";
}

If your XML document specifies a [...]]]></description>
			<content:encoded><![CDATA[<p>12.10.1问题</p>
<p>You want to make sure your XML document abides by a schema, such as XML Schema, RelaxNG, and DTDs.</p>
<p>你想要确认你的XML文件坚持一个计划。例如XML计划。RelaxNG.和DTDs</p>
<p>12.10.2解答</p>
<p>Use the DOM extension<br />
使用这个DOM延展名</p>
<p>With existing DOM objects, call DOMDocument::schemaValidate( ) or DOMDocument::relaxNGValidate( ):</p>
<p>使用现有的DOM对象。调用DOMDocument::schemaVlidate()或者DOMDOcument::relaxNGValidate()</p>
<p><code><br />
$file = 'address-book.xml';<br />
$schema = 'address-book.xsd';<br />
$ab = new DOMDocument<br />
$ab-&gt;load($file);<br />
if ($ab-&gt;schemaValidate($schema)) {<br />
    print "$file is valid.\n";<br />
} else {<br />
    print "$file is invalid.\n";<br />
}<br />
</code></p>
<p>If your XML document specifies a DTD at the top, call DOMDocument::validate( ) to validate it against the DTD.</p>
<p>如果你的XML文件指定一个DTD在这个top、调用DOMDocument::validate()去确认它相反的DTD</p>
<p>With XML in a string, call DOMDocument::schemaValidateSource( ) or DOMDocument::relaxNGValidateSource( ):</p>
<p>然后XML在一个字符串。调用ODMDocument::schemaValidateSource()或者DOMDocument::relaxNGValidateSource()</p>
<p><code><br />
$xml = '&lt;person&gt;&lt;firstname&gt;Adam&lt;/firstname&gt;&lt;/person&gt;';<br />
$schema = 'address-book.xsd';<br />
$ab = new DOMDocument<br />
$ab-&gt;&amp;gt;load($file);<br />
if ($ab-&gt;&amp;gt;schemaValidateSource($schema)) {<br />
    print "XML is valid.\n";<br />
} else {<br />
    print "XML is invalid.\n";<br />
}<br />
</code></p>
<p>12.10.3讨论<br />
Schemas are a way of defining a specification for your XML documents. While the goal is the same, there are multiple</p>
<p>ways to encode a schema, each with a different syntax.</p>
<p>计划是详细定义你的XML文件。当目标是一样的。有多种办法去编辑一个计划，每个不疼痛的语法</p>
<p>Some popular formats are DTDs (Document Type Definitions), XML Schema, and RelaxNG. DTDs have been around longer, but</p>
<p>they are not written in XML and have other issues, so they can be difficult to work with. XML Schema and RelaxNG are</p>
<p>more recent schemas and attempt to solve some of the issues surrounding DTDs.<br />
一些通俗的格式是DTDs(Document Type Definitions)XML Schema 和RelaxNG. DTDs有一个比较久的，但是它不在XML和其他issues.所</p>
<p>以它不同于其他XML</p>
<p>PHP 5 uses the libxml2 library to provide its validation support. Therefore, it lets you validate files against all</p>
<p>three types. It is most flexible when you&#8217;re using XML Schema and RelaxNG, but its XML Schema support is incomplete.</p>
<p>You shouldn&#8217;t run into issues in most XML Schema documents; however, you may find that libxml2 cannot handle some</p>
<p>complex schemas or schemas that use more esoteric features.</p>
<p>PHP5使用这个libxml2库规定确认支持。因此它设置你的有效文件相反于全部的三个类型。它是大部分灵活的，当你使用XML Schema和</p>
<p>RealxNG，但是它XML Schema支持相反的。你需要运行到最多的XML Schema文件。尽管你可能找到那个libxml2不能处理多数复杂的</p>
<p>schemas或者schemas那个使用更多的深奥的features<br />
Within PHP, the DOM extension supports DTD, XML Schema, and RelaxNG validation, while SimpleXML provides only an XML</p>
<p>Schema validator.</p>
<p>使用PHP.这个DOM延展名支持DTD。 XML Schema 和RealxNG确认。使用简单的规定唯一的一个XML Schema有效的</p>
<p>Validating any file using DOM is a similar process, regardless of the underlying schema format. To validate, call a</p>
<p>validation method on a DOM object (see Example 12-21). It returns true if the file passes. If there&#8217;s an error, it</p>
<p>returns false and prints a message to the error log. There is no method for &#8220;capturing&#8221; the error message</p>
<p>确认一些文件使用DOM是一个相似的处理方法，不管下面的schema格式。有效的调用一个有效的方法在一个DOM对象.它返回真实的文件</p>
<p>。如果是一个错误的。它返回错误然后打印出一个信息到这个错误行。它没有办法处理错误信息</p>
<p><code><br />
$file = 'address-book.xml';<br />
$schema = 'address-book.xsd';<br />
$ab = new DOMDocument<br />
$ab-&gt;load($file);<br />
if ($ab-&gt;schemaValidate($schema)) {<br />
    print "$file is valid.\n";<br />
} else {<br />
    print "$file is invalid.\n";<br />
}<br />
</code></p>
<p>If the schema is stored in a string, use DOMDocument::schemaValidateSource( ) instead of schemaValidate( ).</p>
<p>如果这个schema存储在一个字符串。使用DOMDocument::scheemaValidateSource()代替SchemaValidate()</p>
<p>All of the validation methods behave in a similar manner, so you only need to switch the method name in the previous</p>
<p>example to switch to a different validation scheme.<br />
所有的有效方法在某种意义上相似。所以你仅仅需要转换方法命在上一级的菜单例子到一个不同的scheme<br />
Both XML Schema and RelaxNG support validation against files and strings. You can validate a DOM object only against</p>
<p>the DTD defined at the top of the XML document</p>
<p>所有的XML Schema和RllaxNG 支持确认相反的文件和字符串，你可以确认一个DOM对象唯一相反的DTD定义XML文件的顶部</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/208/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.9从XSLT Stylesheets 调用PHP函数</title>
		<link>http://blog.phpman.info/archives/207</link>
		<comments>http://blog.phpman.info/archives/207#comments</comments>
		<pubDate>Wed, 19 Dec 2007 11:28:44 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/207</guid>
		<description><![CDATA[12.9.1问题
You want to call PHP functions from within an XSLT stylesheet.
你想要调用PHP函数从一个XSLT stylesheet
12.9.2解答
Invoke the XSLTProcessor::registerPHPFunctions( ) method to enable this functionality
调用XSLTProcessor::registerPHPFunctions()方法到functionlity

$xslt = new XSLTProcessor();
$xslt-&#62;registerPHPFunctions();

And use the function( ) or functionString( ) function within your stylesheet:
然后使用这个function()或者functionString()函数和你的风格

&#60;xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform&#8221;
    xmlns:php=&#8221;http://php.net/xsl&#8221;
    xsl:extension-element-prefixes=&#8221;php&#8221;&#62;
&#60;xsl:template match=&#8221;/&#8221;&#62;
    &#60;xsl:value-of select=&#8221;php:function(&#8217;strftime&#8217;, &#8216;%c&#8217;)&#8221; /&#62;
&#60;/xsl:template&#62;
&#60;/xsl:stylesheet&#62;

12.9.3讨论
XSLT parameters are great when you need to communicate from PHP to XSLT. [...]]]></description>
			<content:encoded><![CDATA[<p>12.9.1问题<br />
You want to call PHP functions from within an XSLT stylesheet.</p>
<p>你想要调用PHP函数从一个XSLT stylesheet</p>
<p>12.9.2解答<br />
Invoke the XSLTProcessor::registerPHPFunctions( ) method to enable this functionality<br />
调用XSLTProcessor::registerPHPFunctions()方法到functionlity<br />
<code><br />
$xslt = new XSLTProcessor();<br />
$xslt-&gt;registerPHPFunctions();<br />
</code></p>
<p>And use the function( ) or functionString( ) function within your stylesheet:<br />
然后使用这个function()或者functionString()函数和你的风格<br />
<code></p>
<p>&lt;xsl:stylesheet version="1.0"<br />
    xmlns:xsl="<a href="http://www.w3.org/1999/XSL/Transform">http://www.w3.org/1999/XSL/Transform</a>&#8221;<br />
    xmlns:php=&#8221;<a href="http://php.net/xsl">http://php.net/xsl</a>&#8221;<br />
    xsl:extension-element-prefixes=&#8221;php&#8221;&gt;<br />
&lt;xsl:template match=&#8221;/&#8221;&gt;<br />
    &lt;xsl:value-of select=&#8221;php:function(&#8217;strftime&#8217;, &#8216;%c&#8217;)&#8221; /&gt;<br />
&lt;/xsl:template&gt;<br />
&lt;/xsl:stylesheet&gt;<br />
</code></p>
<p>12.9.3讨论<br />
XSLT parameters are great when you need to communicate from PHP to XSLT. However, they&#8217;re not very useful</p>
<p>when you require the reverse. You can&#8217;t use parameters to extract information from the stylesheet during the</p>
<p>transformation. Ideally, you could call PHP functions from a stylesheet and pass information back to PHP.</p>
<p>XSLT参数是重要的。当你需要沟通XSLT。他不是非常有用当你命令这个reverse，你不可以使用选出的信息从stylesheet在这</p>
<p>个转换。完美的。你可以调用PHP函数从一个stylesheet和通过信息到PHP</p>
<p>Fortunately, there&#8217;s a method that implements this functionality: registerPHPFunctions( ). Here&#8217;s how it&#8217;s</p>
<p>enabled:</p>
<p>幸运的。这是一个执行这个函数的方法:regiterPHP函数，当它激活<br />
<code><br />
$xslt = new XSLTProcessor();<br />
$xslt-&gt;registerPHPFunctions();<br />
</code></p>
<p>This allows you to call any PHP function from your stylesheets. It&#8217;s not available by default because it</p>
<p>presents a security risk if you&#8217;re processing stylesheets controlled by other people.<br />
它允许你调用一些PHP函数从你的stylesheets。他不是一个可利用的，因为它出现在危险的。如果你处理限制它</p>
<p>Both built-in and user-defined functions work. Inside your stylesheet, you must define a namespace and call</p>
<p>the function( ) or functionString( ) methods, as shown in Example 12-17.</p>
<p>所有的内置和自定义函数工作。代替你的stylesheet。你必须定义一个名字和调用这个函数()或者fanctionString()方法。</p>
<p>例如在例子12-17<br />
<code><br />
&lt;?xml version="1.0" ?&gt;<br />
&lt;xsl:stylesheet version="1.0"<br />
    xmlns:xsl="<a href="http://www.w3.org/1999/XSL/Transform">http://www.w3.org/1999/XSL/Transform</a>&#8221;<br />
    xmlns:php=&#8221;<a href="http://php.net/xsl">http://php.net/xsl</a>&#8221;<br />
    xsl:extension-element-prefixes=&#8221;php&#8221;&gt;<br />
&lt;xsl:template match=&#8221;/&#8221;&gt;<br />
    &lt;xsl:value-of select=&#8221;php:function(&#8217;strftime&#8217;, &#8216;%c&#8217;)&#8221; /&gt;<br />
&lt;/xsl:template&gt;<br />
&lt;/xsl:stylesheet&gt;<br />
</code><br />
At the top of the stylesheet, define the namespace for PHP: <a href="http://php.net/xsl">http://php.net/xsl</a>. This example sets the</p>
<p>namespace prefix to php. Also, set the extension-element-prefixes value to php so XSLT knows these are</p>
<p>functions.</p>
<p>在stylesheet的顶部。定义PHP的域名：<a href="http://php.net/xsl">http://php.net/xsl</a>.这个例子规定这个前缀是php。设置延展名的元素智到PHP所有</p>
<p>XSLT知道这些函数</p>
<p>To call a PHP function, reference php:function( ). The first parameter is the function name; additional</p>
<p>parameters are the function arguments. In this case, the function name is strftime and the one argument is %</p>
<p>c. This causes strftime to return the current date and time.<br />
去调用一个PHP函数，涉及PHP::function()，这第一个论点是这个函数。另外参数是函数论点，既然这样这个函数名是这个</p>
<p>时间和第一个%c。它导致返回正确的数据和时间<br />
Example 12-18 uses this stylesheet, stored as stylesheet.xsl, to process a single-element XML document<br />
例子12-18使用这个stylesheet。存储在stylesheet,xsl。去存储一个单一的元素XML论点</p>
<p><code><br />
$dom  = new DOMDocument;<br />
$dom-&gt;loadXML('&lt;blank/&gt;');<br />
$xsl  = new DOMDocument<br />
$xsl-&gt;load('stylesheet.xsl');<br />
$xslt = new XSLTProcessor();<br />
$xslt-&gt;importStylesheet($xsl);<br />
$xslt-&gt;registerPHPFunctions();<br />
print $xslt-&gt;transformToXML($dom);<br />
Mon Jul 22 19:10:21 2004<br />
</code></p>
<p>This works like standard XSLT processing, but there&#8217;s an additional call to registerPHPFunctions( ) to</p>
<p>activate PHP function support.</p>
<p>这个工作就像XSLT的标准。但是它是一个复交的调用registerPHPFunctions()激活PHP函数</p>
<p>You can also return DOM objects. Example 12-19 takes the XML address book and mangles all the email addresses</p>
<p>to turn the hostname portion into three dots. Everything else in the document is left untouched.<br />
你同样可以返回DOM对象。例子12-19调用这个XML地址和所有的email地址去转换这个名字的一部分到three格式。每个其他的</p>
<p>在这个文件是为改变的</p>
<p><code><br />
function mangle_email($nodes) {<br />
    return preg_replace('/([^@\s]+)@([-a-z0-9]+\.)+[a-z]{2,}/is',<br />
                        <a href="mailto:'$1@...'">&#8216;$1@&#8230;&#8217;</a>,<br />
                        $nodes[0]-&gt;nodeValue);<br />
}<br />
$dom  = new DOMDocument;<br />
$dom-&gt;load(&#8217;address-book.xml&#8217;);<br />
$xsl  = new DOMDocument<br />
$xsl-&gt;load(&#8217;stylesheet.xsl&#8217;);<br />
$xslt = new XSLTProcessor();<br />
$xslt-&gt;importStylesheet($xsl);<br />
$xslt-&gt;registerPhpFunctions();<br />
print $xslt-&gt;transformToXML($dom);<br />
</code><br />
Inside your stylesheet, create a special template for /address-book/person/email elements, as shown in</p>
<p>Example 12-20.</p>
<p>在你的stylesheet内部，包含一个特殊的模板。对于/address-book/person/email元素。例如在例子12-20<br />
<code><br />
&lt;?xml version="1.0" ?&gt;<br />
&lt;xsl:stylesheet version="1.0"<br />
  xmlns:xsl="<a href="http://www.w3.org/1999/XSL/Transform">http://www.w3.org/1999/XSL/Transform</a>&#8221;<br />
  xmlns:php=&#8221;<a href="http://php.net/xsl">http://php.net/xsl</a>&#8221;<br />
  xsl:extension-element-prefixes=&#8221;php&#8221;&gt;<br />
&lt;xsl:template match=&#8221;@*|node()&#8221;&gt;<br />
  &lt;xsl:copy&gt;<br />
    &lt;xsl:apply-templates select=&#8221;@*|node()&#8221;/&gt;<br />
  &lt;/xsl:copy&gt;<br />
&lt;/xsl:template&gt;<br />
&lt;xsl:template match=&#8221;/address-book/person/email&#8221;&gt;<br />
  &lt;xsl:copy&gt;<br />
    &lt;xsl:value-of select=&#8221;php:function(&#8217;mangle_email&#8217;, node())&#8221; /&gt;<br />
  &lt;/xsl:copy&gt;<br />
&lt;/xsl:template&gt;<br />
&lt;/xsl:stylesheet&gt;<br />
</code></p>
<p>The first template ensures that the elements aren&#8217;t modified, while the second passes the current node to PHP</p>
<p>for mangling. In the second template, the mangle_email( ) function is passed the current node, represented in</p>
<p>XPath as node( ), instead of a string. Be sure not to place the node inside quotation marks, or you&#8217;ll pass</p>
<p>the literal text node( ).</p>
<p>这第一个模板确保这个元素不能修改。当这第二个通用正确的网点到PHP。在第二个模板这个mangle_email()函数通过这个正</p>
<p>确的网点。表现在XPath当作node()。代替一个字符串、确认网点在引号内。。或者你通过文字正文<br />
Nodes becomes DOM objects inside PHP and always arrive in an array. In this case, mangle_email( ) knows</p>
<p>there&#8217;s always only one object and it&#8217;s a DOMText object, so the email address is located in $nodes[0]-</p>
<p>&gt;nodeValue.</p>
<p>网点变成DOM对象代替PHP和总是到达一个数组。既然这样，mangle_email()知道这个总是唯一的对象和DOMText对象，所有这</p>
<p>个email地址在$nodes[0]-&gt;nodeVlue</p>
<p>When you know that you&#8217;re only interested in the text portion of a node, use the functionString( ) function.</p>
<p>This function converts nodes to PHP strings, which allows you to omit the array access and nodeValue</p>
<p>dereference:</p>
<p>当你知道唯一的在正文部分的一个网点。使用这个functionString(()函数，这个函数转换nodes到PHP字符串。那个允许你忽</p>
<p>略数组的访问和nodeValue参照</p>
<p><code><br />
function mangle_email($email) {<br />
    return preg_replace('/([^@\s]+)@([-a-z0-9]+\.)+[a-z]{2,}/is',<br />
                        <a href="mailto:'$1@...'">&#8216;$1@&#8230;&#8217;</a>,<br />
                        $email);<br />
}<br />
// all other code is the same as before<br />
</code></p>
<p>The new stylesheet template for /address-book/person/email is:<br />
这个新的stylesheet模板对于/address-book/person/email是<br />
<code><br />
&lt;xsl:template match="/address-book/person/email"&gt;<br />
  &lt;xsl:copy&gt;<br />
    &lt;xsl:value-of<br />
       select="php:functionString('mangle_email', node())" /&gt;<br />
  &lt;/xsl:copy&gt;<br />
&lt;/xsl:template&gt;<br />
</code></p>
<p>The mangle_email( ) function now processes $email instead of $nodes[0]-&gt;nodeValue because the template now</p>
<p>calls the functionString( ) function.</p>
<p>这个mangle_email()函数处理$email代替$nodes[0]-&gt;nodeValue因为这个模板调用functionString()函数<br />
 </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/207/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.8设置XSLT参数从PHP中</title>
		<link>http://blog.phpman.info/archives/205</link>
		<comments>http://blog.phpman.info/archives/205#comments</comments>
		<pubDate>Mon, 17 Dec 2007 10:38:36 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/205</guid>
		<description><![CDATA[12.8.1问题
You want to set parameters in your XSLT stylesheet from PHP.
你想要设置你的XSLT参数从PHP中
12.8.2解答
Use the XSLTProcessor::setParameter( ) method:
使用这个XSLTProcessor::setParameter()方法

// This could also come from $_GET['city'];
$city = 'San Francisco';
$dom  = new DOMDocument
$dom-&#62;load('address-book.xml');
$xsl  = new DOMDocument
$xsl-&#62;load('stylesheet.xsl');
$xslt = new XSLTProcessor();
$xslt-&#62;importStylesheet($xsl);
$xslt-&#62;setParameter(NULL, 'city', $city);
print $xslt-&#62;transformToXML($dom);

This code sets the XSLT city parameter to the value stored in the PHP variable $city.
这个代码设置XSLT参数到这个存储数值在PHP的变量$city
12.8.3讨论
You can pass data from [...]]]></description>
			<content:encoded><![CDATA[<p>12.8.1问题</p>
<p>You want to set parameters in your XSLT stylesheet from PHP.</p>
<p>你想要设置你的XSLT参数从PHP中</p>
<p>12.8.2解答<br />
Use the XSLTProcessor::setParameter( ) method:</p>
<p>使用这个XSLTProcessor::setParameter()方法<br />
<code><br />
// This could also come from $_GET['city'];<br />
$city = 'San Francisco';<br />
$dom  = new DOMDocument<br />
$dom-&gt;load('address-book.xml');<br />
$xsl  = new DOMDocument<br />
$xsl-&gt;load('stylesheet.xsl');<br />
$xslt = new XSLTProcessor();<br />
$xslt-&gt;importStylesheet($xsl);<br />
$xslt-&gt;setParameter(NULL, 'city', $city);<br />
print $xslt-&gt;transformToXML($dom);<br />
</code></p>
<p>This code sets the XSLT city parameter to the value stored in the PHP variable $city.</p>
<p>这个代码设置XSLT参数到这个存储数值在PHP的变量$city</p>
<p>12.8.3讨论<br />
You can pass data from PHP into your XSLT stylesheet with the setParameter( ) method. This allows you to do</p>
<p>things such as filter data in your stylesheet based on user input.</p>
<p>你可以通过PHP到你的XSLT类型和这个setParameter()方法、它允许你例如过滤数据到你的stylesheet早使用者的输出</p>
<p>For example, the program in Example 12-16 allows you to find people based on their city.<br />
例如。这个程序在例子12-16允许你去寻找people在他们的city</p>
<p><code><br />
// This could also come from $_GET['city'];<br />
$city = 'San Francisco';<br />
$dom  = new DOMDocument<br />
$dom-&gt;load('address-book.xml');<br />
$xsl  = new DOMDocument<br />
$xsl-&gt;load('stylesheet.xsl');<br />
$xslt = new XSLTProcessor();<br />
$xslt-&gt;importStylesheet($xsl);<br />
$xslt-&gt;setParameter(NULL, 'city', $city);<br />
print $xslt-&gt;transformToXML($dom);<br />
</code><br />
The program uses the following stylesheet:</p>
<p>这个程序使用下列stylesheet<br />
<code><br />
&lt;?xml version="1.0" ?&gt;<br />
&lt;xsl:stylesheet version="1.0"<br />
  xmlns:xsl="<a href="http://www.w3.org/1999/XSL/Transform">http://www.w3.org/1999/XSL/Transform</a>&#8220;&gt;<br />
&lt;xsl:template match=&#8221;@*|node()&#8221;&gt;<br />
  &lt;xsl:copy&gt;<br />
    &lt;xsl:apply-templates select=&#8221;@*|node()&#8221;/&gt;<br />
  &lt;/xsl:copy&gt;<br />
&lt;/xsl:template&gt;<br />
&lt;xsl:template match=&#8221;/address-book/person&#8221;&gt;<br />
  &lt;xsl:if test=&#8221;city=$city&#8221;&gt;<br />
    &lt;xsl:copy&gt;<br />
      &lt;xsl:apply-templates select=&#8221;@*|node()&#8221;/&gt;<br />
    &lt;/xsl:copy&gt;<br />
  &lt;/xsl:if&gt;<br />
&lt;/xsl:template&gt;<br />
&lt;/xsl:stylesheet&gt;<br />
</code><br />
The program and stylesheet combine to produce the following results:</p>
<p>这个程序和stylesheet联合录制下列结果<br />
&lt;code&gt;<br />
&lt;?xml version=&#8221;1.0&#8243;?&gt;<br />
&lt;address-book&gt;<br />
    &lt;person id=&#8221;2&#8243;&gt;<br />
        &lt;!&#8211;Adam Trachtenberg&#8211;&gt;<br />
        &lt;firstname&gt;Adam&lt;/firstname&gt;<br />
        &lt;lastname&gt;Trachtenberg&lt;/lastname&gt;<br />
        &lt;city&gt;San Francisco&lt;/city&gt;<br />
        &lt;state&gt;CA&lt;/state&gt;<br />
        &lt;email&gt;amt@php.net&lt;/email&gt;<br />
    &lt;/person&gt;<br />
&lt;/address-book&gt;<br />
</code></p>
<p>The PHP script does a standard XSLT transformation, except that it calls $xslt-&gt;setParameter(NULL, &#8216;city&#8217;,</p>
<p>$city). The first argument is the parameter&#8217;s namespace, the second is the parameter&#8217;s name, and the third is</p>
<p>the parameter&#8217;s value.</p>
<p>这个PHP原本是一个标准XSLT转换。除了它调用$xslt-&gt;setParameter(NULL.&#8217;city&#8217;.$city)这第一个论点是这个参数。这第二</p>
<p>个论点是名字。第三个是参数的值</p>
<p>Here, the value stored in the PHP variable $city&#8217;in this case, San Francisco&#8217;is assigned to the XSLT</p>
<p>parameter city, which does not live under a namespace. This is equal to placing the following in an XSLT</p>
<p>file:</p>
<p>这里。这个数值存储在PHP变量$city。San Francisco的分配到这个XSLT参数city。哪个不能在一个名字下面。他们<br />
相等于下列一个XSLT文件<br />
<code><br />
&lt;xsl:param name="city"&gt;San Francisco&lt;/xsl:param&gt;<br />
</code><br />
You usually access a parameter inside a stylesheet like you do a PHP variable, by placing a dollar sign ($)</p>
<p>in front of its name. The stylesheet example creates a template that matches /address-book/person nodes.<br />
你经常访问一个参数在一个内部。像你的一个PHP变量在变量前面加一个$.这个stylesheet例子创造一个模块匹配网点</p>
<p>Inside the template, you test whether city=$city; in other words, is the city child of the current node equal</p>
<p>to the value of the city parameter? If there&#8217;s a match, the children are copied along; otherwise, the records</p>
<p>are eliminated.<br />
在这个模板内部。你测试city=$city。换句话说。在这个city类相等的数值city 惨呼。如果匹配。这个子类将复制。另外。</p>
<p>记录将消除</p>
<p>In this case, city is set to San Francisco, so David&#8217;s record is removed and Adam&#8217;s remains.</p>
<p>既然这样。city到San Francisco、所以David的记录远离remains</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/205/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.7转换XML为XSLT</title>
		<link>http://blog.phpman.info/archives/204</link>
		<comments>http://blog.phpman.info/archives/204#comments</comments>
		<pubDate>Sun, 16 Dec 2007 11:13:01 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/204</guid>
		<description><![CDATA[12.7.1问题
You have an XML document and an XSL stylesheet. You want to transform the document using XSLT and capture the
results. This lets you apply stylesheets to your data and create different versions of your content for
different media.
你有一个XML文件和一个XSL stylesheet， 你想要转换文件使用XSLT和capure这个结果。它将你应用你的数据和创造不同的
版本在不同的媒体
12.7.2解答
Use PHP&#8217;s XSLT extension
使用PHP的XSLT延展名

// Load XSL template
$xsl = newDOMDocument;
$xsl-&#62;load('stylesheet.xsl');
// Create new XSLTProcessor
$xslt = new XSLTProcessor();
// Load stylesheet
$xslt-&#62;importStylesheet($xsl);
// [...]]]></description>
			<content:encoded><![CDATA[<p>12.7.1问题</p>
<p>You have an XML document and an XSL stylesheet. You want to transform the document using XSLT and capture the</p>
<p>results. This lets you apply stylesheets to your data and create different versions of your content for</p>
<p>different media.</p>
<p>你有一个XML文件和一个XSL stylesheet， 你想要转换文件使用XSLT和capure这个结果。它将你应用你的数据和创造不同的</p>
<p>版本在不同的媒体</p>
<p>12.7.2解答<br />
Use PHP&#8217;s XSLT extension<br />
使用PHP的XSLT延展名</p>
<p><code><br />
// Load XSL template<br />
$xsl = newDOMDocument;<br />
$xsl-&gt;load('stylesheet.xsl');<br />
// Create new XSLTProcessor<br />
$xslt = new XSLTProcessor();<br />
// Load stylesheet<br />
$xslt-&gt;importStylesheet($xsl);<br />
// Load XML input file<br />
$xml = new DOMDocument;<br />
$xml-&gt;load('data.xml');<br />
// Transform to string<br />
$results = $xslt-&gt;transformToXML($xml);<br />
// Transform to a file<br />
$results = $xslt-&gt;transformToURI($xml, 'results.txt');<br />
// Transform to DOM object<br />
$results = $xslt-&gt;transformToDoc($xml);<br />
</code><br />
The transformed text is stored in $results<br />
这个转换正文存储在$results</p>
<p>12.7.3讨论</p>
<p>XML documents describe the content of data, but they don&#8217;t contain any information about how that data should</p>
<p>be displayed. However, when XML content is coupled with a stylesheet described using XSL (eXtensible</p>
<p>Stylesheet Language), the content is displayed according to specific visual rules.</p>
<p>XML文件描述这个数据的内容。但是它不能包含一些必须显示的数据。当XML内容联合一个描述使用XSL、这个内容显示依照特</p>
<p>殊的规则</p>
<p>The glue between XML and XSL is XSLT (eXtensible Stylesheet Language Transformations). These transformations</p>
<p>apply the series of rules enumerated in the stylesheet to your XML data. So just as PHP parses your code and</p>
<p>combines it with user input to create a dynamic page, an XSLT program uses XSL and XML to output a new page</p>
<p>that contains more XML, HTML, or any other format you can describe<br />
结合XML和XSL是XSLT这些转换应用列举规则在这你的XML数据风格，所以如果你的PHP分列你的代码和结合到使用者输出创造</p>
<p>一个动态页面。一个XSLT程序使用XSL和XML去输出一个新的页面包含更多的XML.HTML或者一些其他的格式</p>
<p>There are a few XSLT programs available, each with different features and limitations. PHP 5 supports only</p>
<p>the libxslt processor. This is a different processor than PHP 4 used<br />
这是一个少量的XSLT程序变量。每个不同的的特质和限制，PHP5支持唯一的libxslt处理它是一个不同的处理跟PHP4相比<br />
Using XSLT in PHP 5 involves two main steps: preparing the XSLT object and then triggering the actual</p>
<p>transformation for each XML file.</p>
<p>使用XSLT在PHP5包括两个主要的：准备XSLT对象和控制真正的变化到每个XML文件</p>
<p><code><br />
// Load XSL template<br />
$xsl = newDOMDocument;<br />
$xsl-&gt;load('stylesheet.xsl');<br />
// Create new XSLTProcessor<br />
$xslt = new XSLTProcessor();<br />
// Load stylesheet<br />
$xslt-&gt;importStylesheet($xsl);<br />
</code><br />
Now the transformer is up and running. You can transform any DOM object in one of three ways: into a string,</p>
<p>into a file, or back into another DOM object, as shown in Example 12-15.</p>
<p>现在这个变化的运动、你可以转换DOM对象在第三个路线、在一个字符串内的一个文件或者其他DOM对象。例如在例子12-15<br />
<code><br />
// Load XML input file<br />
$xml = new DOMDocument;<br />
$xml-&gt;load('data.xml');<br />
// Transform to string<br />
$results = $xslt-&gt;transformToXML($xml);<br />
// Transform to a file<br />
$results = $xslt-&gt;transformToURI($xml, 'results.txt');<br />
// Transform to DOM object<br />
$results = $xslt-&gt;transformToDoc($xml);<br />
</code></p>
<p>When you call transformToXML( ) or transformToDoc( ), the extension returns the result string or object. In</p>
<p>contrast, transformToURI( ) returns the number of bytes written to the file, not the actual document.</p>
<p>当你调用transformToXML()或者transformToDoc()。这个延展名返回字符串结果或者对象对比transformtourl()返回这个<br />
字节数字、不是真是的文件<br />
 </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/204/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.6提取信息使用XPath</title>
		<link>http://blog.phpman.info/archives/203</link>
		<comments>http://blog.phpman.info/archives/203#comments</comments>
		<pubDate>Sat, 15 Dec 2007 11:43:47 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/203</guid>
		<description><![CDATA[12.6.1问题
You want to make sophisticated queries of your XML data without parsing the document node by node.
你想要制造一个查询在你的XML数据和分解这个文件网点
12.6.2解答
Use XPath.
使用XPath
XPath is available in SimpleXML:
XPath是简单的可利用的

?php
$s = simplexml_load_file('address-book.xml');
$emails = $s-&#62;xpath('/address-book/person/email');
foreach ($emails as $email) {
    // do something with $email
}

And in DOM:
然后在DOM

?php
$dom = new DOMDocument;
$dom-&#62;load('address-book.xml');
$xpath = new DOMXPath($dom);
$email = $xpath-&#62;query('/address-book/person/email');
foreach ($emails as $email) {
    // do something with $email
}

12.6.3讨论
Except for [...]]]></description>
			<content:encoded><![CDATA[<p>12.6.1问题<br />
You want to make sophisticated queries of your XML data without parsing the document node by node.</p>
<p>你想要制造一个查询在你的XML数据和分解这个文件网点</p>
<p>12.6.2解答</p>
<p>Use XPath.<br />
使用XPath<br />
XPath is available in SimpleXML:<br />
XPath是简单的可利用的<br />
<code><br />
?php<br />
$s = simplexml_load_file('address-book.xml');<br />
$emails = $s-&gt;xpath('/address-book/person/email');<br />
foreach ($emails as $email) {<br />
    // do something with $email<br />
}<br />
</code><br />
And in DOM:</p>
<p>然后在DOM<br />
<code><br />
?php<br />
$dom = new DOMDocument;<br />
$dom-&gt;load('address-book.xml');<br />
$xpath = new DOMXPath($dom);<br />
$email = $xpath-&gt;query('/address-book/person/email');<br />
foreach ($emails as $email) {<br />
    // do something with $email<br />
}<br />
</code><br />
12.6.3讨论<br />
Except for the simplest documents, it&#8217;s rarely easy to access the data you want one element at a time. As your XML files become increasingly complex and your parsing desires grow, using XPath is easier than filtering the data inside a foreach.</p>
<p>除了简单的文件。它很容易去访问这个数据在你想要的一个元素。当作你的XML文件变成复杂的和你的分解要求生成。使用XPath是更加简单的过滤数据在一个foreach</p>
<p>PHP has an XPath class that takes a DOM object as its constructor. You can then search the object and receive DOM nodes in reply. SimpleXML also supports XPath, and it&#8217;s easier to use because it&#8217;s integrated into the SimpleXML object.</p>
<p>PHP有一个XPath类有一个DOM对象当作构造器。你可以搜索这个对象和接受DOM网点在这个回复。SimpleXML同样支持Xpath.然后容易使用因为它统一到一个SimpleXML对象<br />
DOM supports XPath queries, but you do not perform the query directly on the DOM object itself. Instead, you create a DOMXPath object, as shown in Example 12-9.</p>
<p>DOM支持XPath查询。但是它不直接履行查询，例如在例子12-9<br />
<code><br />
$dom = new DOMDocument;<br />
$dom-&gt;load('address-book.xml');<br />
$xpath = new DOMXPath($dom);<br />
$email = $xpath-&gt;query('/address-book/person/email');<br />
</code><br />
Instantiate DOMXPath by passing in a DOMDocument to the constructor. To execute the XPath query, call query( ) with the query text as your argument. This returns an iterable DOM node list of matching nodes (see Example 12-10).<br />
例示DOMPath通过在一个DOMDocument 到这个构造器，去执行这个XPath查询。调用query()和query正文当作你的论点。它返回一个iterable DOM网点，看例子12-10</p>
<p>Using XPath with DOM in a basic example<br />
<code><br />
$dom = new DOMDocument;<br />
$dom-&gt;load('address-book.xml');<br />
$xpath = new DOMXPath($dom);<br />
$emails = $xpath-&gt;query('/address-book/person/email');<br />
foreach ($emails as $e) {<br />
    $email = $e-&gt;firstChild-&gt;nodeValue;<br />
    // do something with $email<br />
}<br />
</code><br />
After creating a new DOMXPath object, query this object using DOMXPath::query( ), passing the XPath query as the first parameter (in this example, it&#8217;s /people/person/email). This function returns a node list of matching DOM nodes.<br />
经过创造一个新的DOMXPath对象。查询这个对象使用DOMPath::query()。通过这个XPath query当作第一个参数<br />
By default, DOMXPath::query( ) operates on the entire XML document. Search a subsection of the tree by passing in the subtree as a final parameter to query( ). For instance, to gather all the first and last names of people in the address book, retrieve all the people nodes and query each node individually, as shown in Example 12-11.</p>
<p>定义DOMXPath::query()操作在全部的XML文件。搜索一个分段的tree通过子树当作一个最后的参数到query()，例如集合所有的第一个和最后一个名字在这个住址名册。找回所有的people网点和查询每个个别的node,例如在例子12-11<br />
<code><br />
$dom = new DOMDocument;<br />
$dom-&gt;load('address-book.xml');<br />
$xpath = new DOMXPath($dom);<br />
$person = $xpath-&gt;query('/address-book/person');<br />
foreach ($person as $p) {<br />
    $fn = $xpath-&gt;query('firstname', $p);<br />
    $firstname = $fn-&gt;item(0)-&gt;firstChild-&gt;nodeValue;<br />
    $ln = $xpath-&gt;query('lastname', $p);<br />
    $lastname = $ln-&gt;item(0)-&gt;firstChild-&gt;nodeValue;<br />
    print "$firstname $lastname\n";<br />
}<br />
David Sklar<br />
Adam Trachtenberg<br />
</code><br />
Inside the foreach, call DOMXPath::query( ) to retrieve the firstname and lastname nodes. Now, in addition to the XPath query, also pass $p to the method. This makes the search local to the node.</p>
<p>在foreach内部，调用DOMXPath::query()重新找回第一个名和最后一个名nodes，现在在除了XPath查询。同样通过$p到这个方法。它确定搜索本地node</p>
<p>In contrast to DOM, all SimpleXML objects have an integrated xpath( ) method. Calling this method queries the current object using XPath and returns a SimpleXML object containing the matching nodes, so you don&#8217;t need to instantiate another object to use XPath. The method&#8217;s one argument is your XPath query.<br />
和DOM对比。所有的SimpleXML对象有一个综合的xpath()方法。调用这个方法查询这个正确的对象使用XPath和返回一个SimoleXML对象包含匹配的nodes。所以你不需要例示其他对象使用XPath。这个方法的一个论点是你的XPath查询<br />
Use Example 12-12 to find all the matching email addresses in the sample address book.</p>
<p>使用例子12-12去寻找所有的匹配email地址。在这个住址名册<br />
<code><br />
$s = simplexml_load_file('address-book.xml');<br />
$emails = $s-&gt;xpath('/address-book/person/email');<br />
foreach ($emails as $email) {<br />
    // do something with $email<br />
}<br />
</code><br />
This is shorter because there&#8217;s no need to dereference the firstNode or to take the nodeValue.</p>
<p>这个是简短的。因为它不需要废弃第一个站点或者获得价值</p>
<p>SimpleXML handles the more complicated example, too. Since xpath( ) returns SimpleXML objects, you can query them directly, as in Example 12-13.</p>
<p>SimpleXML也有很多复杂的例子。从xpath()返回Simple对象。你可以直接查询，例如在例子12-13</p>
<p><code><br />
$s = simplexml_load_file('address-book.xml');<br />
$people = $s-&gt;xpath('/address-book/person');<br />
foreach($people as $p) {<br />
    list($firstname) = $p-&gt;xpath('firstname');<br />
    list($lastname) = $p-&gt;xpath('lastname');<br />
    print "$firstname $lastname\n";<br />
}<br />
David Sklar<br />
Adam Trachtenberg<br />
</code></p>
<p>Since the inner XPath queries return only one element, use list to grab it from the array.</p>
<p>从这个内部的XPath查询返回唯一的元素。使用目录夺取它的数组</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/203/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.5分解巨大的XML文件</title>
		<link>http://blog.phpman.info/archives/202</link>
		<comments>http://blog.phpman.info/archives/202#comments</comments>
		<pubDate>Fri, 14 Dec 2007 11:08:49 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/202</guid>
		<description><![CDATA[12.5.1问题
You want to parse a large XML document. This document is so large that it&#8217;s impractical to use SimpleXML or DOM because you cannot hold the entire document in memory. Instead, you must load the document in one section at a time.
你想要分解一个巨大的XML文件。这个文件是非常大、不切实际的使用SimpleXML或者DOM.因为你不希望全部的文件在memory。代替。你必须装在文件在一个部分
12.5.2解答
Use the XMLReader extension:
使用这个XMLReader延长名

?php
$reader = new XMLReader();
$reader-&#62;open('card-catalog.xml');
/* Loop through document */
while ($reader-&#62;read()) {
    /* [...]]]></description>
			<content:encoded><![CDATA[<p>12.5.1问题<br />
You want to parse a large XML document. This document is so large that it&#8217;s impractical to use SimpleXML or DOM because you cannot hold the entire document in memory. Instead, you must load the document in one section at a time.</p>
<p>你想要分解一个巨大的XML文件。这个文件是非常大、不切实际的使用SimpleXML或者DOM.因为你不希望全部的文件在memory。代替。你必须装在文件在一个部分</p>
<p>12.5.2解答<br />
Use the XMLReader extension:</p>
<p>使用这个XMLReader延长名</p>
<p><code><br />
?php<br />
$reader = new XMLReader();<br />
$reader-&gt;open('card-catalog.xml');<br />
/* Loop through document */<br />
while ($reader-&gt;read()) {<br />
    /* If you're at an element named 'author' */<br />
    if ($reader-&gt;nodeType == XMLREADER::ELEMENT &amp;&amp; $reader-&gt;localName == 'author') {<br />
        /* Move to the text node and print it out */<br />
        $reader-&gt;read();<br />
        print $reader-&gt;value . "\n";<br />
    }<br />
}<br />
</code><br />
There are two major types of XML parsers: ones that hold the entire document in memory at once, and ones that hold only a small portion of the document in memory at any given time.</p>
<p>这是两个主要的XML剖析器类型、一个把握全部的文件在merory,然后一个希望唯一的小的一部分文件在memory在一些时间</p>
<p>The first kind are called tree-based parsers, since they store the document into a data structure known as a tree. The SimpleXML and DOM extensions, from Recipes 12.3 and 12.4, are tree-based parsers. Using a tree-based parser is easier for you, but requires PHP to use more RAM. With most XML documents, this isn&#8217;t a problem. However, when your XML document is quite large, then this can cause major performance issues.</p>
<p>这第一个调用tree-based的剖析器、从它们存储文件到一个数据结构是一个tree。这个SimpleXML和DOM扩展名从第12.3和12.4和tree-based剖析器对于你来说容易的。但是命令PHP去使用更多的RAM。和更多的XML文件。他不是一个问题。经当你的XML文件非常大。然后它导致主要的问题<br />
The other kind of XML parser is a stream-based parser. Stream-based parsers don&#8217;t store the entire document in memory; instead, they read in one node at a time and allow you to interact with it in real time. Once you move onto the next node, the old one is thrown away&#8217;unless you explicitly store it yourself for later use. This makes stream-based parsers faster and less memory consuming, but you may have to write more code to process the document.<br />
这个其他类型的XML剖析器是一个stream-based </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/202/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.4分析复杂的XML文件</title>
		<link>http://blog.phpman.info/archives/201</link>
		<comments>http://blog.phpman.info/archives/201#comments</comments>
		<pubDate>Thu, 13 Dec 2007 08:29:50 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/201</guid>
		<description><![CDATA[12.4.1问题
You have a complex XML document, such as one where you need to introspect the document to determine its
schema, or you need to use more esoteric XML features, such as processing instructions or comments.
你有一个复杂的XML文件。例如在你需要的内部文件去测定它的计划。或者你需要使用很多深奥的XML性质。例如处理指示或者
注释
12.4.2解答
Use the DOM extension. It provides a complete interface to all aspects of the XML specification
使用这个DOM延展名。它规定一个完整的界面到所有XML规范

?php
$dom = new DOMDocument;
$dom-&#62;load('address-book.xml');
foreach ($dom-&#62;getElementsByTagname('person') as $person) [...]]]></description>
			<content:encoded><![CDATA[<p>12.4.1问题<br />
You have a complex XML document, such as one where you need to introspect the document to determine its</p>
<p>schema, or you need to use more esoteric XML features, such as processing instructions or comments.</p>
<p>你有一个复杂的XML文件。例如在你需要的内部文件去测定它的计划。或者你需要使用很多深奥的XML性质。例如处理指示或者</p>
<p>注释</p>
<p>12.4.2解答</p>
<p>Use the DOM extension. It provides a complete interface to all aspects of the XML specification<br />
使用这个DOM延展名。它规定一个完整的界面到所有XML规范</p>
<p><code><br />
?php<br />
$dom = new DOMDocument;<br />
$dom-&gt;load('address-book.xml');<br />
foreach ($dom-&gt;getElementsByTagname('person') as $person) {<br />
    $firstname = $person-&gt;getElementsByTagname('firstname');<br />
    $firstname_text_value = $firstname-&gt;item(0)-&gt;firstChild-&gt;nodeValue;<br />
    $lastname = $person-&gt;getElementsByTagname('lastname');<br />
    $lastname_text_value = $lastname-&gt;item(0)-&gt;firstChild-&gt;nodeValue;<br />
    print "$firstname_text_value $lastname_text_value\n";<br />
}<br />
David Sklar<br />
Adam Trachtenberg<br />
</code></p>
<p>12.4.3讨论<br />
The W3C&#8217;s DOM provides a platform- and language-neutral method that specifies the structure and content of a</p>
<p>document. Using the DOM, you can read an XML document into a tree of nodes and then maneuver through the tree</p>
<p>to locate information about a particular element or elements that match your criteria. This is called tree-</p>
<p>based parsing.<br />
这个W3C&#8217;s DOM规定一个platform-和language-neutral 方法指定结构和内容的文件，使用这个DOM.你可以阅读一个XML文件到</p>
<p>一个tree站点然后机动穿过tree的站点信息的一个特殊元素或者元素匹配你的标准。它调用tree-based分解<br />
 <br />
Additionally, you can modify the structure by creating, editing, and deleting nodes. In fact, you can use the</p>
<p>DOM functions to author a new XML document from scratch; see Recipe 12.2.<br />
另外、你可以修改结构创造。编辑和删除网点、事实上，你可以使用DOM函数去创造一个新的XML文件从新开始，看12.2 <br />
One of the major advantages of the DOM is that by following the W3C&#8217;s specification, many languages implement</p>
<p>DOM functions in a similar manner. Therefore, the work of translating logic and instructions from one</p>
<p>application to another is considerably simplified. PHP 5 comes with a new series of DOM methods that are in</p>
<p>stricter compliance with the DOM standard than previous versions of PHP.<br />
一个有主要优势的DOM文件跟随这个W3C&#8217;s详述。很多语言执行DOM函数在某种意义上相似因此、这个工作翻译逻辑和指示从一</p>
<p>个应用到另一个相当的PHP5伴随一个新增序列的DOM方法是一个严格的DOM标准 <br />
The DOM is large and complex. For more information, read the specification at <a href="http://www.w3.org/DOM/">http://www.w3.org/DOM/</a> or pick</p>
<p>up a copy of XML in a Nutshell.<br />
这个DOM是巨大的复杂。例如信息。阅读详细的在<a href="http://www.w3.org/DOM">http://www.w3.org/DOM</a>或者精选一份XML</p>
<p>DOM functions in PHP are object oriented. To move from one node to another, access properties such as $node-</p>
<p>&gt;childNodes, which contains an array of node objects, and $node-&gt;parentNode, which contains the parent node</p>
<p>object. Therefore, to process a node, check its type and call a corresponding method, as shown in Example 12-</p>
<p>5.<br />
DOM函数在PHP的对象倒像、去移动一个网点到其他访问道具例如$node-&gt;childNodes。哪个包含一个数组站点对象。和$node-</p>
<p>&gt;parentNOde。哪个包含亲代交点。因此。处理一个node。组织它的类型和调用一个相应的方法，例如在例子12&#8211;5</p>
<p>Parsing a DOM object<br />
<code><br />
?php<br />
// $node is the DOM parsed node &lt;book cover="soft"&gt;PHP Cookbook&lt;/book&gt;<br />
$type = $node-&gt;nodeType; <br />
switch($type) {<br />
case XML_ELEMENT_NODE:<br />
    // I'm a tag. I have a tagname property.<br />
    print $node-&gt;tagName;  // prints the tagname property: "book"<br />
    break;<br />
case XML_ATTRIBUTE_NODE:<br />
    // I'm an attribute. I have a name and a value property.<br />
    print $node-&gt;name;  // prints the name property: "cover"<br />
    print $node-&gt;value; // prints the value property: "soft"<br />
    break;<br />
case XML_TEXT_NODE:<br />
    // I'm a piece of text inside an element.<br />
    // I have a name and a content property.<br />
    print $node-&gt;nodeName;  // prints the name property: "#text"<br />
    print $node-&gt;nodeValue; // prints the text content: "PHP Cookbook"<br />
    break;<br />
default:<br />
    // another type<br />
    break;<br />
}<br />
</code><br />
To automatically search through a DOM tree for specific elements, use getElementsByTagname( ). Example 12-6</p>
<p>shows how to do so with multiple book records.<br />
自动的搜索一个DOM tree对于特殊的元素、使用getElementByTagname()。例如12-6显示怎么去多多样的账面记录<br />
<code><br />
Card catalog in XML<br />
&lt;books&gt;<br />
    &lt;book&gt;<br />
        &lt;title&gt;PHP Cookbook&lt;/title&gt;<br />
        &lt;author&gt;Sklar&lt;/author&gt;<br />
        &lt;author&gt;Trachtenberg&lt;/author&gt;<br />
        &lt;subject&gt;PHP&lt;/subject&gt;<br />
    &lt;/book&gt;<br />
    &lt;book&gt;<br />
        &lt;title&gt;Perl Cookbook&lt;/title&gt;<br />
        &lt;author&gt;Christiansen&lt;/author&gt;<br />
        &lt;author&gt;Torkington&lt;/author&gt;<br />
        &lt;subject&gt;Perl&lt;/subject&gt;<br />
    &lt;/book&gt;<br />
&lt;/books&gt;<br />
</code><br />
Example 12-7 shows how to find all authors.<br />
例子12-7显示怎么去找到所有的作者<br />
<code><br />
Printing all authors using DOM<br />
// find and print all authors<br />
$authors = $dom-&gt;getElementsByTagname('author');<br />
// loop through author elements<br />
foreach ($authors as $author) {<br />
    // childNodes holds the author values<br />
    $text_nodes = $author-&gt;childNodes;<br />
    foreach ($text_nodes as $text) {<br />
         print $text-&gt;nodeValue . "\n";<br />
    }<br />
}<br />
Sklar<br />
Trachte nberg<br />
Christiansen<br />
Torkington<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/201/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.2在DOM产生XML</title>
		<link>http://blog.phpman.info/archives/199</link>
		<comments>http://blog.phpman.info/archives/199#comments</comments>
		<pubDate>Tue, 11 Dec 2007 12:44:18 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/199</guid>
		<description><![CDATA[12.2.1问题
You want to generate XML but want to do it in an organized way instead of using print and loops.
你想要产生XML。但是应该在一个organized路线代替使用print 和loops
12.2.2解答
Use the DOM extension to create a DOMDocument object. After building up the document, call DOMDocument::save(
) or DOMDocument::saveXML( ) to generate a well-formed XML document
使用这个DOM的延长区创造一个DOMDocument object、然后树立这个文件、调用DOMDocument::save()或者
DOMDocument::saveXML()去产生一个健康成型的文件

?php
// create a new document
$dom = new DOMDocument('1.0');
// create the [...]]]></description>
			<content:encoded><![CDATA[<p>12.2.1问题<br />
You want to generate XML but want to do it in an organized way instead of using print and loops.</p>
<p>你想要产生XML。但是应该在一个organized路线代替使用print 和loops</p>
<p>12.2.2解答<br />
Use the DOM extension to create a DOMDocument object. After building up the document, call DOMDocument::save(</p>
<p>) or DOMDocument::saveXML( ) to generate a well-formed XML document<br />
使用这个DOM的延长区创造一个DOMDocument object、然后树立这个文件、调用DOMDocument::save()或者</p>
<p>DOMDocument::saveXML()去产生一个健康成型的文件<br />
<code><br />
?php<br />
// create a new document<br />
$dom = new DOMDocument('1.0');<br />
// create the root element, &lt;book&gt;, and append it to the document<br />
$book = $dom-&gt;appendChild($dom-&gt;createElement('book'));<br />
// create the title element and append it to $book<br />
$title = $book-&gt;appendChild($dom-&gt;createElement('title'));<br />
// set the text and the cover attribute for $title<br />
$title-&gt;appendChild($dom-&gt;createTextNode('PHP Cookbook'));<br />
$title-&gt;setAttribute('cover', 'soft');<br />
// create and append author elements to $book<br />
$sklar = $book-&gt;appendChild($dom-&gt;createElement('author'));<br />
// create and append the text for each element<br />
$sklar-&gt;appendChild($dom-&gt;createTextNode('Sklar'));<br />
$trachtenberg = $book-&gt;appendChild($dom-&gt;createElement('author'));<br />
$trachtenberg-&gt;appendChild($dom-&gt;createTextNode('Trachtenberg'));<br />
// print a nicely formatted version of the DOM document as XML<br />
$dom-&gt;formatOutput = true;<br />
echo $dom-&gt;saveXML();<br />
?&gt;<br />
&lt;?xml version="1.0"?&gt;<br />
&lt;book&gt;<br />
  &lt;title cover="soft"&gt;PHP Cookbook&lt;/title&gt;<br />
  &lt;author&gt;Sklar&lt;/author&gt;<br />
  &lt;author&gt;Trachtenberg&lt;/author&gt;<br />
&lt;/book&gt;<br />
</code></p>
<p>12.3.3讨论<br />
The DOM methods follow a pattern. You create an object as either an element or a text node, add and set any</p>
<p>attributes you want, and then append it to the tree in the spot it belongs.<br />
这个DOM方法允许仿制。你创造一个对象当作任意一个元素或者一个文件网点。增加移动一些你想要的属性。然后附加它到心</p>
<p>事驱动器的子目录结果<br />
Before creating elements, create a new document, passing the XML version as the sole argument:<br />
在创造元素之前。创造一个新建文档通过这个XML版本当作单一的论点<br />
<code><br />
$dom = new DOMDocument('1.0');<br />
</code></p>
<p>Now create new elements belonging to the document. Despite being associated with a specific document, nodes</p>
<p>don&#8217;t join the document tree until appended:</p>
<p>现在创造一个新的元素属于文件。不管联合一个特殊文件网点不能链接文件直到设置数据文件的搜索路径</p>
<p><code><br />
$book_element = $dom-&gt;createElement('book');<br />
$book = $dom-&gt;appendChild($book_element);<br />
</code></p>
<p>Here a new book element is created and assigned to the object $book_element. To create the document root,</p>
<p>append $book_element as a child of the $dom document. The result, $book, refers to the specific element and</p>
<p>its location within the DOM object<br />
这是一个新的文件元素创造分配到$book_element去保存这个文件证明，附加$book_element当作一个子类$dom文件。这个结果</p>
<p>$book，引用特殊的元素和位置内部DOM对象</p>
<p>All nodes are created by calling a method on $dom. Once a node is created, it can be appended to any element</p>
<p>in the tree. The element from which we call the appendChild( ) method determines the location in the tree <br />
所有的网点创造调用一个方法在$dom.从一个node创造，它可以附加一些元素在这个tree.这个元素从我们调用这个</p>
<p>appendChid()方法确定位置在这个tree，<br />
You can also append a new child element to $book. Since $book is a child of $dom, the new element is, by</p>
<p>extension, a grandchild of $dom:</p>
<p>你同样可以附加一个新的子元素到$book.从$book是一个子类$dom。这个新的元素是延长一个孙类$dom</p>
<p><code><br />
$title_element = $dom-&gt;createElement('title');<br />
$title = $book-&gt;appendChild($title_element);<br />
</code></p>
<p>By calling $book-&gt;appendChild( ), this code places the $title_element element under the $book element.</p>
<p>调用$book-&gt;appendChild()。这个代码放置这个$titie_element .在这个$book元素</p>
<p>To add the text inside the &lt;title&gt;&lt;/title&gt; tags, create a text node using createTextNode( ) and append it to</p>
<p>$title:</p>
<p>去增加正文代替&lt;title&gt;&lt;/title&gt;标签，创造一个正文网点使用createTextNode()和append()它到$title</p>
<p><code><br />
$text_node = $dom-&gt;createTextNode('PHP Cookbook');<br />
$title-&gt;appendChild($text_node);<br />
</code><br />
Since $title is already added to the document, there&#8217;s no need to re-append it to $book.</p>
<p>从$title是已经增加到这个文件。就不需要去附加到$book<br />
<code><br />
$title_element = $dom-&gt;createElement('title');<br />
$text_node = $dom-&gt;createTextNode('PHP Cookbook');<br />
$title_element-&gt;appendChild($text_node);<br />
$book-&gt;appendChild($title_element);<br />
</code></p>
<p>To add an attribute, call setAttribute( ) upon a node, passing the attribute name and value as arguments:</p>
<p>去增加一个属性。调用setAttribute()upon一个网点。通过这个attribute名字和数值当作论点<br />
<code><br />
$title-&gt;setAttribute('cover', 'soft');<br />
</code><br />
If you print the title element now, it looks like this:</p>
<p>如果你打印这个title元素。它会是这样<br />
<code><br />
&lt;title cover="soft"&gt;PHP Cookbook&lt;/title&gt;<br />
</code><br />
Once you&#8217;re finished, you can output the document as a string or to a file:</p>
<p>从前你完成。你可以输出文件就像一个字符串或者一个文件</p>
<p><code><br />
// put the string representation of the XML document in $books<br />
$books = $dom-&gt;saveXML();<br />
// write the XML document to books.xml<br />
$dom-&gt;save('books.xml');<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/199/feed</wfw:commentRss>
		</item>
		<item>
		<title>12.1产生XML当作一个字符串</title>
		<link>http://blog.phpman.info/archives/198</link>
		<comments>http://blog.phpman.info/archives/198#comments</comments>
		<pubDate>Tue, 11 Dec 2007 10:31:50 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/198</guid>
		<description><![CDATA[12.1.1问题
You want to generate XML. For instance, you want to provide an XML version of your data for another program to
parse.
你想要产生XML。例如。你想要规定一个XML版本的数据解析其他程序
12.1.2解答
Loop through your data and print it out surrounded by the correct XML tags:
通过你的数据打印出正确的XML标签

?php
header(&#8217;Content-Type: text/xml&#8217;);
print &#8216;&#60;?xml version=&#8221;1.0&#8243;?&#62;&#8217; . &#8220;\n&#8221;;
print &#8220;&#60;shows&#62;\n&#8221;;
$shows = array(array(&#8217;name&#8217;     =&#62; &#8216;Simpsons&#8217;,
                     &#8216;channel&#8217;  =&#62; &#8216;FOX&#8217;,
                     &#8217;start&#8217;    =&#62; &#8216;8:00 PM&#8217;,
                     &#8216;duration&#8217; =&#62; &#8216;30&#8242;),
               array(&#8217;name&#8217;     [...]]]></description>
			<content:encoded><![CDATA[<p>12.1.1问题<br />
You want to generate XML. For instance, you want to provide an XML version of your data for another program to</p>
<p>parse.</p>
<p>你想要产生XML。例如。你想要规定一个XML版本的数据解析其他程序</p>
<p>12.1.2解答<br />
Loop through your data and print it out surrounded by the correct XML tags:<br />
通过你的数据打印出正确的XML标签<br />
</code><br />
?php<br />
header(&#8217;Content-Type: text/xml&#8217;);<br />
print &#8216;&lt;?xml version=&#8221;1.0&#8243;?&gt;&#8217; . &#8220;\n&#8221;;<br />
print &#8220;&lt;shows&gt;\n&#8221;;<br />
$shows = array(array(&#8217;name&#8217;     =&gt; &#8216;Simpsons&#8217;,<br />
                     &#8216;channel&#8217;  =&gt; &#8216;FOX&#8217;,<br />
                     &#8217;start&#8217;    =&gt; &#8216;8:00 PM&#8217;,<br />
                     &#8216;duration&#8217; =&gt; &#8216;30&#8242;),</p>
<p>               array(&#8217;name&#8217;     =&gt; &#8216;Law &amp; Order&#8217;,<br />
                     &#8216;channel&#8217;  =&gt; &#8216;NBC&#8217;,<br />
                     &#8217;start&#8217;    =&gt; &#8216;8:00 PM&#8217;,<br />
                     &#8216;duration&#8217; =&gt; &#8216;60&#8242;));<br />
foreach ($shows as $show) {<br />
    print &#8220;    &lt;show&gt;\n&#8221;;<br />
    foreach($show as $tag =&gt; $data) {<br />
        print &#8220;        &lt;$tag&gt;&#8221; . htmlspecialchars($data) . &#8220;&lt;/$tag&gt;\n&#8221;;<br />
    }<br />
    print &#8220;    &lt;/show&gt;\n&#8221;;<br />
}<br />
print &#8220;&lt;/shows&gt;\n&#8221;;;<br />
</code></p>
<p>12.1.3讨论<br />
Printing out XML manually mostly involves lots of foreach loops as you iterate through arrays. However, there</p>
<p>are a few tricky details. First, you need to call header( ) to set the correct Content-Type header for the</p>
<p>document. Since you&#8217;re sending XML instead of HTML, it should be text/xml.</p>
<p>手动打印出XML主要的foreach当作你重复的数组。尽管这是一个详细资料。首先你需要钓鱼hearder()去获得正确的Content-</p>
<p>Type.对于这个文件。从你过的XML代替HTML.它的text/xml<br />
Next, depending on your settings for the short_open_tag configuration directive, trying to print the XML</p>
<p>declaration may accidentally turn on PHP processing. Since the &lt;? of &lt;?xml version=&#8221;1.0&#8243;?&gt; is the short PHP</p>
<p>open tag, to print the declaration to the browser you need to either disable the directive or print the line</p>
<p>from within PHP. We do the latter in the Solution.</p>
<p>下面。依靠你的设置去short_open_tag配置指示。试着打印出XML声明可以转换PHP处理。从这个&lt;?到&lt;?xml version=&#8221;1.0&#8243;?&gt;</p>
<p>是这个短的PHP tag去打印出这个声明到浏览器 你需要的任意显示这个指示或者打印出PHP。我们有解答在后面<br />
Last, entities must be escaped. For example, the &amp; in the show Law &amp; Order needs to be &amp;amp;. Call</p>
<p>htmlspecialchars( ) to escape your data.</p>
<p>最后实体必须逃脱。例如这个&amp;在这个表面&amp;需要到&amp;amo、调用htmlspecialchars()去逃开你的数据<br />
The output from the example in the Solution is shown in Example 12-1.</p>
<p>这个输出这个例子在这个解答在例子12-1<br />
<code><br />
&lt;?xml version="1.0"?&gt;<br />
&lt;shows&gt;<br />
    &lt;show&gt;<br />
        &lt;name&gt;Simpsons&lt;/name&gt;<br />
        &lt;channel&gt;FOX&lt;/channel&gt;<br />
        &lt;start&gt;8:00 PM&lt;/start&gt;<br />
        &lt;duration&gt;30&lt;/duration&gt;<br />
    &lt;/show&gt;<br />
    &lt;show&gt;<br />
        &lt;name&gt;Law &amp;amp; Order&lt;/name&gt;<br />
        &lt;channel&gt;NBC&lt;/channel&gt;<br />
        &lt;start&gt;8:00 PM&lt;/start&gt;<br />
        &lt;duration&gt;60&lt;/duration&gt;<br />
    &lt;/show&gt;<br />
&lt;/shows&gt;<br />
</code></p>
<p>  </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/198/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.7存储适合的结果到一览表</title>
		<link>http://blog.phpman.info/archives/197</link>
		<comments>http://blog.phpman.info/archives/197#comments</comments>
		<pubDate>Mon, 10 Dec 2007 08:41:05 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/197</guid>
		<description><![CDATA[11.7.1问题
You need to collect statistics from log tables that are too large to efficiently query in real time.
你需要收集统计到巨大的表格可以迅速的查询
11.7.2解答
Create a table that stores summary data from the complete log table, and query the summary table to generate
reports in nearly real time.
在全部的表格里创建一个表格去存储主要数据，然后查询一览表去产生报告在瞬间
11.7.3讨论
Let&#8217;s say that you are logging search queries that web site visitors use on search engines [...]]]></description>
			<content:encoded><![CDATA[<p>11.7.1问题<br />
You need to collect statistics from log tables that are too large to efficiently query in real time.</p>
<p>你需要收集统计到巨大的表格可以迅速的查询<br />
11.7.2解答<br />
Create a table that stores summary data from the complete log table, and query the summary table to generate</p>
<p>reports in nearly real time.</p>
<p>在全部的表格里创建一个表格去存储主要数据，然后查询一览表去产生报告在瞬间</p>
<p>11.7.3讨论</p>
<p>Let&#8217;s say that you are logging search queries that web site visitors use on search engines like Google and</p>
<p>Yahoo! to find your web site, and tracking those queries in MySQL. Your search term tracking log table has</p>
<p>this structure: <br />
在你的日志搜索查询这个web站点，访问者使用搜索引擎例如Google和Yahoo. 去寻找你的网络站点。然后跟踪这个查询在</p>
<p>MySQL。你查询一览表的结构</p>
<p><code><br />
CREATE TABLE searches<br />
(<br />
  searchterm    VARCHAR(255) NOT NULL,  # search term determined from HTTP_REFERER<br />
                                        parsing<br />
  dt            DATETIME NOT NULL,      # request date<br />
  source        VARCHAR(15) NOT NULL    # site where search was performed<br />
);<br />
</code></p>
<p>If you are fortunate enough to be logging thousands or tens of thousands of visits from the major search</p>
<p>engines per hour, the searches table could grow to an unmanageable size over a period of several months.<br />
如果你有足够数以千计的访问流量从主要的搜索路径每个小时。这个查询列表会有处理不了的尺寸在单月<br />
You may wish to generate reports that illustrate trends of search terms that have driven traffic to your web</p>
<p>site over time from each major search engine so that you can determine which search engine to purchase</p>
<p>advertising with.</p>
<p>你可以希望产生报告举例搜索查询趋势交易到你的网络站点随着时间过去每个主要搜索引擎，你可以决定购买哪个搜索引擎的</p>
<p>广告</p>
<p>Create a summary table that reflects what your report needs to display, and then query the full dataset hourly</p>
<p>and store the result in the summary table for speedy retrieval during report generation. Your summary table</p>
<p>would have this structure:</p>
<p>创造一个一览表，当报告需要显示。然后每小时查询所有数据存储结果到这个一览表迅速的产生报告。你的一览表需要有它的</p>
<p>结构<br />
<code><br />
CREATE TABLE searchsummary<br />
(<br />
  searchterm    VARCHAR(255) NOT NULL,  # search term<br />
  source        VARCHAR(15) NOT NULL,   # site where search was performed<br />
  sdate         DATE NOT NULL,          # date search performed<br />
  searches      INT UNSIGNED NOT NULL,  # number of searches<br />
  PRIMARY KEY (searchterm, source, sdate)<br />
);<br />
</code><br />
Your report generation script can then use PDO to query the searchsummary table, and if results are not</p>
<p>available, collect them from the searches table and cache the result in searchsummary:</p>
<p>你的报告产生原本的使用者PDO去查询表格。然后如果结果不可利用。收集搜索表格和存储结果到searchsummary<br />
<code><br />
$st = $db-&gt;prepare('SELECT COUNT(*)<br />
                     FROM<br />
                        searchsummary<br />
                     WHERE<br />
                        sdate = ?');<br />
$st-&gt;execute(array(date('Y-m-d', strtotime('yesterday'))));<br />
$row = $st-&gt;fetch();<br />
// no matches in cache<br />
if ($row[0] == 0) {<br />
    $st2 = $db-&gt;prepare('SELECT<br />
                          searchterm,<br />
                          source,<br />
                          FROM_DAYS(TO_DAYS(dt)) AS sdate,<br />
                          COUNT(*) as searches<br />
                       WHERE<br />
                          TO_DAYS(dt) = ?');<br />
   $st2-&gt;execute(array(date('Y-m-d', strtotime('yesterday'))));</p>
<p>   $stInsert = $db-&gt;prepare('INSERT INTO searchsummary<br />
                             (searchterm,source,sdate,searches)<br />
                             VALUES (?,?,?,?)');<br />
   while ($row-&gt;fetch(PDO::FETCH_NUM)) {<br />
       $stInsert-&gt;execute($row);<br />
   }<br />
}<br />
</code></p>
<p>Using this technique, your script will only incur the overhead of querying the full log table once, and all</p>
<p>subsequent requests will retrieve a single row of summary data per search term.</p>
<p>使用这个方法。你的原本将唯一招致全部查询到表格然后给所有后来的请求会重新找回一个单一行的主要数据<br />
   </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/197/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.6存储任意数据到公用存储器</title>
		<link>http://blog.phpman.info/archives/196</link>
		<comments>http://blog.phpman.info/archives/196#comments</comments>
		<pubDate>Sun, 09 Dec 2007 11:05:03 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/196</guid>
		<description><![CDATA[11.6.1问题
You want a chunk of data to be available to all web server processes through shared memory.
你想要将大量的服务器进行可利用的数据存储到公用存储器
11.6.2解答
Use the pc_Shm class shown in Example 11-3. For example, to store a string in shared memory, used
the pc_Shm::save( ) method, which accepts a key/value pair
使用这个Pc_Shm类例如在例子11-3，例如去存储字符串到公用存储器。使用这个pc_Shm::save()方法，哪个认可一
个key/value

?php
$shm = new pc_Shm();
$secret_code = 'land shark';
$shm-&#62;save('mysecret', $secret_code);

Another process can then access that data [...]]]></description>
			<content:encoded><![CDATA[<p>11.6.1问题<br />
You want a chunk of data to be available to all web server processes through shared memory.</p>
<p>你想要将大量的服务器进行可利用的数据存储到公用存储器<br />
11.6.2解答</p>
<p>Use the pc_Shm class shown in Example 11-3. For example, to store a string in shared memory, used</p>
<p>the pc_Shm::save( ) method, which accepts a key/value pair<br />
使用这个Pc_Shm类例如在例子11-3，例如去存储字符串到公用存储器。使用这个pc_Shm::save()方法，哪个认可一</p>
<p>个key/value<br />
<code><br />
?php<br />
$shm = new pc_Shm();<br />
$secret_code = 'land shark';<br />
$shm-&gt;save('mysecret', $secret_code);<br />
</code></p>
<p>Another process can then access that data from shared memory with the pc_Shm::fetch( ) method:</p>
<p>另外的处理方法可以从公用存储器里访问数据使用pc_Shm::fetch()方法<br />
<code><br />
?php<br />
$shm = new pc_Shm();<br />
print $shm-&gt;fetch('mysecret');<br />
</code><br />
11.6.3讨论</p>
<p>Occasionally there are times when you want to cache a value or set of values in shared memory for</p>
<p>rapid retrieval. If your web server is busy with disk I/O, it may make sense to leverage the shmop</p>
<p>functions to achieve greater performance with storage and retrieval of information in that cache.<br />
有时候当你想要隐藏一个数值或者移动数值到共有存储器，如果你的网络服务器正工作于I/O磁盘,它可以起平衡作</p>
<p>用使这个shmop函数去完成存储和修复信息在这个存储区</p>
<p>The pc_Shm class has two convenient methods, pc_Shm::fetch( ) and pc_Shm::save( ), which abstract</p>
<p>away the need to set memory addresses or explictly open and close the shared memory segments.<br />
这个pc_Shm类有两个方便的方法。pc_Shm::fetch()和pc_Shm::save().哪个主要函数需要获得存储地址或者打开关</p>
<p>闭这个公用存储器<br />
<code><br />
&lt;?php<br />
$shm = new pc_Shm();<br />
$shm-&gt;setSize(24576); // 24k<br />
$shm-&gt;save('longstring', 'Lorem ipsum pri eu simul nominati...');<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/196/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.5存储Session到公用存储器</title>
		<link>http://blog.phpman.info/archives/195</link>
		<comments>http://blog.phpman.info/archives/195#comments</comments>
		<pubDate>Sat, 08 Dec 2007 11:37:57 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/195</guid>
		<description><![CDATA[11.5.1问题
You want to store session data in shared memory to maximize performance.
你想要存储session数据到公用存储器，以保持最佳状态
11.5.2解答
Use the pc_Shm_Session class shown in Example 11-3. For example:
使用这个pc_Shm_Session 类例如在例子11-3、例如

?php
$s = new pc_Shm_Session();
ini_get('session.auto_start') or session_start();

11.5.3讨论
As discussed in Recipe 11.4, the session module allows users to define their own session handling
methods. While this flexibility is most commonly used to store session data in a [...]]]></description>
			<content:encoded><![CDATA[<p>11.5.1问题<br />
You want to store session data in shared memory to maximize performance.</p>
<p>你想要存储session数据到公用存储器，以保持最佳状态</p>
<p>11.5.2解答</p>
<p>Use the pc_Shm_Session class shown in Example 11-3. For example:</p>
<p>使用这个pc_Shm_Session 类例如在例子11-3、例如<br />
<code><br />
?php<br />
$s = new pc_Shm_Session();<br />
ini_get('session.auto_start') or session_start();<br />
</code><br />
11.5.3讨论<br />
As discussed in Recipe 11.4, the session module allows users to define their own session handling</p>
<p>methods. While this flexibility is most commonly used to store session data in a database, you may</p>
<p>find that performance suffers with the overhead of the database connection and the subsequent</p>
<p>queries. If sharing session data across a bunch of web servers is not a concern, you can boost</p>
<p>session handling performance by storing that data in shared memory.<br />
在第11.4的讨论中，这个session模块允许使用者定义他们自己的session讨论方法，它适用大多一般的经常存储</p>
<p>session数据在一个数据库，你可以找到受损害的session在数据库链接上面和后发的问题。如果共享session数据</p>
<p>横过web服务器而不涉及，你可以推进session处理执行存储这个数据在公用存储器<br />
Before deciding to use shared memory for session storage, make sure that you can spare the amount of</p>
<p>memory that your traffic plus your average session data size will consume. The performance boost of</p>
<p>shared memory session storage won&#8217;t matter if your site&#8217;s sessions consume all available memory on</p>
<p>your system!<br />
决定使用公用存储器存储session。确认你可以节省内存数量加上你的平均session数据量可以消耗。这个执行推进</p>
<p>公用存储器存储session.不用担心如果你的站点sessions消耗所有可利用的内容在你的系统</p>
<p>To store session data in shared memory, you need to have the shared memory functions explicitly</p>
<p>enabled by building PHP with &#8211;enable-shmop. You will also need the pc_Shm class shown in Example</p>
<p>11-3, as well as the pc_Shm_Session class shown in Example 11-3.</p>
<p>存储session数据在公用存储器，你需要明确公用存储器的函数记忆功能。激活建立PHP&#8211;enable-shmop你同样需要</p>
<p>这个pc_Shm 类例如在例子11-3当作pc_Shm_Session类。例如在例子11-3</p>
<p><code><br />
class pc_Shm {<br />
  var $tmp;<br />
  var $size;<br />
  var $shm;<br />
  var $keyfile;<br />
  function pc_Shm($tmp = '') {<br />
    if (!function_exists('shmop_open')) {<br />
      trigger_error('pc_Shm: shmop extension is required.', E_USER_ERROR);<br />
      return;<br />
    }<br />
    if ($tmp != '' &amp;&amp; is_dir($tmp) &amp;&amp; is_writable($tmp)) {<br />
      $this-&gt;tmp = $tmp;<br />
    } else {<br />
      $this-&gt;tmp = '/tmp';<br />
    }<br />
    // default to 16k<br />
    $this-&gt;size = 16384;<br />
    return true;<br />
  }<br />
  function __construct($tmp = '') {<br />
    return $this-&gt;pc_Shm($tmp);<br />
  }<br />
  function setSize($size) {<br />
    if (ctype_digit($size)) {<br />
      $this-&gt;size = $size;<br />
    }<br />
  }<br />
  function open($id) {<br />
    $key = $this-&gt;_getKey($id);<br />
    $shm = shmop_open($key, 'c', 0644, $this-&gt;size);<br />
    if (!$shm) {<br />
      trigger_error('pc_Shm: could not create shared memory segment', E_USER_ERROR);<br />
      return false;<br />
    }<br />
    $this-&gt;shm = $shm;<br />
    return true;<br />
  }<br />
  function write($data) {<br />
    $written = shmop_write($this-&gt;shm, $data, 0);<br />
    if ($written != strlen($data)) {<br />
      trigger_error('pc_Shm: could not write entire length of data', E_USER_ERROR);<br />
      return false;<br />
    }<br />
    return true;<br />
  }<br />
  function read() {<br />
    $data = shmop_read($this-&gt;shm, 0, $this-&gt;size);<br />
    if (!$data) {<br />
      trigger_error('pc_Shm: could not read from shared memory block', E_USER_ERROR);<br />
      return false;<br />
    }<br />
    return $data;<br />
  }<br />
  function delete() {<br />
    if (shmop_delete($this-&gt;shm)) {<br />
      if (file_exists($this-&gt;tmp . DIRECTORY_SEPARATOR . $this-&gt;keyfile)) {<br />
        unlink($this-&gt;tmp . DIRECTORY_SEPARATOR . $this-&gt;keyfile);<br />
      }<br />
    }<br />
    return true;<br />
  }<br />
  function close() {<br />
    return shmop_close($this-&gt;shm);<br />
  }<br />
  function fetch($id) {<br />
    $this-&gt;open($id);<br />
    $data = $this-&gt;read();<br />
    $this-&gt;close();<br />
    return $data;<br />
  }<br />
  function save($id, $data) {<br />
    $this-&gt;open($id);<br />
    $result = $this-&gt;write($data);<br />
    if (! (bool) $result) {<br />
      return false;<br />
    } else {<br />
      $this-&gt;close();<br />
      return $result;<br />
    }<br />
  }<br />
  function _getKey($id) {<br />
    $this-&gt;keyfile = 'pcshm_' . $id;<br />
    if (!file_exists($this-&gt;tmp . DIRECTORY_SEPARATOR . $this-&gt;keyfile)) {<br />
      touch($this-&gt;tmp . DIRECTORY_SEPARATOR . $this-&gt;keyfile);<br />
    }<br />
    return ftok($this-&gt;tmp . DIRECTORY_SEPARATOR . $this-&gt;keyfile, 'R');<br />
  }<br />
}<br />
</code><br />
The pc_Shm class provides an object-oriented wrapper around PHP&#8217;s shmop functions. The</p>
<p>pc_Shm::_getKey( ) method provides a convenient way to transparently calculate a memory address,</p>
<p>which is often the biggest obstacle for people getting familiar with the shmop functions. By</p>
<p>abstracting the memory address, reading and writing from shared memory is as easy as manipulating a</p>
<p>value in an associative array.</p>
<p>这个pc_Shm类规定一个object_oriented环绕PHP的shmop函数。这个pc_Shm::_getKey()方法规定一个方便的方法去</p>
<p>明显的计算存储地址，那个是经常使用的大妨碍物人们获得熟悉的shmop函数，显示这个存储地址。读写公用存储</p>
<p>器更加简单熟练的一个值在一个联合数组 </p>
<p>pc_Shm creates 16k memory blocks by default. To adjust the size of the blocks used, pass a value in</p>
<p>bytes to the pc_Shm::setSize( ) method.</p>
<p>pc_Shm 创造16K存储区。整修使用者大小通过一个数值在pc_Shm::setSize()方法</p>
<p>With pc_Shm defined, pc_Shm_Session has what it needs to easily provide custom methods for</p>
<p>session_set_save_handler( ). Example 11-3 shows the pc_Shm_Session class.</p>
<p>定义pc_Shm 它可以容易的规定习惯方法对于session_set_save_handler(),例子11-3显示这个pc_Shm_Session类<br />
<code><br />
class pc_Shm_Session {<br />
  var $shm;<br />
  function pc_Shm_Session($tmp = '') {<br />
    if (!function_exists('shmop_open')) {<br />
      trigger_error("pc_Shm_Session: shmop extension is required.",E_USER_ERROR);<br />
      return;<br />
    }<br />
    if (! session_set_save_handler(array(&amp;$this, '_open'),<br />
                     array(&amp;$this, '_close'),<br />
                     array(&amp;$this, '_read'),<br />
                     array(&amp;$this, '_write'),<br />
                     array(&amp;$this, '_destroy'),<br />
                     array(&amp;$this, '_gc'))) {<br />
      trigger_error('pc_Shm_Session: session_set_save_handler() failed', E_USER_ERROR);<br />
      return;<br />
    }<br />
    $this-&gt;shm = new pc_Shm();<br />
    return true;<br />
  }<br />
  function __construct() {<br />
    return $this-&gt;pc_Shm_Session();<br />
  }<br />
  function setSize($size) {<br />
    if (ctype_digit($size)) {<br />
      $this-&gt;shm-&gt;setSize($size);<br />
    }<br />
  }<br />
  function _open() {<br />
    return true;<br />
  }<br />
  function _close() {<br />
    return true;<br />
  }<br />
  function _read($id) {<br />
    $this-&gt;shm-&gt;open($id);<br />
    $data = $this-&gt;shm-&gt;read();<br />
    $this-&gt;shm-&gt;close();<br />
    return $data;<br />
  }<br />
  function _write($id, $data) {<br />
    $this-&gt;shm-&gt;open($id);<br />
    $this-&gt;shm-&gt;write($data);<br />
    $this-&gt;shm-&gt;close();<br />
    return true;<br />
  }<br />
  function _destroy($id) {<br />
    $this-&gt;shm-&gt;open($id);<br />
    $this-&gt;shm-&gt;delete();<br />
    $this-&gt;shm-&gt;close();<br />
  }<br />
  function _gc($maxlifetime) {<br />
    $d = dir($this-&gt;tmp);<br />
    while (false !== ($entry = $d-&gt;read())) {<br />
      if (substr($entry, 0, 6) == 'pcshm_') {<br />
        $tmpfile = $this-&gt;tmp . DIRECTORY_SEPARATOR . $entry;<br />
        $id = substr($entry, 6);<br />
        $fmtime = filemtime($tmpfile);<br />
        $age = now() - $fmtime;<br />
        if ($age &gt;= $maxlifetime) {<br />
          $this-&gt;shm-&gt;open($id);<br />
          $this-&gt;shm-&gt;delete();<br />
          $this-&gt;shm-&gt;close();<br />
        }<br />
      }<br />
    }<br />
    $d-&gt;close();<br />
    return true;<br />
  }<br />
}<br />
</code></p>
<p>Versions of Microsoft Windows prior to Windows 2000 do not support shared memory. Also, when using</p>
<p>PHP in a Windows server environment, shmop functions will only work if PHP is running as a web</p>
<p>server module, such those provided by Apache or IIS. CLI and CGI interfaces to PHP do not support</p>
<p>shmop functions under Windows.</p>
<p>微软2000操作系统之前的版本都不支持公用存储器，同样当使用PHP在一个Windows服务器环境。shmop函数仅仅可</p>
<p>以工作。如果PHP运行在一个web服务器模块 例如那些Apache或者IIS。CLT和CGI界面不支持shmop函数在Windows</p>
<p><code><br />
?php<br />
ini_set('session.save_path', '/dev/shm');<br />
ini_get('session.auto_start') or session_start();<br />
</code><br />
 </p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/195/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.4将session存储到数据库</title>
		<link>http://blog.phpman.info/archives/194</link>
		<comments>http://blog.phpman.info/archives/194#comments</comments>
		<pubDate>Fri, 07 Dec 2007 09:09:08 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/194</guid>
		<description><![CDATA[11.4.1问题
You want to store session data in a database instead of in files. If multiple web servers all have access to the same database, the
session data is then mirrored across all the web servers.
你想要存储session数据在一个数据库代替在文件里。如果多样化网络服务器都有权使用一样的数据库。这个session数据在这个DOS访问所有 web服务器
11.4.2解答
Use a class or a set of functions in conjunction with the session_set_save_handler( ) function to define database-aware routines for
session management. [...]]]></description>
			<content:encoded><![CDATA[<p>11.4.1问题<br />
You want to store session data in a database instead of in files. If multiple web servers all have access to the same database, the</p>
<p>session data is then mirrored across all the web servers.<br />
你想要存储session数据在一个数据库代替在文件里。如果多样化网络服务器都有权使用一样的数据库。这个session数据在这个DOS访问所有 web服务器<br />
11.4.2解答<br />
Use a class or a set of functions in conjunction with the session_set_save_handler( ) function to define database-aware routines for</p>
<p>session management. For example, use PEAR&#8217;s HTTP_Session package for convenient database session storage:</p>
<p>使用一个类或者一个函数集和这个session_set_save_handler()函数定义database-aware程序管理、例如。使用REAR&#8217;s HTTP_Session 便利的存储session到</p>
<p>数据库</p>
<p><code><br />
?php<br />
require_once 'HTTP/Session/Container/DB.php';<br />
$s = new HTTP_Session_Container_DB('mysql://user:password@localhost/db');<br />
ini_get('session.auto_start') or session_start();<br />
</code><br />
11.4.3讨论<br />
One of the most powerful aspects of the session module is its abstraction of how sessions get saved. The session_set_save_handler( )</p>
<p>function tells PHP to use different functions for the various session operations such as saving a session and reading session data.</p>
<p>一个session 模块最有力的方面是怎么获得session.这个session_set_save_handler()函数告诉PHP去使用不同的函数在不同的session操作。例如获得一个</p>
<p>session和读出session的数据<br />
The PEAR HTTP_Session package provides classes that take advantage of PEAR&#8217;s DB, MDB, and MDB2 database abstraction packages to store</p>
<p>session data in a database. If the database is shared between multiple web servers, users&#8217; session information is portable across all</p>
<p>those web servers. So if you have a bunch of web servers behind a load balancer, you don&#8217;t need any fancy tricks to ensure that a user&#8217;s</p>
<p>session data is accurate no matter which web server she gets sent to.</p>
<p>这个PEAR HTTP_Session 规定利用PEAR&#8217;sDB 和MDB2数据库提交数据库包去存储session数据，如果这个数据库共享多个浏览器。使用者的session信息轻松越</p>
<p>过这些服务器。所有如果你有一个网络服务器的加载权衡，你不需要一些特别的窍门去确保使用者的session数据正确性</p>
<p>To use HTTP_Session_Container_DB, pass a data source name (DSN) to the class when you instantiate it. The session data is stored in a</p>
<p>table called sessiondata whose structure is:<br />
去使用HTTP_Session_Container_DB。通过一个数据发起姓名(DSN)到这个类。当你示例时。这个session数据存储在一个sessiondata的表格里</p>
<p><code><br />
CREATE TABLE sessiondata<br />
(<br />
  id CHAR(32) NOT NULL,<br />
  data MEDIUMBLOB,<br />
  expiry INT UNSIGNED NOT NULL,<br />
  PRIMARY KEY (id)<br />
);<br />
</code><br />
If you want the table name to be different than sessiondata, you can set a new table name with an options array when instantiating the</p>
<p>HTTP_Session_Container_DB class:</p>
<p>如果你想要表格名字不同于sessiondata。 你可以设置一个新的表格名和一个选项数组当示例这个HTTP_Session_Container_DB类</p>
<p><code><br />
?php<br />
require_once 'HTTP/Session/Container/DB.php';<br />
$options = array(<br />
  'table'  =&gt; 'php_session',<br />
  'dsn'    =&gt; 'mysql://user:password@localhost/db'<br />
);<br />
$s = new HTTP_Session_Container_DB($options);<br />
ini_get('session.auto_start') or session_start();<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/194/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.3防止SESSION固定</title>
		<link>http://blog.phpman.info/archives/193</link>
		<comments>http://blog.phpman.info/archives/193#comments</comments>
		<pubDate>Fri, 07 Dec 2007 02:09:59 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/193</guid>
		<description><![CDATA[11.3.1问题
You want to make sure that your application is not vulnerable to session fixation attacks.
你想要确认你的应用软件不容易遭到攻击session可以抵御攻击
11.3.2解答
Require the use of session cookies without session identifiers appended to URLs, and generate a new session ID frequently:
命令使用session cookies和session 表示符附加到URLs，然后产生一个新的session ID

ini_set('session.use_only_cookies', true);
session_start();
if (!isset($_SESSION['generated'])
    &#124;&#124; $_SESSION['generated'] &#60; (time() - 30)) {
    session_regenerate_id();
    $_SESSION['generated'] = time();
}

11.3.3讨论
In this example, we start by setting [...]]]></description>
			<content:encoded><![CDATA[<p>11.3.1问题<br />
You want to make sure that your application is not vulnerable to session fixation attacks.</p>
<p>你想要确认你的应用软件不容易遭到攻击session可以抵御攻击</p>
<p>11.3.2解答<br />
Require the use of session cookies without session identifiers appended to URLs, and generate a new session ID frequently:</p>
<p>命令使用session cookies和session 表示符附加到URLs，然后产生一个新的session ID</p>
<p><code><br />
ini_set('session.use_only_cookies', true);<br />
session_start();<br />
if (!isset($_SESSION['generated'])<br />
    || $_SESSION['generated'] &lt; (time() - 30)) {<br />
    session_regenerate_id();<br />
    $_SESSION['generated'] = time();<br />
}<br />
</code><br />
11.3.3讨论<br />
In this example, we start by setting PHP&#8217;s session behavior to use cookies only. This overrides PHP&#8217;s default behavior of transparently</p>
<p>appending values such as ?PHPSESSID=12345678 to any URL on a page whenever a visitor&#8217;s session is started if he doesn&#8217;t have cookies</p>
<p>enabled in his browser.</p>
<p>在这个例子，我们首先安装PHP&#8217;s session去使用唯一cookies、它不考虑PHP的默认行为附加值例如PHPSESSID=1234567到一些URL的页面，当访问者的</p>
<p>session已经开始，否则cookies在浏览器激活<br />
Once the session is started, we set a value that will keep track of the last time a session ID was generated. By requiring a new one to</p>
<p>be generated on a regular basis&#8217;every 30 seconds in this example&#8217;the opportunity for an attacker to obtain a valid session ID is</p>
<p>dramatically reduced.</p>
<p>一旦session启动。我们给定值，它会产生上次的一个session ID，它命令新的一个session在每30秒产生一个正规的元素。在这个例子攻击者的机会是获得</p>
<p>一个有效的session ID简化</p>
<p>These two approaches combine to virtually eliminate the risk of session fixation. An attacker has a hard time obtaining a valid session</p>
<p>ID because it changes so often, and since sessions IDs can only be passed in cookies, a URL-based attack is not possible. Finally, since</p>
<p>we enabled the session.use_only_cookies setting, no session cookies will be left lying around in browser histories or in server referrer</p>
<p>logs.</p>
<p>这两个联合方法事实上排除了有风险的固定session。攻击者很困难去获得一个有效的session ID.因为它是经常变化的。从前的session IDs已经被传递到</p>
<p>cookies。一个基于URL的攻击不可能存在。最后我们激活这个session.use_only_cookies设置。没有session cookies将被丢失在浏览器历史或者在浏览器提</p>
<p>交日志</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/193/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.2防止Session丢失</title>
		<link>http://blog.phpman.info/archives/192</link>
		<comments>http://blog.phpman.info/archives/192#comments</comments>
		<pubDate>Thu, 06 Dec 2007 10:48:14 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/192</guid>
		<description><![CDATA[11.2.1问题
You want make sure an attacker can&#8217;t access another user&#8217;s session
你想要确认攻击者不能访问其他使用者的session
11.2.2解答
Allow passing of session IDs via cookies only, and generate an additional session token that is passed via URLs. Only requests that
contain a valid session ID and a valid session token may access the session:
允许通过session IDs到唯一的cookies。然后产生一个另外的session表示通过URLs、唯一的请求包含一个有效的session ID和一个有效的session表示可以
访问这个session

?php
ini_set('session.use_only_cookies', true);
session_start();
$sat     = 'YourSpecialValueHere';
$tokenstr = (str) date('W') . $salt;
$token    [...]]]></description>
			<content:encoded><![CDATA[<p>11.2.1问题<br />
You want make sure an attacker can&#8217;t access another user&#8217;s session<br />
你想要确认攻击者不能访问其他使用者的session</p>
<p>11.2.2解答<br />
Allow passing of session IDs via cookies only, and generate an additional session token that is passed via URLs. Only requests that</p>
<p>contain a valid session ID and a valid session token may access the session:</p>
<p>允许通过session IDs到唯一的cookies。然后产生一个另外的session表示通过URLs、唯一的请求包含一个有效的session ID和一个有效的session表示可以</p>
<p>访问这个session</p>
<p><code><br />
?php<br />
ini_set('session.use_only_cookies', true);<br />
session_start();<br />
$sat     = 'YourSpecialValueHere';<br />
$tokenstr = (str) date('W') . $salt;<br />
$token    = md5($tokenstr);<br />
if (!isset($_REQUEST['token']) || $_REQUEST['token'] != $token) {<br />
    // prompt for login<br />
    exit;<br />
}<br />
$_SESSION['token'] = $token;<br />
output_add_rewrite_var('token', $token);<br />
</code><br />
If you&#8217;re using a PHP version earlier than 4.3.0, output_add_rewrite_var( ) is not available. Instead, use the code in Example 11-1.<br />
如果你使用一个早于4.3.0的PHP版本。output_add_rewrite_var()不可用。代替它，使用这个代码在例子11-1<br />
Adding a session token to links<br />
增加一个session的链接<br />
<code><br />
?php<br />
ini_set('session.use_only_cookies', true);<br />
session_start();<br />
$salt     = 'YourSpecialValueHere';<br />
$tokenstr = (str) date('W') . $salt;<br />
$token    = md5($tokenstr);<br />
if (!isset($_REQUEST['token']) || $_REQUEST['token'] != $token) {<br />
    // prompt for login<br />
    exit;<br />
}<br />
$_SESSION['token'] = $token;<br />
ob_start('inject_session_token');<br />
function inject_session_token($buffer)<br />
{<br />
    $hyperlink_pattern = "/&lt;a[^&gt;]+href=\"([^\"]+)/i";<br />
    preg_match_all($hyperlink_pattern, $buffer, $matches);<br />
    foreach ($matches[1] as $link) {<br />
        if (strpos($link, '?') === false) {<br />
            $newlink = $link . '?token=' . $_SESSION['token'];<br />
        } else {<br />
            $newlink = $link .= '&amp;token=' . $_SESSION['token'];<br />
        }<br />
        $buffer = str_replace($link, $newlink, $buffer);<br />
    }<br />
    return $buffer;<br />
}<br />
</code><br />
The regular expression for matching hyperlinks in the inject_session_token( ) function isn&#8217;t bulletproof; it will not catch hyperlinks</p>
<p>with href attributes quoted with single quotes.<br />
这个正则表达式匹配超链接在这个inject_session_token()函数不是bulletproof.他不能捕捉超链接和href使用单引号</p>
<p>11.2.3讨论<br />
This example creates an auto-shifting token by joining the current week number together with a salt term of your choice. With this</p>
<p>technique, tokens will be valid for a reasonable period of time without being fixed.</p>
<p>这个例子创造一个auto-shifting表示连接通用的星期数加之你选择的一个salt期限。用这个方法表示一个有效合理的时段</p>
<p>We then check for the token in the request, and if it&#8217;s not found, we prompt for a new login.</p>
<p>然后我们阻止这个请求。然后如果它找不到。我们提示一个新的注册</p>
<p>If it is found, it needs to be added to generated links. output_add_rewrite_var( ) does this easily. Without output_add_rewrite_var( ),</p>
<p>we continue generating the page and declare an output buffer callback function that will make sure that any hyperlinks on the page are</p>
<p>modified to contain the current token before the page is displayed.</p>
<p>如果建立。它需要增加连接。output_add_rewrite_var()可以更加简单。使用output_add_rewrite_var()，我们连续产生这个页面声明输出缓冲器回收函数</p>
<p>。它可以确认一些超链接在这个页面修正、包含当前通用的页面显示<br />
Note that the inject_session_token( ) function in the example does not address imagemaps, form submissions, or Ajax calls; make sure that</p>
<p>you adjust any such functionality on a page to include the session token that&#8217;s been generated and stored in the session<br />
注意这个inject_session_token()函数在这个例子不能显示图像。或者Ajax钓鱼。确认你调整这些功能性在一个页面包含session产生存储在这个session</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/192/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.1使用Session跟踪</title>
		<link>http://blog.phpman.info/archives/191</link>
		<comments>http://blog.phpman.info/archives/191#comments</comments>
		<pubDate>Thu, 06 Dec 2007 10:47:06 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/191</guid>
		<description><![CDATA[11.1使用Session跟踪
11.1.1问题
You want to maintain information about a user as she moves through your site
你想要维护使用者的信息移动到你的站点
11.1.2解答
Use the sessions module. The session_start( ) function initializes a session, and accessing an element in the auto-global $_SESSION array tells PHP to keep track of the corresponding variable:
使用者这个session模块。这个seesion_start()函数初始化一个session。然后访问一个元素在全局变量$_SESSION数组告诉PHP相应的变量

?php
session_start();
$_SESSION['visits']++;
print 'You have visited here '.$_SESSION['visits'].' times.';

11.1.3讨论
The session function keep track of users by [...]]]></description>
			<content:encoded><![CDATA[<p>11.1使用Session跟踪</p>
<p>11.1.1问题<br />
You want to maintain information about a user as she moves through your site<br />
你想要维护使用者的信息移动到你的站点</p>
<p>11.1.2解答<br />
Use the sessions module. The session_start( ) function initializes a session, and accessing an element in the auto-global $_SESSION array tells PHP to keep track of the corresponding variable:</p>
<p>使用者这个session模块。这个seesion_start()函数初始化一个session。然后访问一个元素在全局变量$_SESSION数组告诉PHP相应的变量</p>
<p><code><br />
?php<br />
session_start();<br />
$_SESSION['visits']++;<br />
print 'You have visited here '.$_SESSION['visits'].' times.';<br />
</code></p>
<p>11.1.3讨论<br />
The session function keep track of users by issuing them cookies with randomly generated session IDs.</p>
<p>这个session函数保存使用者的cookies和未知的sessionIDs</p>
<p>By default, PHP stores session data in files in the /tmp directory on your server. Each session is stored in its own file. To change the directory in which the files are saved, set the session.save_path configuration directive to the new directory in php.ini or with ini_set( ). You can also call session_save_path( ) with the new directory to change directories, but you need to do this before starting the session or accessing any session variables</p>
<p>By default。PHP存储session数据在文件在你的服务器目录、每个session存储它自己的文件。去改变目录这个文件保存在哪里。移动这个session.save_path配置指示新的目录在php.ini或者ini_set()，你同样可以调用session_save_path()和这个新的目录去改变目录，但是你需要之前已经开始的session或者访问一些session的变量<br />
To start a session automatically on each request, set session.auto_start to 1 in php.ini. With session.auto_start, there&#8217;s no need to call session_start( ).</p>
<p>自动开始一个session在每个索引。设置session.auto_start到1在php.ini.使用session.auto_start，就不需要调用session_start()</p>
<p>With the session.use_trans_sid configuration directive turned on, if PHP detects that a user doesn&#8217;t accept the session ID cookie, it automatically adds the session ID to URLs and forms.[] For example, consider this code that prints a URL:</p>
<p>使用这个session.use_trans_sid配置指示开始。如果PHP发现这个使用者不接受session ID cookie。它自动的增加session Id 到URLs和forms.[]例如考虑这个代码打印出一个URL<br />
<code><br />
?php<br />
print '&lt;a href="train.php" mce_href="train.php"&gt;Take the A Train&lt;/a&gt;';<br />
</code><br />
If sessions are enabled, but a user doesn&#8217;t accept cookies, what&#8217;s sent to the browser is something like:</p>
<p>如果sessions激活。但是使用者不接受cookies。发送浏览器重要<br />
<code><br />
?php<br />
&lt;a href="train.php?PHPSESSID=2eb89f3344520d11969a79aea6bd2fdd" mce_href="train.php?PHPSESSID=2eb89f3344520d11969a79aea6bd2fdd"&gt;Take the A Train&lt;/a&gt;<br />
</code><br />
 </p>
<p>In this example, the session name is PHPSESSID and the session name is 2eb89f3344520d11969a79aea6bd2fdd. PHP adds those to the URL so they are passed along to the next page. Forms are modified to include a hidden element that passes the session ID.</p>
<p>在这些例子。这个session名字是PHPSESSID和这个session名字是2eb89f3344520d11969a79aea6bd2fdd.PHP增加这些URL,所以它通过下一个页面。改良包括隐藏的元素到这个sessionID<br />
Due to a variety of security concerns relating to embedding session IDs in URLs, this behavior is disabled by default. To enable transparent session IDs in URLs, you need to turn on session.use_trans_sid in php.ini or through the use of ini_set(&#8217;session.use_trans_sid&#8217;, true) in your scripts before the session is started.</p>
<p>由于一个多种安全涉及embedding session IDs在URLs.这些行为是丧失能力的。能够显然的sessions IDs在URLs.你需要转换session.ues_trans_sid在php.ini或者通过这些使用ini_set(&#8217;session.use_trans_sid&#8217;,ture)在你的原本session开始<br />
Although session.use_trans_sid is convenient, it can cause you some security-related headaches. Because URLs have session IDs in them, distribution of such a URL lets anybody who receives the URL act as the user to whom the session ID was given. A user that copies a URL from his web browser and pastes it into an email message sent to friends unwittingly allows all those friends (and anybody else to whom the message is forwarded) to visit your site and impersonate him.</p>
<p>通过session.use_trans_sid很方便。它可以使你有一些安全，因为URLs有sessionIDs在这些。分配这些就像一个URL任何接收URL获得使用者的ID.一个使用者复制一个URL从它的浏览器，然后粘贴它到一个email信息无意的发送到一个好友允许所有好友访问你的站点<br />
Separately, redirects with the Location header aren&#8217;t automatically modified, so you have to add a session ID to them yourself using the SID constant:</p>
<p>个别的改变方向位置标题不能自动修改。所有你需要增加一个session ID到这些yourself使用者SID常量</p>
<p><code><br />
$redirect_url = 'http://www.example.com/airplane.php';<br />
if (defined('SID') &amp;&amp; (!isset($_COOKIE[session_name()]))) {<br />
    $redirect_url .= '?' . SID;<br />
}<br />
header("Location: $redirect_url");<br />
&lt;/code&gt;<br />
The session_name( ) function returns the name of the cookie to the session ID is stored in, so this code appends the SID constant to $redirect_url if the constant is defined, and the session cookie isn't set.</p>
<p>这个session_name()函数返回cookie的名字到session ID存储它，所以这个代码附加这个SID常量到$redirect_url。如果常量是定义过的。这个session cookie不移动<br />
<code>;<br />
?php<br />
ini_set('session.use_only_cookies', true);<br />
session_start();<br />
$salt     = 'YourSpecialValueHere';<br />
$tokenstr = (str) date('W') . $salt;<br />
$token    = md5($tokenstr);<br />
if (!isset($_REQUEST['token']) || $_REQUEST['token'] != $token) {<br />
    // prompt for login<br />
    exit;<br />
}<br />
$_SESSION['token'] = $token;<br />
ob_start('inject_session_token');<br />
function inject_session_token($buffer)<br />
{<br />
    $hyperlink_pattern = "/&lt;a[^&gt;]+href=\"([^\"]+)/i";<br />
    preg_match_all($hyperlink_pattern, $buffer, $matches);<br />
    foreach ($matches[1] as $link) {<br />
        if (strpos($link, '?') === false) {<br />
            $newlink = $link . '?token=' . $_SESSION['token'];<br />
        } else {<br />
            $newlink = $link .= '&amp;token=' . $_SESSION['token'];<br />
        }<br />
        $buffer = str_replace($link, $newlink, $buffer);<br />
    }<br />
    return $buffer;<br />
}<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/191/feed</wfw:commentRss>
		</item>
		<item>
		<title>11.0介绍</title>
		<link>http://blog.phpman.info/archives/190</link>
		<comments>http://blog.phpman.info/archives/190#comments</comments>
		<pubDate>Wed, 05 Dec 2007 10:41:24 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/190</guid>
		<description><![CDATA[As web applications have matured, the need for statefulness has become a common requirement. Stateful web applications, meaning applications that keep
track of a particular visitor&#8217;s information as he travels throughout a site, are now so common that they are taken for granted.
当中web软件应用成熟。它需要充满规定丰富的成为一个必要条件。规定web应用。意思是应用详细的访问者的信息当中一个地点，既然是一个共有的。它们认可
Given the prevalence of web applications that keep track of things for their visitors&#8217;such [...]]]></description>
			<content:encoded><![CDATA[<p>As web applications have matured, the need for statefulness has become a common requirement. Stateful web applications, meaning applications that keep</p>
<p>track of a particular visitor&#8217;s information as he travels throughout a site, are now so common that they are taken for granted.</p>
<p>当中web软件应用成熟。它需要充满规定丰富的成为一个必要条件。规定web应用。意思是应用详细的访问者的信息当中一个地点，既然是一个共有的。它们认可<br />
Given the prevalence of web applications that keep track of things for their visitors&#8217;such as shopping carts, online banking, personalized home page</p>
<p>portals, and social networking community sites&#8217;it is hard to imagine the Internet we use every day without stateful applications.</p>
<p>获得流行的web应用软件，访问者当作购物车。联机银行的私人主页入口和社会网络站点，假设我们每天使用Internet的应用软件<br />
HTTP, the protocol that web servers and clients use to talk to each other, is a stateless protocol by design. However, since PHP 4.0, developers who&#8217;ve</p>
<p>built applications with PHP have had a convenient set of session management functions that have made the challenge of implementing statefulness much</p>
<p>easier. This chapter focuses on several good practices to keep in mind while developing stateful applications.<br />
HTTP.这个网络浏览器协议和客户机程序使用彼此。它是一个无国界协议，尽管从PHP4.0开发者建立应用软件和PHP有一套方便的管理函数。它已经获得这个挑战执行非常简</p>
<p>单。这一章集中几个单独的有良好习惯做法的发展中的应用软件<br />
Sessions are focused on maintaining visitor-specific state between requests. Some applications also require an equivalent type of lightweight storage</p>
<p>of non-visitor-specific state for a period of time at the server-side level. This is known as data persistence.</p>
<p>集中维护特殊访问者的请求。一些应用软件同样命令一个相等的类型不匹配的特殊访问者，它们是持续的<br />
Recipe 11.1 explains PHP&#8217;s session module, which lets you easily associate persistent data with a user as he moves through your site. Recipes 11.2 and</p>
<p>11.3 explore session hijacking and session fixation vulnerabilities and how to avoid them.</p>
<p>第11.1章说明PHP的模块。哪个是不容易结合持久的数据和一个使用者当作你的移动站点。第11.2章和11.3章探测session hijackin and session fixation弱点和消除他们<br />
Session data is stored in flat files in the server&#8217;s /tmp directory by default. Recipes 11.4 and 11.5 explain how to store session data in alternate</p>
<p>locations, such as a database and shared memory, and discusses the pros and cons of these different approaches.</p>
<p>Session数据存储在flat文件在这个服务器/tmp目录默认。第11.4章和11.5章说明怎么去存储session数据在交替的位置。例如一个数据库和公用存储器讨论赞成与反对 </p>
<p>这些不同的方法</p>
<p>Recipe 11.6 demonstrates how to use shared memory for more than just session data storage, and Recipe 11.7 illustrates techniques for longer-term</p>
<p>storage of summary information that has been gleaned from logfiles.<br />
第11.6章证明这么去使用公用存储器对于这些正好的数据保存，在第11.7章举例证明比较久的存储技术概要信息来自这些文件</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/190/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.16程序：存储一个有线状图案装饰的留言板</title>
		<link>http://blog.phpman.info/archives/189</link>
		<comments>http://blog.phpman.info/archives/189#comments</comments>
		<pubDate>Wed, 05 Dec 2007 10:39:12 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/189</guid>
		<description><![CDATA[Storing and retrieving threaded messages requires extra care to display the threads in the correct order. Finding the children of each message and building the tree of message relationships can easily lead to a recursive web of queries. Users generally look at a list of messages and read individual messages far more often then they [...]]]></description>
			<content:encoded><![CDATA[<p>Storing and retrieving threaded messages requires extra care to display the threads in the correct order. Finding the children of each message and building the tree of message relationships can easily lead to a recursive web of queries. Users generally look at a list of messages and read individual messages far more often then they post messages. With a little extra processing when saving a new message to the database, the query that retrieves a list of messages to display is simpler and much more efficient.<br />
存储和重新找回有线状图案装饰留言板很注意显示这个思路在这个正确的规则。发现每个子信息建立三个子信息关联很容易的通向一个递归的web查询，使用者通常注意一列信息阅读单一的信息对于更多经常使用的信息和一个小量的额外处理当获得一个新的信息到这个数据库这个查询重新找回一列信息显示更加简单直接</p>
<p>Store messages in a table structured like this:<br />
存储信息在一个表格结构例如<br />
<code><br />
CREATE TABLE pc_message (<br />
  id INT UNSIGNED NOT NULL,<br />
  posted_on DATETIME NOT NULL,<br />
  author CHAR(255),<br />
  subject CHAR(255),<br />
  body MEDIUMTEXT,<br />
  thread_id INT UNSIGNED NOT NULL,<br />
  parent_id INT UNSIGNED NOT NULL,<br />
  level INT UNSIGNED NOT NULL,<br />
  thread_pos INT UNSIGNED NOT NULL,<br />
  PRIMARY KEY(id)<br />
);<br />
&lt;/code&gt;<br />
The primary key, id, is a unique integer that identifies a particular message. The time and date that a message is posted is stored in posted_on, and author, subject, and body are (surprise!) a message's author, subject, and body. The remaining four fields keep track of the threading relationships between messages. The integer tHRead_id identifies each thread.</p>
<p>这个主要的键。id是一个唯一的整数确认一个特殊的信息。这个时间和日期的信息是一个主要的村粗在posted_on和作者，题目和主要(surprise!)作者信息题目。保留的4个文件关联信息之间、这个整数tHread_id鉴别每个思路</p>
<p>&lt;code&gt;<br />
&lt;?php<br />
$board = new MessageBoard();<br />
$board-&gt;go();<br />
class MessageBoard {<br />
    protected $db;<br />
    protected $form_errors = array();<br />
    protected $inTransaction = false;<br />
    public function __construct() {<br />
        set_exception_handler(array($this,'logAndDie'));<br />
        $this-&gt;db = new PDO('sqlite:/usr/local/data/message.db');<br />
        $this-&gt;db-&gt;setAttribute(PDO::ATTR_ERRMODE,PDO::ERRMODE_EXCEPTION);<br />
    }<br />
    public function go() {<br />
        // The value of $_REQUEST['cmd'] tells us what to do<br />
        $cmd = isset($_REQUEST['cmd']) ? $_REQUEST['cmd'] : 'show';<br />
        switch ($cmd) {<br />
            case 'read':          // read an individual message<br />
              $this-&gt;read();<br />
              break;<br />
            case 'post':          // display the form to post a message<br />
              $this-&gt;post();<br />
              break;<br />
            case 'save':          // save a posted message<br />
              if ($this-&gt;valid()) { // if the message is valid,<br />
                  $this-&gt;save();    // then save it<br />
                  $this-&gt;show();    // and display the message list<br />
              } else {<br />
                  $this-&gt;post();    // otherwise, redisplay the posting form<br />
              }<br />
              break;<br />
            case 'show':          // show a message list by default<br />
            default:<br />
              $this-&gt;show();<br />
              break;<br />
        }<br />
    }<br />
    // save() saves the message to the database<br />
    protected function save() {<br />
        $parent_id = isset($_REQUEST['parent_id']) ?<br />
                     intval($_REQUEST['parent_id']) : 0;<br />
        // Make sure pc_message doesn't change while we're working with it.<br />
        $this-&gt;db-&gt;beginTransaction();<br />
        $this-&gt;inTransaction = true;<br />
        // is this message a reply?<br />
        if ($parent_id) {<br />
            // get the thread, level, and thread_pos of the parent message<br />
            $st = $this-&gt;db-&gt;prepare("SELECT thread_id,level,thread_pos<br />
                                FROM pc_message WHERE id = ?");<br />
            $st-&gt;execute(array($parent_id));<br />
            $parent = $st-&gt;fetch();<br />
            // a reply's level is one greater than its parent's<br />
            $level = $parent['level'] + 1;<br />
            /* what's the biggest thread_pos in this thread among messages<br />
            with the same parent? */<br />
            $st = $this-&gt;db-&gt;prepare('SELECT MAX(thread_pos) FROM pc_message<br />
                    WHERE thread_id = ? AND parent_id = ?');<br />
            $st-&gt;execute(array($parent['thread_id'], $parent_id));<br />
            $thread_pos = $st-&gt;fetchColumn(0);<br />
            // are there existing replies to this parent?<br />
            if ($thread_pos) {<br />
                // this thread_pos goes after the biggest existing one<br />
                $thread_pos++;<br />
            } else {<br />
                // this is the first reply, so put it right after the parent<br />
                $thread_pos = $parent['thread_pos'] + 1;<br />
            }<br />
            /* increment the thread_pos of all messages in the thread that<br />
            come after this one */<br />
            $st = $this-&gt;db-&gt;prepare('UPDATE pc_message SET thread_pos = thread_pos + 1<br />
                          WHERE thread_id = ? AND thread_pos &gt;= ?');<br />
            $st-&gt;execute(array($parent['thread_id'], $thread_pos));<br />
            // the new message should be saved with the parent's thread_id<br />
            $thread_id = $parent['thread_id'];<br />
        } else {<br />
            // the message is not a reply, so it's the start of a new thread<br />
            $thread_id = $this-&gt;db-&gt;query('SELECT MAX(thread_id) + 1 FROM pc_message')<br />
                           -&gt;fetchColumn(0);<br />
            $level = 0;<br />
            $thread_pos = 0;<br />
        }<br />
        /* insert the message into the database. Using prepare() and execute()<br />
        makes sure that all fields are properly quoted */<br />
        $st = $this-&gt;db-&gt;prepare("INSERT INTO pc_message (id,thread_id,parent_id,<br />
                       thread_pos,posted_on,level,author,subject,body)<br />
                       VALUES (?,?,?,?,?,?,?,?,?)");</p>
<p>        $st-&gt;execute(array(null,$thread_id,$parent_id,$thread_pos,<br />
                             date('c'),$level,$_REQUEST['author'],<br />
                             $_REQUEST['subject'],$_REQUEST['body']));<br />
        // Commit all the operations<br />
        $this-&gt;db-&gt;commit();<br />
        $this-&gt;inTransaction = false;<br />
    }<br />
    // show() displays a list of all messages<br />
    protected function show() {<br />
        print '&lt;h2&gt;Message List&lt;/h2&gt;&lt;p&gt;';<br />
        /* order the messages by their thread (thread_id) and their position<br />
        within the thread (thread_pos) */<br />
        $st = $this-&gt;db-&gt;query("SELECT id,author,subject,LENGTH(body) AS body_length,<br />
                       posted_on,level FROM pc_message<br />
                       ORDER BY thread_id,thread_pos");<br />
        while ($row = $st-&gt;fetch()) {<br />
            // indent messages with level &gt; 0<br />
            print str_repeat('&amp;nbsp;',4 * $row['level']);<br />
            // print out information about the message with a link to read it<br />
            print "&lt;a href='" . htmlentities($_SERVER['PHP_SELF']) .<br />
            "?cmd=read&amp;amp;id={$row['id']}'&gt;" .<br />
            htmlentities($row['subject']) . '&lt;/a&gt; by ' .<br />
            htmlentities($row['author']) . ' @ ' .<br />
            htmlentities($row['posted_on']) .<br />
            " ({$row['body_length']} bytes) &lt;br/&gt;";<br />
        }<br />
        // provide a way to post a non-reply message<br />
        print "&lt;hr/&gt;&lt;a href='" .<br />
              htmlentities($_SERVER['PHP_SELF']) .<br />
              "?cmd=post'&gt;Start a New Thread&lt;/a&gt;";<br />
    }<br />
    // read() displays an individual message<br />
    public function read() {<br />
        /* make sure the message id we're passed is an integer and really<br />
        represents a message */<br />
        if (! isset($_REQUEST['id'])) {<br />
            throw new Exception('No message ID supplied');<br />
        }<br />
        $id = intval($_REQUEST['id']);<br />
        $st = $this-&gt;db-&gt;prepare("SELECT author,subject,body,posted_on<br />
                                 FROM pc_message WHERE id = ?");<br />
        $st-&gt;execute(array($id));<br />
        $msg = $st-&gt;fetch();<br />
        if (! $msg) {<br />
            throw new Exception('Bad message ID');<br />
        }<br />
        /* don't display user-entered HTML, but display newlines as<br />
        HTML line breaks */<br />
        $body = nl2br(htmlentities($msg['body']));</p>
<p>        // display the message with links to reply and return to the message list<br />
        $self = htmlentities($_SERVER['PHP_SELF']);<br />
        $subject = htmlentities($msg['subject']);<br />
        $author = htmlentities($msg['author']);<br />
        print&lt;&lt;&lt;_HTML_<br />
&lt;h2&gt;$subject&lt;/h2&gt;<br />
&lt;h3&gt;by $author&lt;/h3&gt;<br />
&lt;p&gt;$body&lt;/p&gt;<br />
&lt;hr/&gt;<br />
&lt;a href="$self?cmd=post&amp;parent_id=$id"&gt;Reply&lt;/a&gt;<br />
&lt;br/&gt;<br />
&lt;a href="$self?cmd=list"&gt;List Messages&lt;/a&gt;<br />
_HTML_;<br />
    }<br />
    // post() displays the form for posting a message<br />
    public function post() {<br />
        $safe =  array();<br />
        foreach (array('author','subject','body') as $field) {<br />
            // escape characters in default field values<br />
            if (isset($_POST[$field])) {<br />
                $safe[$field] = htmlentities($_POST[$field]);<br />
            } else {<br />
                $safe[$field] = '';<br />
            }<br />
            // make the error messages display in red<br />
            if (isset($this-&gt;form_errors[$field])) {<br />
                $this-&gt;form_errors[$field] = '&lt;span style="color: red"&gt;' .<br />
                   $this-&gt;form_errors[$field] . '&lt;/span&gt;&lt;br/&gt;';<br />
            } else {<br />
                $this-&gt;form_errors[$field] = '';<br />
            }<br />
        // is this message a reply<br />
        if (isset($_REQUEST['parent_id']) &amp;&amp;<br />
        $parent_id = intval($_REQUEST['parent_id'])) {<br />
        // send the parent_id along when the form is submitted<br />
        $parent_field =<br />
            sprintf('&lt;input type="hidden" name="parent_id" value="%d" /&gt;',<br />
                    $parent_id);<br />
        // if no subject's been passed in, use the subject of the parent<br />
        if (! strlen($safe['subject'])) {<br />
             $st = $this-&gt;db-&gt;prepare('SELECT subject FROM pc_message WHERE id = ?');<br />
             $st-&gt;execute(array($parent_id));<br />
             $parent_subject = $st-&gt;fetchColumn(0);<br />
            /* prefix 'Re: ' to the parent subject if it exists and<br />
               doesn't already have a 'Re:' */<br />
            $safe['subject'] = htmlentities($parent_subject);<br />
            if ($parent_subject &amp;&amp; (! preg_match('/^re:/i',$parent_subject))) {<br />
                $safe['subject'] = "Re: {$safe['subject']}";<br />
            }<br />
          }<br />
        } else {<br />
            $parent_field = '';<br />
        }<br />
    // display the posting form, with errors and default values<br />
    $self = htmlentities($_SERVER['PHP_SELF']);<br />
    print&lt;&lt;&lt;_HTML_<br />
&lt;form method="post" action="$self"&gt;<br />
&lt;table&gt;<br />
&lt;tr&gt;<br />
 &lt;td&gt;Your Name:&lt;/td&gt;<br />
 &lt;td&gt;{$this-&gt;form_errors['author']}<br />
     &lt;input type="text" name="author" value="{$safe['author']}" /&gt;<br />
&lt;/td&gt;<br />
&lt;tr&gt;<br />
 &lt;td&gt;Subject:&lt;/td&gt;<br />
 &lt;td&gt;{$this-&gt;form_errors['subject']}<br />
     &lt;input type="text" name="subject" value="{$safe['subject']}" /&gt;<br />
&lt;/td&gt;<br />
&lt;tr&gt;<br />
 &lt;td&gt;Message:&lt;/td&gt;<br />
 &lt;td&gt;{$this-&gt;form_errors['body']}<br />
     &lt;textarea rows="4" cols="30" wrap="physical"<br />
               name="body"&gt;{$safe['body']}&lt;/textarea&gt;<br />
&lt;/td&gt;<br />
&lt;tr&gt;&lt;td colspan="2"&gt;&lt;input type="submit" value="Post Message" /&gt;&lt;/td&gt;&lt;/tr&gt;<br />
&lt;/table&gt;<br />
$parent_field<br />
&lt;input type="hidden" name="cmd" value="save" /&gt;<br />
&lt;/form&gt;<br />
_HTML_;<br />
    }<br />
    // validate() makes sure something is entered in each field<br />
    public function valid() {<br />
        $this-&gt;form_errors = array();<br />
        if (! (isset($_POST['author']) &amp;&amp; strlen(trim($_POST['author'])))) {<br />
            $this-&gt;form_errors['author'] = 'Please enter your name.';<br />
        }<br />
        if (! (isset($_POST['subject']) &amp;&amp; strlen(trim($_POST['subject'])))) {<br />
            $this-&gt;form_errors['subject'] = 'Please enter a message subject.';<br />
        }<br />
        if (! (isset($_POST['body']) &amp;&amp; strlen(trim($_POST['body'])))) {<br />
            $this-&gt;form_errors['body'] = 'Please enter a message body.';<br />
        }<br />
        return (count($this-&gt;form_errors) == 0);<br />
    }<br />
    public function logAndDie(Exception $e) {<br />
        print 'ERROR: ' . htmlentities($e-&gt;getMessage());<br />
        if ($this-&gt;db &amp;&amp; $this-&gt;db-&gt;inTransaction) {<br />
            $this-&gt;db-&gt;rollback();<br />
        }<br />
        exit();<br />
    }<br />
}<br />
</code><br />
To properly handle concurrent usage, save( ) needs exclusive access to the msg table between the time it starts calculating the tHRead_pos of the new message and when it actually inserts the new message into the database. We&#8217;ve used PDO&#8217;s beginTransaction( ) and commit( ) methods to accomplish this. Note that logAndDie( ), the exception handler, rolls back the transaction when appropriate if an error occured inside the transaction. Although PDO always calls rollback( ) at the end of a script if a transaction was started, explicitly including the call inside logAndDie( ) makes clearer what&#8217;s happening to someone reading the code.</p>
<p>去适当的操作并发的用法。save()需要唯一有权使用这个msg表格它开始计算这个tHread_pos的新的信息和当它嵌入这个新的信息到这个数据库我们使用PDO的beginTransaction()和commit()方法去完成它注意logAndDie()。这个例外的管理者压低到标准水平处理它当适当的时候。如果一个错误出现在这个处理。尽管PDO总是调用rollback()在这个最后的一个版本如果一个处理开始明确的包括调用logAndDie()更清楚当发生在更多的代码<br />
The level field can be used when displaying messages to limit what you retrieve from the database. If discussion threads become very deep, this can help prevent your pages from growing too large. Example 10-44 shows how to display just the first message in each thread and any replies to that first message.</p>
<p>这个标准的文件可以使用当显示信息限制当你从数据库重新找回。如果讨论思路非常深。它可以帮助你的页面更加大。例子10-44显示怎么正好显示这第一个信息在每个思路和任何回答第一个信息<br />
<code><br />
?php<br />
$st = $this-&gt;db-&gt;query(<br />
    "SELECT * FROM pc_message WHERE level &lt;= 1 ORDER BY thread_id,thread_pos");<br />
while ($row = $st-&gt;fetch()) {<br />
    // display each message<br />
}<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/189/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.15访问一个数据库连接到你的程序</title>
		<link>http://blog.phpman.info/archives/188</link>
		<comments>http://blog.phpman.info/archives/188#comments</comments>
		<pubDate>Thu, 15 Nov 2007 06:36:17 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/188</guid>
		<description><![CDATA[10.15.1问题
You&#8217;ve got a program with lots of functions and classes in it, and you want to maintain a single database
connection that&#8217;s easily accessible from anywhere in the program.
你拥有一个程序和许多函数和类在内。然后你想要支持一个单一的数据库连接它很容易无论何处在这个程序
10.15.2解答
Use a static class method that creates the connection if it doesn&#8217;t exist and returns the connection (see
Example 10-40).
使用一个静态的类方法创造这个连接。如果它不存在然后返回这个连接(请看例子10-40)

?php
class DBCxn {
    // What DSN to connect to?
    public [...]]]></description>
			<content:encoded><![CDATA[<p>10.15.1问题<br />
You&#8217;ve got a program with lots of functions and classes in it, and you want to maintain a single database</p>
<p>connection that&#8217;s easily accessible from anywhere in the program.</p>
<p>你拥有一个程序和许多函数和类在内。然后你想要支持一个单一的数据库连接它很容易无论何处在这个程序</p>
<p>10.15.2解答<br />
Use a static class method that creates the connection if it doesn&#8217;t exist and returns the connection (see</p>
<p>Example 10-40).</p>
<p>使用一个静态的类方法创造这个连接。如果它不存在然后返回这个连接(请看例子10-40)<br />
<code><br />
?php<br />
class DBCxn {<br />
    // What DSN to connect to?<br />
    public static $dsn = 'sqlite:c:/data/zodiac.db';<br />
    public static $user = null;<br />
    public static $pass = null;<br />
    public static $driverOpts = null;<br />
    // Internal variable to hold the connection<br />
    private static $db;<br />
    // No cloning or instantiating allowed<br />
    final private function __construct() { }<br />
    final private function __clone() { }<br />
    public static function get() {<br />
        // Connect if not already connected<br />
        if (is_null(self::$db)) {<br />
            self::$db = new PDO(self::$dsn, self::$user, self::$pass,<br />
                                self::$driverOpts);<br />
        }<br />
        // Return the connection<br />
        return self::$db;<br />
    }<br />
}<br />
</code></p>
<p>10.15.3讨论</p>
<p>The DBCxn::get( ) method defined in Example 10-40 accomplishes two things: you can call it from anywhere</p>
<p>in your program without worrying about variable scope and it prevents more than one connection from being</p>
<p>created in a program.</p>
<p>这个DBCxn::get()方法定义在例子10-40完成两个事情。你可以调用它从任何地方到你的程序不用担心变量作用域和它防</p>
<p>止超过1个的连接从创造的一个程序</p>
<p>To change what kind of connection DBCxn::get( ) provides, just alter the $dsn, $user, $pass, and</p>
<p>$driverOpts properties of the class. If you need to manage multiple different database connections during</p>
<p>the same script execution, change $dsn and $db to an array and have get( ) accept an argument identifying</p>
<p>which connection to use. Example 10-41 shows a version of DBCxn that provides access to three different</p>
<p>databases.<br />
去改变DBCxn::get()的连接。正好改变这个$dsn. $user. $pass.和$driverOpts这个类的道具。如果你需要经营多种不</p>
<p>同的数据库连接这个一样的执行。改变$dsn和$db到一个数组和get()认可一个论点确认哪个使用连接。例子10-41显示一</p>
<p>个DBCxn的译本有权使用三个不同的数据库<br />
<code><br />
?php<br />
class DBCxn {<br />
    // What DSNs to connect to?<br />
    public static $dsn =<br />
       array('zodiac' =&gt; 'sqlite:c:/data/zodiac.db',<br />
             'users' =&gt; array('mysql:host=db.example.com','monty','7f2iuh'),<br />
             'stats' =&gt; array('oci:statistics', 'statsuser','statspass'))<br />
    // Internal variable to hold the connection<br />
    private static $db = array();<br />
    // No cloning or instantiating allowed<br />
    final private function __construct() { }<br />
    final private function __clone() { }<br />
    public static function get($key) {<br />
        if (! isset(self::$dsn[$key])) {<br />
            throw new Exception("Unknown DSN: $key");<br />
        }<br />
        // Connect if not already connected<br />
        if (! isset(self::$db[$key])) {<br />
            if (is_array(self::$dsn[$key])) {<br />
                // The next two lines only work with PHP 5.1.3 and above<br />
                $c = new ReflectionClass('PDO');<br />
                self::$db[$key] = $c-&gt;newInstanceArgs(self::$dsn[$key]);<br />
            } else {<br />
                self::$db[$key] = new PDO(self::$dsn[$key]);<br />
            }<br />
        }<br />
        // Return the connection<br />
        return self::$db[$key];<br />
    }<br />
}<br />
</code></p>
<p>In Example 10-41, you must pass a key to DBCxn::get( ) that identifies which entry in $dsn to use. The</p>
<p>code inside get( ) is a little more complicated, too, because it has to handle variable numbers of</p>
<p>arguments to the PDO constructor. Some databases, such as SQLite, just need one argument. Others may</p>
<p>provide two, three, or four arguments. Example 10-41 uses the ReflectionClass::newInstanceArgs( ) method,</p>
<p>added in PHP 5.1.3, to concisely call a constructor and provide arguments in an array. If you&#8217;re using an</p>
<p>earlier version of PHP, replace the calls to new ReflectionClass(&#8217;PDO&#8217;) and to newInstanceArgs( ) with</p>
<p>the code in Example 10-42.</p>
<p>在例子10-41，你必须通过一个键到DBCxn::get()它确认哪个登陆$dsn使用这个代码在get()内也有一些复杂。因为它很</p>
<p>困难去处理PDO构造器的变量数字。一些数据库。例如SQL。正好需要一个论点，其他可以添加两个、三个、或者四格。</p>
<p>例子10-14使用这个ReflectionClass::newInstanceArgs()方法增加在PHP5.1.3去简明的调用一个构造器和规定论点在一</p>
<p>个数组。如果你使用一个早期的PHP文本取代调用新的ReflectionClass(&#8217;PDO&#8217;)和newInstanceArgs()和这个代码在例子</p>
<p>10-42</p>
<p><code><br />
?php<br />
$args = self::$dsn[$key];<br />
$argCount = count($args);<br />
if ($argCount == 1) {<br />
    self::$db[$key] = new PDO($args[0]);<br />
} else if ($argCount == 2) {<br />
    self::$db[$key] = new PDO($args[0],$args[1]);<br />
} else if ($argCount == 3) {<br />
    self::$db[$key] = new PDO($args[0],$args[1],$args[2]);<br />
} else if ($argCount == 4) {<br />
    self::$db[$key] = new PDO($args[0],$args[1],$args[2],$args[3]);<br />
}<br />
</code></p>
<p>Example 10-42 checks for each possible count of arguments to provide to the PDO constructor and invokes</p>
<p>the constructor accordingly.</p>
<p>例子10-42检查每个可能的计算论点到规定这个PDO构造器和因此调用这个构造器</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/188/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.14 Caching 查询和结果</title>
		<link>http://blog.phpman.info/archives/187</link>
		<comments>http://blog.phpman.info/archives/187#comments</comments>
		<pubDate>Thu, 15 Nov 2007 06:17:47 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/187</guid>
		<description><![CDATA[10.14.1问题
You don&#8217;t want to rerun potentially expensive database queries when the results haven&#8217;t changed
你不想返回潜在的昂贵的数据库查询当这个结果不再改变
10.14.2解答
Use PEAR&#8217;s Cache_Lite package. It makes it simple to cache arbitrary data. In this case, cache the
results of a SELECT query and use the text of the query as a cache key. Example 10-39 shows how to cache
query results with Cache_Lite.
使用PEAR&#8217;s Cache_Lite [...]]]></description>
			<content:encoded><![CDATA[<p>10.14.1问题</p>
<p>You don&#8217;t want to rerun potentially expensive database queries when the results haven&#8217;t changed<br />
你不想返回潜在的昂贵的数据库查询当这个结果不再改变</p>
<p>10.14.2解答<br />
Use PEAR&#8217;s Cache_Lite package. It makes it simple to cache arbitrary data. In this case, cache the</p>
<p>results of a SELECT query and use the text of the query as a cache key. Example 10-39 shows how to cache</p>
<p>query results with Cache_Lite.</p>
<p>使用PEAR&#8217;s Cache_Lite package.它是一个简单的chache 数据。既然这样cache这个SELECT结果和使用这个正文查询当</p>
<p>作一个cache键。例子10-39显示怎么去cache查询结果使用Cache_Lite<br />
<code><br />
?php<br />
require_once 'Cache/Lite.php';<br />
$opts = array(<br />
   // Where to put the cached data<br />
   'cacheDir' =&gt; 'c:/tmp',<br />
   // Let us store arrays in the cache<br />
  'automaticSerialization' =&gt; true,<br />
  // How long stuff lives in the cache<br />
  'lifeTime' =&gt; 600 /* ten minutes */);<br />
// Create the cache<br />
$cache = new Cache_Lite($opts);<br />
// Connect to the database<br />
$db = new PDO('sqlite:c:/data/zodiac.db');<br />
// Define our query and its parameters<br />
$sql = 'SELECT * FROM zodiac WHERE planet = ?';<br />
$params = array($_GET['planet']);<br />
// Get the unique cache key<br />
$key = cache_key($sql, $params);<br />
// Try to get results from the cache<br />
$results = $cache-&gt;get($key);<br />
if ($results === false) {<br />
    // No results found, so do the query and put the results in the cache<br />
    $st = $db-&gt;prepare($sql);<br />
    $st-&gt;execute($params);<br />
    $results = $st-&gt;fetchAll();<br />
    $cache-&gt;save($results);<br />
}<br />
// Whether from the cache or not, $results has our data<br />
foreach ($results as $result) {<br />
    print "$result[id]: $result[planet], $result[sign] &lt;br/&gt;\n";<br />
}<br />
function cache_key($sql, $params) {<br />
    return md5($sql .<br />
               implode('|',array_keys($params)) .<br />
               implode('|',$params));<br />
}<br />
</code><br />
10.14.3讨论</p>
<p>Cache_Lite is a generic, lightweight mechanism for caching arbitrary information. It uses files to store</p>
<p>the information it&#8217;s caching. The Cache_Lite constructor takes an array of options that control its</p>
<p>behavior. The two most important ones in Example 10-39 are automaticSerialization, which makes it easier</p>
<p>to store arrays in the cache, and cacheDir, which defines where the cache files go. Make sure cacheDir</p>
<p>ends with a /.<br />
Cache_Lite是一个一般的特殊配置对于caching 信息。它使用文件去存储这个caching信息、这个Cache_Lite构造器去获</p>
<p>得很多选项配置它的行为。这两个重要的信息在例子10-39是自动连载。哪个是很容易存储数组在这个cache和cacheDir</p>
<p>哪个定义这个小cache文件。确认cacheDir结束于a/<br />
The cache is just a mapping of keys to values. It&#8217;s up to us to make sure that we supply a cache key that</p>
<p>uniquely identifies the data we want to cache&#8217;in this case, the SQL query and the parameters bound to it.</p>
<p>The cache_key function computes an appropriate key. After that, Example 10-39 just checks to see if the</p>
<p>results are already in the cache. If not, it executes the query against the database and stuffs the</p>
<p>results in the cache for next time.<br />
这个cache正好是一个mapping的键。它确认补充一个cache键到独特的你想要的数据到cache。这个SQL查询和这个参数限</p>
<p>制它。这个cache_key函数计算一个适当的键。然后例子10-39正好检查它如果这个结果已经在这个cache。如果不是它执</p>
<p>行这个query相反的在这个数据和这个结果在这个cache</p>
<p>Note that you can&#8217;t put a PDO or PDOStatement object in the cache&#8217;you have to fetch results and then put</p>
<p>the results in the cache.</p>
<p>现在你不能放置一个PDO或者PDOStatement对象在这个cache你获得的结果和放这个结果在这个cache</p>
<p>The cache isn&#8217;t altered if you change the database with an INSERT, UPDATE, or DELETE query. If there are</p>
<p>cached SELECT statements that refer to data no longer in the database, you need to explicitly remove</p>
<p>everything from the cache with the Cache_Lite::clean( ) method. You can also remove an individual element</p>
<p>from the cache by passing a cache key to Cache_Lite::remove( ).</p>
<p>这个cache不改变如果你改变这个数据库和一个INSERT. UPDATE或者DELETE查询如果他是一个cached SELECT指令这个数</p>
<p>据不在这个数据库，你需要明确的移动cache的每个事情和这个Cache_Lite::clean()方法，你同样可以移动一个单元素</p>
<p>从这个cache通过一个cache键到Cache_Lite::remove()<br />
The cache_key( ) function in Example 10-39 is case sensitive. This means that if the results of SELECT *</p>
<p>FROM zodiac are in the cache, and you run the query SELECT * from zodiac, the results aren&#8217;t found in the</p>
<p>cache and the query is run again. Maintaining consistent capitalization, spacing, and field ordering when</p>
<p>constructing your SQL queries results in more efficient cache usage.<br />
这个cache_key()函数在例子10-39是区分大小写的。他的意思是如果SELECT*FORM zodiac是在这个cache.然后允许这个</p>
<p>query SELECT*from zodiac这个结果不是在这个query再次运行维持一致的大写，间隔排序当建立你的SQL查询在很直接</p>
<p>的cache用法</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/187/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.12建立Query标题</title>
		<link>http://blog.phpman.info/archives/186</link>
		<comments>http://blog.phpman.info/archives/186#comments</comments>
		<pubDate>Tue, 13 Nov 2007 10:43:20 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/186</guid>
		<description><![CDATA[10.12.1问题
You want to construct an INSERT or UPDATE query from an array of field names. For example, you want to
insert a new user into your database. Instead of hardcoding each field of user information (such as
username, email address, postal address, birthdate, etc.), you put the field names in an array and use the
array to build [...]]]></description>
			<content:encoded><![CDATA[<p>10.12.1问题<br />
You want to construct an INSERT or UPDATE query from an array of field names. For example, you want to</p>
<p>insert a new user into your database. Instead of hardcoding each field of user information (such as</p>
<p>username, email address, postal address, birthdate, etc.), you put the field names in an array and use the</p>
<p>array to build the query. This is easier to maintain, especially if you need to conditionally INSERT or</p>
<p>UPDATE with the same set of fields.</p>
<p>你想要建造一个INSERT或者UPDATE创造性从一个数组文件名。例如。你想要嵌入一个新的使用者到你的数据库代替处理译</p>
<p>码的每个使用者信息文件(例如使用名。email地址。postal address. birthdate. etc)你防止这个文件名在一个数组和</p>
<p>使用这个数组去建立这个查询。他是一个简单的特别是如果你需要有条件嵌入INSERT或者UPDATE和一样的文件</p>
<p>10.12.2解答</p>
<p>To construct an UPDATE query, build an array of field/value pairs and then implode( ) together each</p>
<p>element of that array, as shown in Example 10-31.<br />
去建立一个UPDATE 查询，建立一个数组一对文件/值和然后implode()一起的一个元素数组。例如在例子10-31<br />
<code><br />
?php<br />
// A list of field names<br />
$fields = array('symbol','planet','element');<br />
$update_fields = array();<br />
$update_values = array();<br />
foreach ($fields as $field) {<br />
    $update_fields[] = "$field = ?";<br />
    // Assume the data is coming from a form<br />
    $update_values[] = $_POST[$field];<br />
}<br />
$st = $db-&gt;prepare("UPDATE zodiac SET " .<br />
                   implode(',', $update_fields) .<br />
                  'WHERE sign = ?');<br />
// Add 'sign' to the values array<br />
$update_values[] = $_GET['sign'];<br />
// Execute the query<br />
$st-&gt;execute($update_values);<br />
</code><br />
For an INSERT query, do the same thing, although the SQL syntax is a little different, as Example 10-32</p>
<p>demonstrates<br />
对于一个INSERT查询。做一样的时区，尽管这个SQL syntax 是一个很小的差别。例如在例子10-32示例</p>
<p><code><br />
?php<br />
// A list of field names<br />
$fields = array('symbol','planet','element');<br />
$placeholders = array();<br />
$values = array();<br />
foreach ($fields as $field) {<br />
    // One placeholder per field<br />
    $placeholders[] = '?';<br />
    // Assume the data is coming from a form<br />
    $values[] = $_POST[$field];<br />
}<br />
$st = $db-&gt;prepare('INSERT INTO zodiac (' .<br />
                   implode(',',$fields) .<br />
                   ') VALUES (' .<br />
                   implode(',', $placeholders) .<br />
                   ')');<br />
// Execute the query<br />
$st-&gt;execute($values);<br />
</code></p>
<p>10.12.3讨论</p>
<p>Placeholders make this sort of thing a breeze. Because they take care of escaping the provided data, you</p>
<p>can easily stuff user-submitted data into programatically generated queries.</p>
<p>占位符制作一个短的时区。因为它存储数据，你可以轻松的使使用者提交数据到产生queries<br />
If you use sequence-generated integers as primary keys, you can combine the two query-construction</p>
<p>techniques into one function. That function determines whether a record exists and then generates the</p>
<p>correct query, including a new ID, as shown in the pc_build_query( ) function in Example 10-33.</p>
<p>如果你使用sequence-generated 整数当作主要键，你可以联合两个query-construction技术在一个函数。哪个函数确定</p>
<p>一个记录然后产生正确的查询。包括一个新的ID。例如在这个pc_build_query()函数在例子10-33<br />
<code><br />
?php<br />
function pc_build_query($db,$key_field,$fields,$table) {<br />
    $values = array();<br />
    if (! empty($_POST[$key_field])) {<br />
        $update_fields = array();<br />
        foreach ($fields as $field) {<br />
            $update_fields[] = "$field = ?";<br />
            // Assume the data is coming from a form<br />
            $values[] = $_POST[$field];<br />
        }<br />
        // Add the key field's value to the $values array<br />
        $values[] = $_POST[$key_field];<br />
        $st = $db-&gt;prepare("UPDATE $table SET " .<br />
                   implode(',', $update_fields) .<br />
                   "WHERE $key_field = ?");<br />
    } else {<br />
        // Start values off with a unique ID<br />
        // If your DB is set to generate this value, use NULL instead<br />
        $values[] = md5(uniqid());<br />
        $placeholders = array('?');<br />
        foreach ($fields as $field) {<br />
            // One placeholder per field<br />
            $placeholders[] = '?';<br />
            // Assume the data is coming from a form<br />
            $values[] = $_POST[$field];<br />
        }<br />
        $st = $db-&gt;prepare("INSERT INTO $table ($key_field," .<br />
                           implode(',',$fields) . ') VALUES ('.<br />
                           implode(',',$placeholders) .')');<br />
    }<br />
    $st-&gt;execute($values);<br />
    return $st;<br />
}<br />
</code></p>
<p>Using this function, you can make a simple page to edit all the information in the zodiac table, shown in</p>
<p>Example 10-34.</p>
<p>使用这些函数。你可以制作一个简单的页面去编辑所有的信息在这个zodiac表格。例如在例子10-34<br />
<code><br />
?php<br />
$db = new PDO('sqlite:/usr/local/data/zodiac.db');<br />
$db-&gt;setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);<br />
$fields = array('sign','symbol','planet','element',<br />
                'start_month','start_day','end_month','end_day');</p>
<p>$cmd = isset($_REQUEST['cmd']) ? $_REQUEST['cmd'] : 'show';</p>
<p>switch ($cmd) {<br />
 case 'edit':<br />
 try {<br />
    $st = $db-&gt;prepare('SELECT ' . implode(',',$fields) .<br />
                       ' FROM zodiac WHERE id = ?');<br />
    $st-&gt;execute(array($_REQUEST['id']));<br />
    $row = $st-&gt;fetch(PDO::FETCH_ASSOC);<br />
 } catch (Exception $e) {<br />
     $row = array();<br />
 }<br />
 case 'add':<br />
     print '&lt;form method="post" action="' .<br />
           htmlentities($_SERVER['PHP_SELF']) . '"&gt;';<br />
     print '&lt;input type="hidden" name="cmd" value="save"&gt;';<br />
     print '&lt;table&gt;';<br />
     if ('edit' == $_REQUEST['cmd']) {<br />
         printf('&lt;input type="hidden" name="id" value="%d"&gt;',<br />
                $_REQUEST['id']);<br />
     }<br />
     foreach ($fields as $field) {<br />
         if ('edit' == $_REQUEST['cmd']) {<br />
             $value = htmlentities($row[$field]);<br />
         } else {<br />
             $value = '';<br />
         }<br />
         printf('&lt;tr&gt;&lt;td&gt;%s: &lt;/td&gt;&lt;td&gt;&lt;input type="text" name="%s" value="%s"&gt;',<br />
                $field,$field,$value);<br />
         printf('&lt;/td&gt;&lt;/tr&gt;');<br />
     }<br />
     print '&lt;tr&gt;&lt;td&gt;&lt;/td&gt;&lt;td&gt;&lt;input type="submit" value="Save"&gt;&lt;/td&gt;&lt;/tr&gt;';<br />
     print '&lt;/table&gt;&lt;/form&gt;';<br />
     break;<br />
 case 'save':<br />
     try {<br />
       $st = pc_build_query($db,'id',$fields,'zodiac');<br />
       print 'Added info.';<br />
     } catch (Exception $e) {<br />
       print "Couldn't add info: " . htmlentities($e-&gt;getMessage());<br />
     }<br />
     print '&lt;hr&gt;';<br />
 case 'show':<br />
 default:<br />
     $self = htmlentities($_SERVER['PHP_SELF']);<br />
     print '&lt;ul&gt;';<br />
     foreach ($db-&gt;query('SELECT id,sign FROM zodiac') as $row) {<br />
         printf('&lt;li&gt; &lt;a href="%s?cmd=edit&amp;id=%s"&gt;%s&lt;/a&gt;',<br />
                $self,$row['id'],$row['sign']);<br />
     }<br />
     print '&lt;hr&gt;&lt;li&gt; &lt;a href="'.$self.'?cmd=add"&gt;Add New&lt;/a&gt;';<br />
     print '&lt;/ul&gt;';<br />
     break;<br />
</code></p>
<p>The switch statement controls what action the program takes based on the value of $_REQUEST[&#8217;cmd&#8217;]. If</p>
<p>$_REQUEST[&#8217;cmd&#8217;] is add or edit, the program displays a form with text boxes for each field in the $fields</p>
<p>array, as shown in Figure 10-1. If $_REQUEST[&#8217;cmd&#8217;] is edit, values for the row with the supplied $id are</p>
<p>loaded from the database and displayed as defaults. If $_REQUEST[&#8217;cmd&#8217;] is save, the program uses</p>
<p>pc_build_query( ) to generate an appropriate query to either INSERT or UPDATE the data in the database.</p>
<p>这个switch叙述控制action程序基于$_REQUEST[&#8217;cmd&#8217;]如果$_REQUEST[&#8217;cmd&#8217;]是增加获得编辑这个程序显示一个form和每</p>
<p>个文件的正文框在$fields数组例如在表格10-1.如果$_REQUEST[&#8217;cmd&#8217;]编辑。每行的数值和$id从这个数据库显示默认。</p>
<p>如果$_REQUEST[&#8217;cmd&#8217;]获得、这个程序使用pc_build_query()去产生一个适合的query到INSERT或者UPDATE这个数据在数</p>
<p>据库</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/186/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.11创造唯一的标识符</title>
		<link>http://blog.phpman.info/archives/185</link>
		<comments>http://blog.phpman.info/archives/185#comments</comments>
		<pubDate>Tue, 13 Nov 2007 09:24:08 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/185</guid>
		<description><![CDATA[10.11.1问题
You want to assign unique IDs to users, articles, or other objects as you add them to your database.
你想要分配唯一的IDs到使用者文章或者其他对象当作你增加他们到你的数据库
10.11.2解答
Use PHP&#8217;s uniqid( ) function to generate an identifier. To restrict the set of characters in the identifier, pass it through md5( ), which returns a string containing only numerals and the letters a through f. Example [...]]]></description>
			<content:encoded><![CDATA[<p>10.11.1问题<br />
You want to assign unique IDs to users, articles, or other objects as you add them to your database.</p>
<p>你想要分配唯一的IDs到使用者文章或者其他对象当作你增加他们到你的数据库</p>
<p>10.11.2解答<br />
Use PHP&#8217;s uniqid( ) function to generate an identifier. To restrict the set of characters in the identifier, pass it through md5( ), which returns a string containing only numerals and the letters a through f. Example 10-28 creates identifiers using both techniques.</p>
<p>使用PHP的unqid()函数产生一个标识符。去限制设置标识符的特征，通过它md5()哪个返回一个字符串仅仅包含数字和一个文字f。例子10-28创造一个标识符使用两个技术</p>
<p><code><br />
?php<br />
$st = $db-&gt;prepare('INSERT INTO users (id, name) VALUES (?,?)');<br />
$st-&gt;execute(array(uniqid(), 'Jacob'));<br />
$st-&gt;execute(array(md5(uniqid()), 'Ruby'));<br />
</code></p>
<p>You can also use a database-specific method to have the database generate the ID. For example, SQLite 3 and MySQL support AUTOINCREMENT columns that automatically assign increasing integers to a column as rows are inserted.<br />
你同样可以使用一个数据库特殊方法使用数据库产生这个ID,例如SQL3和MySQL支持AUTOTNCREMENT自动分配渐多整数到一个column嵌入的行</p>
<p>10.11.3讨论<br />
uniqid( ) uses the current time (in microseconds) and a random number to generate a string that is extremely difficult to guess. md5( ) computes a hash of whatever you give it. It doesn&#8217;t add any randomness to the identifier, but restricts the characters that appear in it. The results of md5( ) don&#8217;t contain any punctuation, so you don&#8217;t have to worry about escaping issues. Plus, you can&#8217;t spell any naughty words with just the first six letters of the alphabet (in English, at least).</p>
<p>uniqid()使用当前时间和一个任意数去产生一个字符串就是说很难猜测。md5()计算你获得的无用信息它不能增加一些随意的标识符，但是限制这个，这个md5()的结果不能包含一些标识符，所以你不用担心escaping issues加上你不能拼写不适合的单词在字母表的第六个<br />
<code><br />
?php<br />
// the type INTEGER PRIMARY KEY AUTOINCREMENT tells SQLite<br />
// to assign ascending IDs<br />
$db-&gt;exec(&lt;&lt;&lt;_SQL_<br />
  CREATE TABLE users (<br />
    id  INTEGER PRIMARY KEY AUTOINCREMENT,<br />
    name VARCHAR(255)<br />
  )<br />
_SQL_<br />
);<br />
// No need to insert a value for 'id' -- SQLite assigns it<br />
$st = $db-&gt;prepare('INSERT INTO users (name) VALUES (?)');<br />
// These rows are assigned 'id' values<br />
foreach (array('Jacob','Ruby') as $name) {<br />
    $st-&gt;execute(array($name));<br />
}<br />
?&gt;<br />
&lt;/code&gt;<br />
Example 10-30 shows the same thing for MySQL.<br />
 例子10-30显示一样的MySQL</code><code>&lt;code&gt;<br />
&lt;?php<br />
// the AUTO_INCREMENT tells MySQL to assign ascending IDs<br />
// that column must be the PRIMARY KEY<br />
$db-&gt;exec(&lt;&lt;&lt;_SQL_<br />
  CREATE TABLE users (<br />
    id  INT NOT NULL AUTO_INCREMENT,<br />
    name VARCHAR(255),<br />
    PRIMARY KEY(id)<br />
  )<br />
_SQL_<br />
);<br />
// No need to insert a value for 'id' -- MySQL assigns it<br />
$st = $db-&gt;prepare('INSERT INTO users (name) VALUES (?)');<br />
// These rows are assigned 'id' values<br />
foreach (array('Jacob','Ruby') as $name) {<br />
    $st-&gt;execute(array($name));<br />
}<br />
?&gt;<br />
&lt;/code&gt;</p>
<p>When the database creates ID values automatically, the PDO::lastInsertId( ) method retrieves them. Call lastInsertId( ) on your PDO object to get the auto-generated ID of the last inserted row. Some database backends also let you pass a sequence name to lastInsertId( ) to get the last value from the sequence.</p>
<p>当这个数据库保护ID自动数值、这个PDO::lastInsertId()方法重新找回这些，调用lastInsertId()在你的PDO对象获得这个auto-generated ID的最后嵌入行。一些数据库同样获得一个sequence 名字到lastInsetID()获得最后的数据从这个sequence</p>
<p></code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/185/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.10调试错误信息</title>
		<link>http://blog.phpman.info/archives/184</link>
		<comments>http://blog.phpman.info/archives/184#comments</comments>
		<pubDate>Tue, 13 Nov 2007 09:17:59 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/184</guid>
		<description><![CDATA[10.10.1问题
You want access to information to help you debug database problems. For example, when a query fails, you want to see what error message the database returns.
你想要有权使用信息帮助你调试数据库的问题。例如当一个query失败。你想看到错误信息在这个数据库返回
10.10.2解答
Use PDO::errorCode( ) or PDOStatement::errorCode( ) after an operation to get an error code if the operation failed. The corresponding errorInfo( ) method returns more information about the error. [...]]]></description>
			<content:encoded><![CDATA[<p>10.10.1问题<br />
You want access to information to help you debug database problems. For example, when a query fails, you want to see what error message the database returns.</p>
<p>你想要有权使用信息帮助你调试数据库的问题。例如当一个query失败。你想看到错误信息在这个数据库返回</p>
<p>10.10.2解答<br />
Use PDO::errorCode( ) or PDOStatement::errorCode( ) after an operation to get an error code if the operation failed. The corresponding errorInfo( ) method returns more information about the error. Example 10-26 handles the error that results from trying to access a nonexistent table.</p>
<p>使用PDO::errorCode()或者PDOStatement::errorCode()在一个运转错误代码如果这个操作失败这个相应的errorInfo()方法返回错误信息。例子10-26处理这个错误结果设法访问不存在的表格<br />
<code><br />
?php<br />
$st = $db-&gt;prepare('SELECT * FROM imaginary_table');<br />
if (! $st) {<br />
    $error = $db-&gt;errorInfo();<br />
    print "Problem ({$error[2]})";<br />
}<br />
</code></p>
<p>10.10.3讨论<br />
The errorCode( ) method returns a five-character error code. PDO uses the SQL 92 SQLSTATE error codes. By that standard, 00000 means &#8220;no error,&#8221; so a call to errorCode( ) that returns 00000 indicates success.<br />
着errorCode()方法返回一个五处错误代码。PDO使用SQL 92 SQLSTATE错误代码。标准情况下。0000意思是&#8221;no error&#8221; 所以调用errorCode()返回0000显示成功<br />
The errorInfo( ) method returns a three-element array. The first element contains the five-character SQLSTATE code (the same thing that errorCode( ) returns). The second element is a database backend-specific error code. The third element is a database backend-specific error message.</p>
<p>这个errorInfo()方法返回一个三个元素数组，这一个元素包含5个特征SQLSTATE 代码。这第二个元素是一个数据库返回绝对代码。这第三个元素是一个数据库的错误信息</p>
<p>Make sure to call errorCode( ) or errorInfo( ) on the same object on which you called the method that you&#8217;re checking for an error. In Example 10-26, the prepare( ) method is called on the PDO object, so errorInfo( ) is called on the PDO object. If you want to check whether a fetch( ) called on a PDOStatement object succeeded, call errorCode( ) or errorInfo( ) on the PDOStatement object.</p>
<p>确认调用errorCode()或者errorInfo()在一样的对象在哪个调用方法检查出一个错误、在例子10-26，这个prepare()方法调用这个PDO对象。所以errorInfo()是调用在这个PDO对象。如果你想要检查一个fetch()调用一个PDOStatement对象，调用errorCode()或者errorInfo()在这个PDOStatement对象<br />
One exception to this rule is when creating a new PDO object. If that fails, PDO throws an exception. It does this because otherwise there&#8217;d be no object on which you could call errorCode( ) or errorInfo( ). The message in the exception details why the connection failed<br />
一个例外的规则。当创造一个新的PDO对象。如果他是错误的。PDO通过一个例外。他可以因为其他的对象不是问题。哪个你调用errorCode()或者errorInfo()这个信息在特别详细的资料</p>
<p><code><br />
?php<br />
try {<br />
    $db = new PDO('sqlite:/usr/local/zodiac.db');<br />
    // Make all DB errors throw exceptions<br />
    $db-&gt;setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);<br />
    $st = $db-&gt;prepare('SELECT * FROM zodiac');<br />
    $st-&gt;execute();<br />
    while ($row = $st-&gt;fetch(PDO::FETCH_NUM)) {<br />
        print implode(',',$row). "&lt;br/&gt;\n";<br />
    }<br />
} catch (Exception $e) {<br />
    print "Database Problem: " . $e-&gt;getMessage();<br />
}<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/184/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.11创造唯一的标识符</title>
		<link>http://blog.phpman.info/archives/183</link>
		<comments>http://blog.phpman.info/archives/183#comments</comments>
		<pubDate>Tue, 13 Nov 2007 08:31:23 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/183</guid>
		<description><![CDATA[10.11.1问题
You want to assign unique IDs to users, articles, or other objects as you add them to your database.
你想要分配唯一的IDs到使用者文章或者其他对象当作你增加他们到你的数据库
10.11.2解答
Use PHP&#8217;s uniqid( ) function to generate an identifier. To restrict the set of characters in the
identifier, pass it through md5( ), which returns a string containing only numerals and the letters a
through f. Example 10-28 creates [...]]]></description>
			<content:encoded><![CDATA[<p>10.11.1问题<br />
You want to assign unique IDs to users, articles, or other objects as you add them to your database.</p>
<p>你想要分配唯一的IDs到使用者文章或者其他对象当作你增加他们到你的数据库</p>
<p>10.11.2解答<br />
Use PHP&#8217;s uniqid( ) function to generate an identifier. To restrict the set of characters in the</p>
<p>identifier, pass it through md5( ), which returns a string containing only numerals and the letters a</p>
<p>through f. Example 10-28 creates identifiers using both techniques.</p>
<p>使用PHP的unqid()函数产生一个标识符。去限制设置标识符的特征，通过它md5()哪个返回一个字符串仅仅包含数字和一</p>
<p>个文字f。例子10-28创造一个标识符使用两个技术</p>
<p><code><br />
?php<br />
$st = $db-&gt;prepare('INSERT INTO users (id, name) VALUES (?,?)');<br />
$st-&gt;execute(array(uniqid(), 'Jacob'));<br />
$st-&gt;execute(array(md5(uniqid()), 'Ruby'));<br />
</code></p>
<p>You can also use a database-specific method to have the database generate the ID. For example, SQLite 3</p>
<p>and MySQL support AUTOINCREMENT columns that automatically assign increasing integers to a column as rows</p>
<p>are inserted.<br />
你同样可以使用一个数据库特殊方法使用数据库产生这个ID,例如SQL3和MySQL支持AUTOTNCREMENT自动分配渐多整数到一</p>
<p>个column嵌入的行</p>
<p>10.11.3讨论<br />
uniqid( ) uses the current time (in microseconds) and a random number to generate a string that is</p>
<p>extremely difficult to guess. md5( ) computes a hash of whatever you give it. It doesn&#8217;t add any</p>
<p>randomness to the identifier, but restricts the characters that appear in it. The results of md5( ) don&#8217;t</p>
<p>contain any punctuation, so you don&#8217;t have to worry about escaping issues. Plus, you can&#8217;t spell any</p>
<p>naughty words with just the first six letters of the alphabet (in English, at least).</p>
<p>uniqid()使用当前时间和一个任意数去产生一个字符串就是说很难猜测。md5()计算你获得的无用信息它不能增加一些随</p>
<p>意的标识符，但是限制这个，这个md5()的结果不能包含一些标识符，所以你不用担心escaping issues加上你不能拼写不</p>
<p>适合的单词在字母表的第六个<br />
<code><br />
?php<br />
// the type INTEGER PRIMARY KEY AUTOINCREMENT tells SQLite<br />
// to assign ascending IDs<br />
$db-&gt;exec(&lt;&lt;&lt;_SQL_<br />
  CREATE TABLE users (<br />
    id  INTEGER PRIMARY KEY AUTOINCREMENT,<br />
    name VARCHAR(255)<br />
  )<br />
_SQL_<br />
);<br />
// No need to insert a value for 'id' -- SQLite assigns it<br />
$st = $db-&gt;prepare('INSERT INTO users (name) VALUES (?)');<br />
// These rows are assigned 'id' values<br />
foreach (array('Jacob','Ruby') as $name) {<br />
    $st-&gt;execute(array($name));<br />
}<br />
</code><br />
Example 10-30 shows the same thing for MySQL.<br />
 例子10-30显示一样的MySQL</p>
<p><code><br />
?php<br />
// the AUTO_INCREMENT tells MySQL to assign ascending IDs<br />
// that column must be the PRIMARY KEY<br />
$db-&gt;exec(&lt;&lt;&lt;_SQL_<br />
  CREATE TABLE users (<br />
    id  INT NOT NULL AUTO_INCREMENT,<br />
    name VARCHAR(255),<br />
    PRIMARY KEY(id)<br />
  )<br />
_SQL_<br />
);<br />
// No need to insert a value for 'id' -- MySQL assigns it<br />
$st = $db-&gt;prepare('INSERT INTO users (name) VALUES (?)');<br />
// These rows are assigned 'id' values<br />
foreach (array('Jacob','Ruby') as $name) {<br />
    $st-&gt;execute(array($name));<br />
}<br />
</code></p>
<p>When the database creates ID values automatically, the PDO::lastInsertId( ) method retrieves them. Call</p>
<p>lastInsertId( ) on your PDO object to get the auto-generated ID of the last inserted row. Some database</p>
<p>backends also let you pass a sequence name to lastInsertId( ) to get the last value from the sequence.</p>
<p>当这个数据库保护ID自动数值、这个PDO::lastInsertId()方法重新找回这些，调用lastInsertId()在你的PDO对象获得这</p>
<p>个auto-generated ID的最后嵌入行。一些数据库同样获得一个sequence 名字到lastInsetID()获得最后的数据从这个</p>
<p>sequence</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/183/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.8使用一个Query找到返回行数</title>
		<link>http://blog.phpman.info/archives/179</link>
		<comments>http://blog.phpman.info/archives/179#comments</comments>
		<pubDate>Sun, 11 Nov 2007 09:21:51 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/179</guid>
		<description><![CDATA[10.8.1问题
You want to know how many rows a SELECT query returned, or you want to know how many rows were changed by an INSERT, UPDATE, or DELETE query.
你想要知道query返回多少行。或者你想知道多少行改变一个INSERT. UPDATE 或者DELECT去query
10.8.2解答
If you&#8217;re issuing an INSERT, UPDATE, or DELETE with PDO::exec( ), the return value from exec( ) is the number of modified rows.
如果你讨论一个 INSERT. UPDATE或者DELETE和PDO::exec()这个返回数值从exec()是这个修正的行数
If you&#8217;re [...]]]></description>
			<content:encoded><![CDATA[<p>10.8.1问题<br />
You want to know how many rows a SELECT query returned, or you want to know how many rows were changed by an INSERT, UPDATE, or DELETE query.</p>
<p>你想要知道query返回多少行。或者你想知道多少行改变一个INSERT. UPDATE 或者DELECT去query</p>
<p>10.8.2解答<br />
If you&#8217;re issuing an INSERT, UPDATE, or DELETE with PDO::exec( ), the return value from exec( ) is the number of modified rows.</p>
<p>如果你讨论一个 INSERT. UPDATE或者DELETE和PDO::exec()这个返回数值从exec()是这个修正的行数</p>
<p>If you&#8217;re issuing an INSERT, UPDATE, or DELETE with PDO::prepare( ) and PDOStatement::execute( ), call PDOStatement::rowCount( ) to get the number of modified rows, as shown in Example 10-22.<br />
如果讨论一个INSERT、UPDATE或者DELETE和PDO::prepare()和PDOStatement::execue()调用PDOStatement::rowCount()去获得这个修正的行数。例如在例子10-22<br />
<code><br />
?php<br />
$st = $db-&gt;prepare(&#8217;DELETE FROM family WHERE name LIKE ?&#8217;);<br />
$st-&gt;execute(array(&#8217;Fredo&#8217;));<br />
print &#8220;Deleted rows: &#8221; . $st-&gt;rowCount();<br />
$st-&gt;execute(array(&#8217;Sonny&#8217;));<br />
print &#8220;Deleted rows: &#8221; . $st-&gt;rowCount();<br />
$st-&gt;execute(array(&#8217;Luca Brasi&#8217;));<br />
print &#8220;Deleted rows: &#8221; . $st-&gt;rowCount();<br />
</code></p>
<p>If you&#8217;re issuing a SELECT statement, the only foolproof way to find out how many rows are returned is to retrieve them all with fetchAll( ) and then count how many rows you have, as shown in Example 10-23.</p>
<p>如果你讨论一个SELECT指令。这个唯一的十分简单的办法去找出返回行数重新找出所有fetchAll()和然后计算你的行数例如在例子10-23</p>
<p><code><br />
?php<br />
$st = $db-&gt;query(&#8217;SELECT symbol,planet FROM zodiac&#8217;);<br />
$all= $st-&gt;fetchAll(PDO::FETCH_COLUMN, 1);<br />
print &#8220;Retrieved &#8220;. count($all) . &#8221; rows&#8221;;<br />
</code></p>
<p>10.8.3讨论<br />
Although some database backends provide information to PDO about the number of rows retrieved by a SELECT so that rowCount( ) can work in those circumstances, not all do. So relying on that behavior isn&#8217;t a good idea.</p>
<p>尽管一些数据库规定信息到PDO重新找回的行数用一个SELECT所有这个rowCount()可以工作既然这样。不是全部所有依靠它不是一个好主意</p>
<p>However, retrieving everything in a large result set can be inefficient. As an alternative, ask the database to calculate a result set size with the COUNT(*) function. Use the same WHERE clause as you would otherwise, but ask SELECT to return COUNT(*) instead of a list of fields<br />
尽管重新找回一个大的结果设置效率低的二者选其一。询问这个数据库计算一个结果发送这个COUNT(*)函数。使用这个一样的WHERE条款当作其他，但是查询SELECT返回COUNT(*)代替这个目录文件</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/179/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.7 重复有效查询</title>
		<link>http://blog.phpman.info/archives/178</link>
		<comments>http://blog.phpman.info/archives/178#comments</comments>
		<pubDate>Sun, 11 Nov 2007 08:47:58 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/178</guid>
		<description><![CDATA[10.7.1问题
You want to run the same query multiple times, substituting in different values each time.
你想要运行一样的查询语句取代不同的数值在每个时间
10.7.2解答
Set up the query with PDO::prepare( ) and then run it by calling execute( ) on the prepared statement
that prepare( ) returns. The placeholders in the query passed to prepare( ) are replaced with data by
execute( ), as shown in Example [...]]]></description>
			<content:encoded><![CDATA[<p>10.7.1问题<br />
You want to run the same query multiple times, substituting in different values each time.</p>
<p>你想要运行一样的查询语句取代不同的数值在每个时间</p>
<p>10.7.2解答<br />
Set up the query with PDO::prepare( ) and then run it by calling execute( ) on the prepared statement</p>
<p>that prepare( ) returns. The placeholders in the query passed to prepare( ) are replaced with data by</p>
<p>execute( ), as shown in Example 10-17.</p>
<p>设置这个query和PDO::prepare()然后运行它调用execute()在这个编报表。这个prepare()返回，这个占位符在这个</p>
<p>query通过到prepare()替换用execute()这个数据。例如在例子10-17<br />
<code><br />
?php<br />
// Prepare<br />
$st = $db-&gt;prepare("SELECT sign FROM zodiac WHERE element LIKE ?");<br />
// Execute once<br />
$st-&gt;execute(array('fire'));<br />
while ($row = $st-&gt;fetch()) {<br />
    print $row[0] . "&lt;br/&gt;\n";<br />
}<br />
// Execute again<br />
$st-&gt;execute(array('water'));<br />
while ($row = $st-&gt;fetch()) {<br />
    print $row[0] . "&lt;br/&gt;\n";<br />
}<br />
</code></p>
<p>10.7.3讨论<br />
The values passed to execute( ) are called bound parameters&#8217;each value is associated with (or &#8220;bound to&#8221;)</p>
<p>a placeholder in the query. Two great things about bound parameters are security and speed. With bound</p>
<p>parameters, you don&#8217;t have to worry about SQL injection attacks. PDO appropriately quotes and escapes</p>
<p>each parameter so that special characters are neutralized. Also, upon prepare( ), many database backends</p>
<p>do some parsing and optimizing of the query, so each call to execute( ) is faster than calling exec( ) or</p>
<p>query( ) with a fully formed query in a string you&#8217;ve built yourself.</p>
<p>这个数值通过到execute()是调用限制参数的每个值是联合(or &#8220;bound to&#8221;)一个占位符在query。两个顺利的事情跳过这</p>
<p>个安全的参数，限制参数，你不用担心SQL受攻击PDO适当的引证躲避每个参数所以它的特殊字符压制同样upon perpare</p>
<p>()很多数据库使它最优化所以每个调用exexute(0是更快于调用exex()或者query()和一个完全的formed查询在一个字符</p>
<p>串本身</p>
<p>In Example 10-17, the first execute( ) runs the query SELECT sign FROM zodiac WHERE element LIKE &#8216;fire&#8217;.</p>
<p>The second execute( ) runs SELECT sign FROM zodiac WHERE element LIKE &#8216;water&#8217;.</p>
<p>在例子10-17.这第一个execute()运行这个query SELECT标记FROM在每个元素像 &#8216;fire&#8217; 这个第二个execute()运行</p>
<p>SELECT标记FROM在WHERE元素像&#8217;water&#8217;<br />
Each time, execute( ) substitutes the value in its second argument for the ? placeholder. If there is</p>
<p>more than one placeholder, put the arguments in the array in the order they should appear in the query.</p>
<p>Example 10-18 shows prepare( ) and execute( ) with two placeholders.</p>
<p>每时。execute()提交这个值在第二个论点对于这个?占位符。如果它是多于1个的占位符，防止这个论点在这个数组应该</p>
<p>整齐的显示在这个query例子10-18展示prepare()和execute()和两个占位符<br />
<code><br />
?php</code><code>$st = $db-&gt;prepare(<br />
    "SELECT sign FROM zodiac WHERE element LIKE ? OR planet LIKE ?");</code><code>// SELECT sign FROM zodiac WHERE element LIKE 'earth' OR planet LIKE 'Mars'<br />
$st-&gt;execute(array('earth','Mars'));</p>
<p>In addition to the ? placeholder style, PDO also supports named placeholders. If you've got a lot of</p>
<p>placeholders in a query, this can make them easier to read. Instead of ?, put a placeholder name (which</p>
<p></code>has to begin with a colon) in the query, and then use those placeholder names (without the colons) as</p>
<p>keys in the parameter array you pass to execute( ). Example 10-19 shows named placeholders in action.</p>
<p>除了这个?占位符之外、PDO同样支持指定占位符。如果你获得许多的占位符在一个query他们可以更加容易去读，代替放</p>
<p>置一个占位符在这个query然后使用这些指定占位符当作键在这个参数数组通过到execute()例如10-19显示指定占位符的</p>
<p>操作<br />
<code><br />
?php<br />
$st = $db-&gt;prepare(<br />
    "SELECT sign FROM zodiac WHERE element LIKE :element OR planet LIKE :planet");<br />
// SELECT sign FROM zodiac WHERE element LIKE 'earth' OR planet LIKE 'Mars'<br />
$st-&gt;execute(array('planet' =&gt; 'Mars', 'element' =&gt; 'earth'));<br />
$row = $st-&gt;fetch();<br />
</code></p>
<p>With named placeholders, your queries are easier to read and you can provide the values to execute( ) in</p>
<p>any order. Note, though, that each placeholder name can only appear in a query once. If you want to</p>
<p>provide the same value more than once in a query, use two different placeholder names and include the</p>
<p>value twice in the array passed to execute( ).</p>
<p>用指定占位符，你更加容易去查询阅读你可以规定execute()除外的数值，注意。虽然这每个指定占位符仅仅显示在一个</p>
<p>query。如果你想要规定一样的数值在一个query。使用两个不同的指定占位符和包括这个数值在这个数组通过execute()</p>
<p><code><br />
?php<br />
$pairs = array('Mars' =&gt; 'water',<br />
               'Moon' =&gt; 'water',<br />
               'Sun' =&gt; 'fire');<br />
$st = $db-&gt;prepare(<br />
    "SELECT sign FROM zodiac WHERE element LIKE :element AND planet LIKE :planet");<br />
$st-&gt;bindParam(':element', $element);<br />
$st-&gt;bindparam(':planet', $planet);<br />
foreach ($pairs as $planet =&gt; $element) {<br />
    // No need to pass anything to execute() --<br />
    // the values come from $element and $planet<br />
    $st-&gt;execute();<br />
    var_dump($st-&gt;fetch());<br />
}<br />
</code></p>
<p>In Example 10-20, there&#8217;s no need to pass any values to execute( ). The two calls to bindParam( ) tell</p>
<p>PDO &#8220;whenever you execute $st, use whatever&#8217;s in the $element variable for the :element placeholder and</p>
<p>whatever&#8217;s in the $planet variable for the :planet placeholder.&#8221; The values in those variables when you</p>
<p>call bindParam( ) don&#8217;t matter&#8217;it&#8217;s the values in those variables when execute( ) is called that counts.</p>
<p>Since the foreach statement puts array keys in $planet and array values in $element, the keys and values</p>
<p>from $pairs are substituted into the query.<br />
在例子10-20.这些不需要通过一些儿数值到execute()。这两个调用到bindParam(0告诉PDO &#8220;whenever you execute $st</p>
<p>使用每个在这个$element数值对于这个:element占位符和whatever&#8217;s在这个$plant 变量对于这个:planet placeholder&#8221;</p>
<p>这个数值在这些便可当你调用bindParam()不是很重要的这个数值在这些变量当execute()调用这些计算从这个延伸生命</p>
<p>放置数组键在$plant和数组值在$element这个键和数值从$pairs是提交到这个query<br />
<code><br />
?php<br />
$st = $db-&gt;prepare('INSERT INTO files (path,contents) VALUES (:path,:contents)');<br />
$st-&gt;bindParam(':path',$path);<br />
$st-&gt;bindParam(':contents',$fp,PDO::PARAM_LOB);<br />
foreach (glob('c:/documents/*.*') as $path) {<br />
    // Get a filehandle that PDO::PARAM_LOB can work with<br />
    $fp = fopen($path,'r');<br />
    $st-&gt;execute();<br />
}<br />
</code><br />
Using PDO::PARAM_LOB effectively depends on your underlying database. For example, with Oracle your querymust create an empty LOB handle and be inside a transaction. The &#8220;Inserting an image into a database:Oracle&#8221; example of the PDO manpage at <a href="http://www.php.net/PDO">http://www.php.net/PDO</a> shows the proper syntax to do this.<br />
使用PDO::PARAM_LOB 有效的依靠你的潜在的数据库。例如。和你的查询必须创造一个空的LOB操作在你的一个处理、这</p>
<p>个&#8221;Inserting an image into a database:砸合格PDO manpage在<a href="http://www.php.net/PDO">http://www.php.net/PDO</a> 显示正确的语法</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/178/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.6在SQL数据库修改数据</title>
		<link>http://blog.phpman.info/archives/177</link>
		<comments>http://blog.phpman.info/archives/177#comments</comments>
		<pubDate>Sat, 10 Nov 2007 04:03:47 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/177</guid>
		<description><![CDATA[10.6.1问题
You want to add, remove, or change data in an SQL database.
你想要在数据库里增加，移动或者修改数据
10.6.2解答
Use PDO::exec( ) to send an INSERT, DELETE, or UPDATE command, as shown in Example 10-14.
使用PDO::exec()去发送一个INSERT. DELETE或者UPDATE命令。例如在例子10-14

?php
$db-&#62;exec("INSERT INTO family (id,name) VALUES (1,'Vito')")
$db-&#62;exec("DELETE FROM family WHERE name LIKE 'Fredo'");
$db-&#62;exec("UPDATE family SET is_naive = 1 WHERE name LIKE 'Kay'");

You can also prepare a query with PDO::prepare( [...]]]></description>
			<content:encoded><![CDATA[<p>10.6.1问题<br />
You want to add, remove, or change data in an SQL database.<br />
你想要在数据库里增加，移动或者修改数据</p>
<p>10.6.2解答<br />
Use PDO::exec( ) to send an INSERT, DELETE, or UPDATE command, as shown in Example 10-14.<br />
使用PDO::exec()去发送一个INSERT. DELETE或者UPDATE命令。例如在例子10-14<br />
<code><br />
?php<br />
$db-&gt;exec("INSERT INTO family (id,name) VALUES (1,'Vito')")<br />
$db-&gt;exec("DELETE FROM family WHERE name LIKE 'Fredo'");<br />
$db-&gt;exec("UPDATE family SET is_naive = 1 WHERE name LIKE 'Kay'");<br />
</code><br />
You can also prepare a query with PDO::prepare( ) and execute it with PDOStatement::execute( ), as shown</p>
<p>in Example 10-15.</p>
<p>你同样可以准备一个查询和PDO::prepare()和执行它和PDOtatement::execute()。例如在例子10-15</p>
<p><code><br />
?php<br />
$st = $db-&gt;prepare('INSERT INTO family (id,name) VALUES (?,?)');<br />
$st-&gt;execute(array(1,'Vito'));<br />
$st = $db-&gt;prepare('DELETE FROM family WHERE name LIKE ?');<br />
$st-&gt;execute(array('Fredo'));<br />
$st = $db-&gt;prepare('UPDATE family SET is_naive = ? WHERE name LIKE ?');<br />
$st-&gt;execute(array(1,'Kay');<br />
</code></p>
<p>10.6.3讨论<br />
The exec( ) method sends to the database whatever it&#8217;s passed. For INSERT, UPDATE, and DELETE queries, it</p>
<p>returns the number of rows affected by the query.</p>
<p>这个exec()方法发送到数据库通过。对于INSERT. UPDATE和DELETE查询，它返回这行查询的数字<br />
The prepare( ) and execute( ) methods are especially useful for queries that you want to execute multiple</p>
<p>times. Once you&#8217;ve prepared a query, you can execute it with new values without re-preparing it. Example</p>
<p>10-16 reuses the same prepared query three times.</p>
<p>这个prepare()和execute()方法是特别有用于查询你想要的多个时间。以前你准备好一个查询，你可以执行它和一个新</p>
<p>的re-preparing例如10-16重新使用一样的三个查询时间</p>
<p><code><br />
&lt;?php<br />
$st = $db-&gt;prepare('DELETE FROM family WHERE name LIKE ?');<br />
$st-&gt;execute(array('Fredo'));<br />
$st-&gt;execute(array('Sonny'));<br />
$st-&gt;execute(array('Luca Brasi'));<br />
</code></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/177/feed</wfw:commentRss>
		</item>
		<item>
		<title>10.5 找出每行的循环</title>
		<link>http://blog.phpman.info/archives/176</link>
		<comments>http://blog.phpman.info/archives/176#comments</comments>
		<pubDate>Sat, 10 Nov 2007 03:54:59 +0000</pubDate>
		<dc:creator>dgz</dc:creator>
		
		<category><![CDATA[未分类]]></category>

		<guid isPermaLink="false">http://blog.phpman.info/archives/176</guid>
		<description><![CDATA[10.5.1问题
You want a concise way to execute a query and retrieve the data it returns.
你想要一个简单的办法去执行一个查询和找回这个数据返回
10.5.2解答
Use fetchAll( ) to get all the results from a query at once, as shown in Example 10-13.
使用fetchAll()去获得所有的结果从一个查询。例如在例子10-13

?php
$st = $db-&#62;query('SELECT planet, element FROM zodiac');
$results = $st-&#62;fetchAll();
foreach ($results as $i =&#62; $result) {
   print "Planet $i is {$result['planet']} &#60;br/&#62;\n";
}

10.5.3讨论
The fetchAll( ) method [...]]]></description>
			<content:encoded><![CDATA[<p>10.5.1问题<br />
You want a concise way to execute a query and retrieve the data it returns.<br />
你想要一个简单的办法去执行一个查询和找回这个数据返回</p>
<p>10.5.2解答<br />
Use fetchAll( ) to get all the results from a query at once, as shown in Example 10-13.</p>
<p>使用fetchAll()去获得所有的结果从一个查询。例如在例子10-13<br />
<code><br />
?php<br />
$st = $db-&gt;query('SELECT planet, element FROM zodiac');<br />
$results = $st-&gt;fetchAll();<br />
foreach ($results as $i =&gt; $result) {<br />
   print "Planet $i is {$result['planet']} &lt;br/&gt;\n";<br />
}<br />
</code></p>
<p>10.5.3讨论</p>
<p>The fetchAll( ) method is useful when you need to do something that depends on all the rows a query</p>
<p>returns, such as counting how many rows there are or handling rows out of order. Like fetch( ), fetchAll(</p>
<p>) defaults to representing each row as an array with both numeric and string keys and accepts the various</p>
<p>PDO::FETCH_* constants to change that behavior.<br />
这个fetchAll()方法是有用的。当你需要这些在所有的行一个查询返回，例如计算在那里有多少行或者处理每行的顺序</p>
<p>。例如fetch()、fetchALL()默认表现每行当作一个数组、数字、字符串键和认可PDO::FETCH_* constants去改变这个行</p>
<p>为</p>
<p>fetchAll( ) also accepts a few other constants that affect the results it returns. To retrieve just a</p>
<p>single column from the results, pass PDO::FETCH_COLUMN and a second argument, the index of the column you</p>
<p>want. The first column is 0, not 1.</p>
<p>fetchAll()同样认可一个少量常量影响返回结果。去重新找回单一的结果。通过PDO::FETCH_COLUMN和一个第二个论点这</p>
<p>个column的索引是你想要的。这第一个column是0.不是1</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.phpman.info/archives/176/feed</wfw:commentRss>
		</item>
	</channel>
</rss>
