﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>C++博客-漫步者-文章分类-C&amp;C plus plus</title><link>http://www.cppblog.com/Walker/category/16499.html</link><description>先学会转文章，在仔细读文章，最后自己写点东西........</description><language>zh-cn</language><lastBuildDate>Sun, 24 Apr 2011 23:37:40 GMT</lastBuildDate><pubDate>Sun, 24 Apr 2011 23:37:40 GMT</pubDate><ttl>60</ttl><item><title>SDI Minimize and Maxinum  flash windw</title><link>http://www.cppblog.com/Walker/articles/144094.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Wed, 13 Apr 2011 02:02:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/144094.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/144094.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/144094.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/144094.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/144094.html</trackback:ping><description><![CDATA[<h2>Why the flash occurs</h2>
<p>In order to understand why the application does not minimize properly, we need to look into the MFC code that constructs and displays the main window. By placing a breakpoint in the <code><font color=#990000>ProcesShellCommand</font></code> function, we see that, by default, the AppWnd <code><font color=#990000>OnFileNew</font></code> handler is called. <code><font color=#990000>OnFileNew</font></code> calls the <code><font color=#990000>CDocument* CDocument* CSingleDocTemplate::OpenDocumentFile(LPCTSTR lpszPathName,BOOL bMakeVisible) OpenDocument</font></code>, which creates a new document instance, creates a new frame for the document, and finally displays the window by calling <code><font color=#990000>InitialUpdateFrame(pFrame, pDocument, bMakeVisible);</font></code>, and displays the view and the mainframe window. The reason why the application does not display correctly when a different SW parameter is chosen instead of <code><font color=#990000>SW_SHOW</font></code>, is because <code><font color=#990000>InitialUpdateFrame</font></code> <code><font color=#990000>CFrameWnd::ActivateFrame()</font></code> calls <code><font color=#990000>ShowWindow</font></code> during the initialization of the window in the function. This implies that the call to <code><font color=#990000>ShowWindow</font></code> in <code><font color=#990000>InitInstance()</font></code> is redundant and not needed.</p>
<h2>The solution</h2>
<p>There are two solutions that can be used to solve the flashing problem. The first solution is to make a subclass of the <code><font color=#990000>SingleDocumentTemplate</font></code> and call our derived version of <code><font color=#990000>OpenDocument</font></code> with <code><font color=#990000>bMakeVisible = </font><span class=code-keyword><font color=#0000ff>false</font></span></code> for the minimized case. This, however, does not solve the case of using <code><font color=#990000>SW_MAXMIMIZE</font></code>. Another solution, which is far more simpler and can be used for any <code><font color=#990000>ShowWIndow</font></code> mode, is to set the application <code><font color=#990000>ShowWindow</font></code> property prior to initializing the window, as shown below:</p>
<div style="DISPLAY: block" id=premain3 class="small-text align-right" width="100%"><img style="CURSOR: pointer" id=preimg3 src="http://www.codeproject.com/images/minus.gif" width=9 height=9 preid="3"><span style="MARGIN-BOTTOM: 0px; CURSOR: pointer" id=precollapse3 preid="3"> Collapse</span><span> | </span><a href="http://www.codeproject.com/KB/MFC/NoFlashSDI.aspx#" preid="3"><font color=#004cd5>Copy Code</font></a></div>
<pre style="MARGIN-TOP: 0px" id=pre3>        CSingleDocTemplate * pDocTemplate;
pDocTemplate = <span class=code-keyword><font color=#0000ff>new</font></span> CSingleDocTemplate (
IDR_MAINFRAME,
RUNTIME_CLASS(CMyMFCProgramDoc),
RUNTIME_CLASS(CMainFrame),       <em><font color=#008000><span class=code-comment>//</span><span class=code-comment> main SDI frame window</span></font></em>
RUNTIME_CLASS(CMyMFCProgramView));
AddDocTemplate(pDocTemplate);
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> Parse command line for standard shell commands, DDE, file open</span></font></em>
CCommandLineInfo cmdInfo;
ParseCommandLine(cmdInfo);
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> Add the following line:</span></font></em>
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> Set the initial window display to whatever mode you like</span></font></em>
<span class=code-keyword><font color=#0000ff>this</font></span>-<span class=code-keyword><font color=#0000ff>&gt;</font></span>m_nCmdShow = SW_MAXIMIZE;
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> Dispatch commands specified on the command line</span></font></em>
<span class=code-keyword><font color=#0000ff>if</font></span> (!ProcessShellCommand(cmdInfo))
<span class=code-keyword><font color=#0000ff>return</font></span> FALSE;
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> The following line should be deleted since it is not needed </span></font></em>
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> for a SDI application that used MFC The one and only window has</span></font></em>
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment> been initialized, so show and update it.</span></font></em>
<em><font color=#008000><span class=code-comment>//</span><span class=code-comment>m_pMainWnd-&gt;ShowWindow(SW_SHOW);</span></font></em>
m_pMainWnd-<span class=code-keyword><font color=#0000ff>&gt;</font></span>UpdateWindow();
<span class=code-keyword><font color=#0000ff>return</font></span> TRUE;</pre>
<p>One may ask if the <code><font color=#990000>ShowWindow()</font></code> line in the <code><font color=#990000>InitInstance</font></code> has no purpose, and why Microsoft put that line there in the first place. The answer is, if one decides to construct an SDI application using the MFC application wizard and checks the option not to use MFC, this line is required to show the window. However, Microsoft should have deleted this line if MFC is used. However, since the vast majority of applications initially display <code><font color=#990000>ShowWindow</font></code> with the <code><font color=#990000>SW_SHOW</font></code> parameter, calling <code><font color=#990000>ShowWindow</font></code> twice (the first time in <code><font color=#990000>ActivateFrame</font></code>, as described above) will not influence the display of the application.</p>
<img src ="http://www.cppblog.com/Walker/aggbug/144094.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2011-04-13 10:02 <a href="http://www.cppblog.com/Walker/articles/144094.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>AfxMessageBoxFormatted and MessageBoxFormatted</title><link>http://www.cppblog.com/Walker/articles/144093.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Wed, 13 Apr 2011 01:50:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/144093.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/144093.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/144093.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/144093.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/144093.html</trackback:ping><description><![CDATA[<span class=code-keyword><font color=#0000ff>void</font></span> AfxMessageBoxFormatted(LPCTSTR pFormatString, ...)<br>{<br>&nbsp;&nbsp;&nbsp; va_list vl;<br>&nbsp;&nbsp;&nbsp; va_start(vl, pFormatString);&lt;br&gt;<br>&nbsp;&nbsp;&nbsp; CString strFormat;<br>&nbsp;&nbsp;&nbsp; strFormat.FormatV(pFormatString, vl); <span class=code-comment><em><font color=#008000>//</font></em></span><span class=code-comment><em><font color=#008000> This Line is important!&lt;br&gt;<br></font></em></span>&nbsp;&nbsp;&nbsp; <span class=code-comment><em><font color=#008000>//</font></em></span><span class=code-comment><em><font color=#008000> Display message box. <br></font></em></span>&nbsp;&nbsp;&nbsp; AfxMessageBox(strFormat);<br>}<br><br><span class=code-keyword><font color=#0000ff>void</font></span> MessageBoxFormatted(HWND hWnd, LPCTSTR pCaption, LPCTSTR pFormatString, ...)<br>{<br>&nbsp;&nbsp;&nbsp; va_list vl;<br>&nbsp;&nbsp;&nbsp; va_start(vl, pFormatString);&lt;br&gt;&nbsp;&nbsp;&nbsp; <br>&nbsp;&nbsp;&nbsp; TCHAR strFormat[<span class=code-digit><font color=#000080>1024</font></span>]; <span class=code-comment><em><font color=#008000>//</font></em></span><em><font color=#008000><span class=code-comment> Must ensure size!&lt;br&gt;<br></span><br></font></em>&nbsp;&nbsp;&nbsp; <span class=code-comment><em><font color=#008000>//</font></em></span><span class=code-comment><em><font color=#008000> Generic version of vsprintf, works for both MBCS and Unicode builds <br></font></em></span>&nbsp;&nbsp;&nbsp; _vstprintf(strFormat, pFormatString, vl);&lt;br&gt; <br>&nbsp;&nbsp;&nbsp; <span class=code-comment><em><font color=#008000>//</font></em></span><span class=code-comment><em><font color=#008000> Or use following for more secure code<br></font></em></span>&nbsp;&nbsp;&nbsp; <span class=code-comment><em><font color=#008000>//</font></em></span><span class=code-comment><em><font color=#008000> _vstprintf_s(strFormat, sizeof(strFormat), pFormatString, vl)&lt;br&gt;<br></font></em></span>&nbsp;&nbsp;&nbsp; ::MessageBox(hWnd, strFormat, pCaption,MB_ICONINFORMATION);<br>}
<img src ="http://www.cppblog.com/Walker/aggbug/144093.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2011-04-13 09:50 <a href="http://www.cppblog.com/Walker/articles/144093.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>函数指针</title><link>http://www.cppblog.com/Walker/articles/144092.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Wed, 13 Apr 2011 01:48:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/144092.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/144092.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/144092.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/144092.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/144092.html</trackback:ping><description><![CDATA[<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">在程序运行中，函数代码是程序的算法指令部分，它们和数组一样也占用存储空间，都有相应的地址。可以使用指针变量指向数组的首地址，也可以使用指针变量指向函数代码的首地址，指向函数代码首地址的指针变量称为函数指针。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>1</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">．函数指针定义</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>函数类型</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt"> </span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>（</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>*</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>指针变量名）</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>(</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>形参列表</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>)</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">；</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&#8220;</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>函数类型</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&#8221;</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>说明函数的返回类型，由于</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&#8220;()&#8221;</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>的优先级高于</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&#8220;*&#8221;,</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>所以指针变量名外的括号必不可少，后面的</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&#8220;</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>形参列表</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&#8221;</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">表示指针变量指向的函数所带的参数列表。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">例如：</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>int (*f)(int x);</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>double (*ptr)(double x);</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>在定义函数指针时请注意：</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US><br>&nbsp;&nbsp;&nbsp; <br></span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>函数指针和它指向的函数的参数个数和类型都应该是</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>—</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">致的；</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">函数指针的类型和函数的返回值类型也必须是一致的。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>2</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">．函数指针的赋值</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">函数名和数组名一样代表了函数代码的首地址，因此在赋值时，直接将函数指针指向函数名就行了。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">例如，</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>int func(int x);&nbsp;&nbsp; /* </span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>声明一个函数</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US> */</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>int (*f) (int x);&nbsp;&nbsp;&nbsp; /* </span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>声明一个函数指针</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US> */</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>f=func;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; /* </span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>将</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>函数的首地址赋给指针</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>f */</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>赋值时函数</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>不带括号，也不带参数，由于</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>代表函数的首地址，因此经过赋值以后，指针</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>f</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>就指向函数</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func(x)</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">的代码的首地址。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>3</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">．通过函数指针调用函数</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">函数指针是通过函数名及有关参数进行调用的。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>与其他指针变量相类似，如果指针变量</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>pi</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>是指向某整型变量</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>i</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>的指针，则</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>*p</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>等于它所指的变量</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>i</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>；如果</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>pf</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>是指向某浮点型变量</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>f</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>的指针，则</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>*pf</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>就等价于它所指的变量</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>f</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>。同样地，</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>*f</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>是指向函数</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func(x)</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>的指针，则</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>*f</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>就代表它所指向的函数</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>。所以在执行了</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>f=func;</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>之后，</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>(*f)</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>和</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>func</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">代表同一函数。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">由于函数指针指向存储区中的某个函数，因此可以通过函数指针调用相应的函数。现在我们就讨论如何用函数指针调用函数，它应执行下面三步：</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">首先，要说明函数指针变量。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>例如：</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>int (*f)(int x);</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">其次，要对函数指针变量赋值。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>例如：</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US> f=func;&nbsp;&nbsp;&nbsp; (func(x)</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>必须先要有定义</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>)</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>最后，要用</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US> (*</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>指针变量</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>)(</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>参数表</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>);</span><font face=宋体><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial">调用函数。</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></font></p>
<p style="LINE-HEIGHT: 11.5pt"><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>例如：</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>&nbsp;&nbsp;&nbsp; (*f)(x);(x</span><span style="COLOR: #333333; FONT-SIZE: 10pt; mso-ascii-font-family: Arial; mso-hansi-font-family: Arial; mso-bidi-font-family: Arial"><font face=宋体>必须先赋值</font></span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 10pt" lang=EN-US>)</span><span style="FONT-FAMILY: Arial; COLOR: #333333; FONT-SIZE: 8pt" lang=EN-US><o:p></o:p></span></p>
<img src ="http://www.cppblog.com/Walker/aggbug/144092.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2011-04-13 09:48 <a href="http://www.cppblog.com/Walker/articles/144092.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>What are TCHAR, WCHAR, LPSTR, LPWSTR, LPCTSTR etc?</title><link>http://www.cppblog.com/Walker/articles/144091.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Wed, 13 Apr 2011 01:47:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/144091.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/144091.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/144091.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/144091.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/144091.html</trackback:ping><description><![CDATA[&nbsp;
<p><strong><span>VC </span></strong><strong><span>字符串相关宏</span></strong><strong><span> _T</span></strong><strong><span>、</span></strong><strong><span>TEXT,_TEXT</span></strong><strong><span>、</span></strong><strong><span>L </span></strong><strong><span>的作用</span></strong><strong></strong></p>
<p><span>一、</span> <span>在字符串前加一个</span><span>L</span><span>作用</span><span>: </span></p>
<p><span><span>&nbsp;&nbsp; </span></span><span>如</span><span>&nbsp;L"</span><span>我的字符串</span><span>"<span>&nbsp;&nbsp;&nbsp; </span></span><span>表示将</span><span>ANSI</span><span>字符串转换成</span><span>unicode</span><span>的字符串，就是每个字符占用两个字节。</span></p>
<p><span>&nbsp;strlen("asd")<span>&nbsp;&nbsp; </span>=<span>&nbsp;&nbsp; </span>3;<span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;strlen(L"asd")<span>&nbsp;&nbsp; </span>=<span>&nbsp;&nbsp; </span>6;</span></p>
<p>&nbsp;</p>
<p><span>二、</span><span>&nbsp;_T</span><span>宏可以把一个引号引起来的字符串，根据你的环境设置，使得编译器会根据编译目标环境选择合适的（</span><span>Unicode</span><span>还是</span><span>ANSI</span><span>）字符处理方式</span></p>
<p><span><span>&nbsp;&nbsp; </span></span><span>如果你定义了</span><span>UNICODE</span><span>，那么</span><span>_T</span><span>宏会把字符串前面加一个</span><span>L</span><span>。这时</span><span> _T("ABCD") </span><span>相当于</span><span> L"ABCD" </span><span>，这是宽字符串。</span><span> </span></p>
<p><span><span>&nbsp;&nbsp; </span></span><span>如果没有定义，那么</span><span>_T</span><span>宏不会在字符串前面加那个</span><span>L</span><span>，</span><span>_T("ABCD") </span><span>就等价于</span><span> "ABCD"</span></p>
<p>&nbsp;</p>
<p><span>三、</span><span>TEXT,_TEXT </span><span>和</span><span>_T </span><span>一样的</span></p>
<p>&nbsp;</p>
<p><span>如下面三语句：</span><span><span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;TCHAR<span>&nbsp;&nbsp; </span>szStr1[]<span>&nbsp;&nbsp; </span>=<span>&nbsp;&nbsp; </span>TEXT("str1");<span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;char<span>&nbsp;&nbsp; </span>szStr2[]<span>&nbsp;&nbsp; </span>=<span>&nbsp;&nbsp; </span>"str2";<span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;WCHAR<span>&nbsp;&nbsp; </span>szStr3[]<span>&nbsp;&nbsp; </span>=<span>&nbsp;&nbsp; </span>L("str3");<span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;</span><span>那么第一句话在定义了</span><span>UNICODE</span><span>时会解释为第三句话，没有定义时就等于第二句话。</span><span>&nbsp;</span></p>
<p><span>&nbsp;</span><span>但二句话无论是否定义了</span><span>UNICODE</span><span>都是生成一个</span><span>ANSI</span><span>字符串，而第三句话总是生成</span><span>UNICODE</span><span>字符串。</span><span><span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;</span><span>为了程序的可移植性，建议都用第一种表示方法。</span><span><span>&nbsp;&nbsp; </span></span></p>
<p><span>&nbsp;</span><span>但在某些情况下，某个字符必须为</span><span>ANSI</span><span>或</span><span>UNICODE</span><span>，那就用后两种方法。</span></p>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p align=left><span>Many C++ Windows programmers get confused over what bizarre identifiers like </span><span>TCHAR</span><span>, </span><span>LPCTSTR</span><span> are. Here, in brief, I would try to clear out the fog.<br><br>In general, a character can be 1 byte or 2 bytes. Lets say 1-byte character is ANSI, using which English characters are represented. And lets say 2-byte character is Unicode, which can represent ALL languages in the world. <br><br>VC++ support </span><span>char</span><span> and </span><span>wchar_t</span><span> as native datatypes for ANSI and Unicode characters respectively.<br><br>What if you want your C/C++ program to be Character-mode independent? <br>That means, instead of replacing:</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>char</span><span> cResponse; <em><span>// 'Y' or 'N'<br></span></em><span>char</span> sUsername[<span>64</span>];<br><em><span>// str* functions</span></em></span></p>
</div>
<p align=left><span>with</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>wchar_t</span><span> cResponse; <em><span>// 'Y' or 'N'<br></span></em><span>wchar_t</span> sUsername[<span>64</span>];<br><em><span>// wcs* functions</span></em></span></p>
</div>
<p align=left><span>You can simply code it:</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>#include</span><span>&lt;</span><span>TCHAR.H</span><span>&gt;</span><span> // Implicit or explicit include<br></span><span>TCHAR cResponse; <em><span>// 'Y' or 'N'<br></span></em>TCHAR sUsername[<span>64</span>];<br><em><span>// _tcs* functions</span></em></span></p>
</div>
<p align=left><span>Thus, when your project is being compiled as Unicode, the </span><span>TCHAR </span><span>would translate to </span><span>wchar_t</span><span>. If it is being compiled as ANSI/MBCS, it would translated to </span><span>char</span><span>. Likewise, instead of using </span><span>strcpy</span><span>, </span><span>strlen</span><span>, </span><span>strcat</span><span> (including the secure versions suffixed with <strong>_s</strong>); or </span><span>wcscpy</span><span>, </span><span>wcslen</span><span>, </span><span>wcscat</span><span> (including secure), you can simply use </span><span>_tcscpy</span><span>, </span><span>_tcslen</span><span>, </span><span>_tcscat</span><span> functions. <br><br>When you need to express hard-coded string, you can use:</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>"ANSI String"</span><span>; <em><span>// ANSI<br></span></em>L<span>"Unicode String"</span>; <em><span>// Unicode<br></span></em><br>_T(<span>"Either string, depending on compilation"</span>); <em><span>// ANSI or Unicode<br>// or use TEXT macro, if you need more readability.</span></em></span></p>
</div>
<p align=left><span>The non-prefixed string is ANSI string, the <strong>L</strong> prefixed string is Unicode, and string specified in </span><span>_T</span><span> or </span><span>TEXT</span><span> would be either, depending on compilation.<br><br><br>String classes, like MFC/ATL's </span><span>CString</span><span> implement two version using macro. There are two classes named </span><span>CStringA</span><span> for ANSI, </span><span>CStringW</span><span> for Unicode. When you use </span><span>CString</span><span> (which is a <strong>macro/typedef</strong>), it translates to either of two classes.</span></p>
<div align=center><span>
<hr align=center SIZE=2 width="100%">
</span></div>
<p align=left><span>Okay. The </span><span>TCHAR</span><span> type-definition was for a single character. You can definitely declare an array of TCHAR. <br>What if you want to express a <em>character-pointer</em>, or a <em>const-character-pointer</em> - Which one of the following?</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><em><span>// ANSI characters<br></span></em><span>foo_ansi(<span>char</span>*);<br>foo_ansi(<span>const</span> <span>char</span>*);<br><em><span>/*const*/</span></em> <span>char</span>* pString;<br><br><em><span>// Unicode/wide-string<br></span></em>foo_uni(WCHAR*); <em><span>// or wchar_t*<br></span></em>foo_uni(<span>const</span> WCHAR*);<br><em><span>/*const*/</span></em> WCHAR* pString;<br><br><em><span>// Independent <br></span></em>foo_char(TCHAR*);<br>foo_char(<span>const</span> TCHAR*);<br><em><span>/*const*/</span></em> TCHAR* pString;</span></p>
</div>
<p align=left><span>After reading about </span><span>TCHAR</span><span> stuff, you'd definitely select the last one as your choice. But here is better alternative. Before that, note that </span><span>TCHAR.H</span><span> header file declares <strong>only</strong> </span><span>TCHAR</span><span> datatype and for the following stuff, you need to include </span><span>Windows.h</span><span> (defined in </span><span>WinNT.h</span><span>).<br><br>NOTE: If your project implicitly or explicitly includes </span><span>Windows.h</span><span>, you need not to include </span><span>TCHAR.H</span></p>
<ul type=disc>
    <li><strong><span>char*</span></strong><span> replacement: </span><strong><span>LPSTR</span></strong></li>
    <li><strong><span>const char*</span></strong><span> replacement: </span><span>LPCSTR</span></li>
    <li><strong><span>WCHAR*</span></strong><span> replacement: </span><strong><span>LPWSTR</span></strong></li>
    <li><strong><span>const WCHAR*</span></strong><span> replacement: </span><strong><span>LPCWSTR</span></strong><span> (<strong>C</strong> before <strong>W</strong>, since </span><span>const</span><span> is before </span><span>WCHAR</span><span>)</span></li>
    <li><strong><span>TCHAR*</span></strong><span> replacement: </span><strong><span>LPTSTR</span></strong></li>
    <li><strong><span>const TCHAR*</span></strong><span> replacement: </span><strong><span>LPCTSTR</span></strong></li>
</ul>
<p align=left><span>Now, I hope, you understand the following signatures :</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>BOOL SetCurrentDirectory( LPCTSTR lpPathName );<br>DWORD GetCurrentDirectory(DWORD nBufferLength,LPTSTR lpBuffer);</span></p>
</div>
<div align=center><span>
<hr align=center SIZE=2 width="100%">
</span></div>
<p align=left><span>Continuing. You must have seen some functions/methods asking you to pass <strong>number of characters</strong>, or returning the number of characters. Well, like </span><span>GetCurrentDirectory</span><span>, you need to pass number of characters, and <strong>not</strong> number of bytes. For example::</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>TCHAR sCurrentDir[<span>255</span>];<br><br><em><span>// Pass 255 and not 255*2 <br></span></em>GetCurrentDirectory(sCurrentDir, <span>255</span>);</span></p>
</div>
<p align=left><span>On the other side, if you need to allocate number or characters, you must allocate proper number of bytes. In C++, you can simply use </span><span>new</span><span>:</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>LPTSTR pBuffer; <em><span>// TCHAR* <br></span></em><br>pBuffer = <span>new</span> TCHAR[<span>128</span>]; <em><span>// Allocates 128 or 256 BYTES, depending on compilation.</span></em></span></p>
</div>
<p align=left><span>But if you use memory allocation functions like </span><span>malloc</span><span>, </span><span>LocalAlloc</span><span>, </span><span>GlobalAlloc</span><span> etc; you must specify the number of bytes!</span></p>
<p align=left><span>Collapse | <a href="http://www.codeproject.com/Tips/76252/What-are-TCHAR-WCHAR-LPSTR-LPWSTR-LPCTSTR-etc.aspx##"><span>Copy Code</span></a></span></p>
<div>
<p align=left><span>pBuffer = (TCHAR*) malloc (<span>128</span> * <span>sizeof</span>(TCHAR) );</span></p>
</div>
<p><span>Typecasting the return value is required, as you know. The expression in malloc's argument ensures that it allocates desired number of bytes - and makes up room for desired number of characters.</span></p>
<p><span><span>1</span></span></p>
<img src ="http://www.cppblog.com/Walker/aggbug/144091.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2011-04-13 09:47 <a href="http://www.cppblog.com/Walker/articles/144091.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>（转）C、C++ 时间 </title><link>http://www.cppblog.com/Walker/articles/81194.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Mon, 27 Apr 2009 03:11:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/81194.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/81194.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/81194.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/81194.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/81194.html</trackback:ping><description><![CDATA[<h1 class=postTitle><a id=AjaxHolder_ctl01_TitleUrl class=postTitle2 href="http://www.cnblogs.com/Kane_zzt/archive/2009/04/23/1442387.html"><font color=#bd1717>C++ 时间</font></a> </h1>
<div class=clear></div>
<div class=postBody>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 本文从介绍基础概念入手，探讨了在C/C++中对日期和时间操作所用到的数据结构和函数，并对计时、时间的获取、时间的计算和显示格式等方面进行了阐述。本文还通过大量的实例向你展示了time.h头文件中声明的各种函数和数据结构的详细使用方法。&nbsp;&nbsp;</p>
<p>关键字：UTC（世界标准时间），Calendar Time（日历时间），epoch（时间点），clock tick（时钟计时单元）&nbsp;&nbsp;</p>
<p>1．概念&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;在C/C++中，对字符串的操作有很多值得注意的问题，同样，C/C++对时间的操作也有许多值得大家注意的地方。最近，在技术群中有很多网友也多次问到 过C++语言中对时间的操作、获取和显示等等的问题。下面，在这篇文章中，笔者将主要介绍在C/C++中时间和日期的使用方法.&nbsp;&nbsp;</p>
<p>通过学习许多C/C++库，你可以有很多操作、使用时间的方法。但在这之前你需要了解一些&#8220;时间&#8221;和&#8220;日期&#8221;的概念，主要有以下几个：&nbsp;&nbsp;</p>
<p>Coordinated Universal Time（UTC）：协调世界时，又称为世界标准时间，也就是大家所熟知的格林威治标准时间（Greenwich Mean Time，GMT）。比如，中国内地的时间与UTC的时差为+8，也就是UTC+8。美国是UTC-5。&nbsp;&nbsp;</p>
<p>Calendar Time：日历时间，是用&#8220;从一个标准时间点到此时的时间经过的秒数&#8221;来表示的时间。这个标准时间点对不同的编译器来说会有所不同，但对一个编译系统来 说，这个标准时间点是不变的，该编译系统中的时间对应的日历时间都通过该标准时间点来衡量，所以可以说日历时间是&#8220;相对时间&#8221;，但是无论你在哪一个时区， 在同一时刻对同一个标准时间点来说，日历时间都是一样的。&nbsp;&nbsp;</p>
<p>epoch：&nbsp;&nbsp;&nbsp; 时间点。时间点在标准C/C++中是一个整数，它用此时的时间和标准时间点相差的秒数（即日历时间）来表示。&nbsp;&nbsp;</p>
<p>clock tick：时钟计时单元（而不把它叫做时钟滴答次数），一个时钟计时单元的时间长短是由CPU控制的。一个clock tick不是CPU的一个时钟周期，而是C/C++的一个基本计时单位。&nbsp;&nbsp;</p>
<p>我们可以使用ANSI标准库中的time.h头文件。这个头文件中定义的时间和日期所使用的方法，无论是在结构定义，还是命名，都具有明显的C语言风格。下面，我将说明在C/C++中怎样使用日期的时间功能。&nbsp;&nbsp;</p>
<p>2． 计时&nbsp;&nbsp;</p>
<p>C/C++中的计时函数是clock()，而与其相关的数据类型是clock_t。在MSDN中，查得对clock函数定义如下：&nbsp;&nbsp;</p>
<p>clock_t clock( void );&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp; 这 个函数返回从&#8220;开启这个程序进程&#8221;到&#8220;程序中调用clock()函数&#8221;时之间的CPU时钟计时单元（clock tick）数，在MSDN中称之为挂钟时间（wal-clock）。其中clock_t是用来保存时间的数据类型，在time.h文件中，我们可以找到对 它的定义：&nbsp;&nbsp;</p>
<p>#ifndef _CLOCK_T_DEFINED&nbsp;&nbsp;<br>typedef long clock_t;&nbsp;&nbsp;<br>#define _CLOCK_T_DEFINED&nbsp;&nbsp;<br>#endif&nbsp;&nbsp;</p>
<p>很明显，clock_t是一个长整形数。在time.h文件中，还定义了一个常量CLOCKS_PER_SEC，它用来表示一秒钟会有多少个时钟计时单元，其定义如下：&nbsp;&nbsp;</p>
<p>#define CLOCKS_PER_SEC ((clock_t)1000)&nbsp;&nbsp;</p>
<p>可以看到每过千分之一秒（1毫秒），调用clock（）函数返回的值就加1。下面举个例子，你可以使用公式clock()/CLOCKS_PER_SEC来计算一个进程自身的运行时间：&nbsp;&nbsp;</p>
<p>void elapsed_time()&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>printf("Elapsed time:%u secs.\n",clock()/CLOCKS_PER_SEC);&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>当然，你也可以用clock函数来计算你的机器运行一个循环或者处理其它事件到底花了多少时间：&nbsp;&nbsp;</p>
<p>#include &#8220;stdio.h&#8221;&nbsp;&nbsp;<br>#include &#8220;stdlib.h&#8221;&nbsp;&nbsp;<br>#include &#8220;time.h&#8221;&nbsp;&nbsp;</p>
<p>int main( void )&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>long i = 10000000L;&nbsp;&nbsp;<br>clock_t start, finish;&nbsp;&nbsp;<br>double duration;&nbsp;&nbsp;<br>/* 测量一个事件持续的时间*/&nbsp;&nbsp;<br>printf( "Time to do %ld empty loops is ", i );&nbsp;&nbsp;<br>start = clock();&nbsp;&nbsp;<br>while( i-- ) ;&nbsp;&nbsp;<br>finish = clock();&nbsp;&nbsp;<br>duration = (double)(finish - start) / CLOCKS_PER_SEC;&nbsp;&nbsp;<br>printf( "%f seconds\n", duration );&nbsp;&nbsp;<br>system("pause");&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>在笔者的机器上，运行结果如下：&nbsp;&nbsp;</p>
<p>Time to do 10000000 empty loops is 0.03000 seconds&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp; 上面我们看到时钟计时单元的长度为1毫秒，那么计时的精度也为1毫秒，那么我们可不可以通过改变CLOCKS_PER_SEC的定义，通过把它定义的大一些，从而使计时精度更高呢？通过尝试，你会发现这样是不行的。在标准C/C++中，最小的计时单位是一毫秒。&nbsp;&nbsp;</p>
<p>3．与日期和时间相关的数据结构&nbsp;&nbsp;</p>
<p>在标准C/C++中，我们可通过tm结构来获得日期和时间，tm结构在time.h中的定义如下：&nbsp;&nbsp;</p>
<p>#ifndef _TM_DEFINED&nbsp;&nbsp;<br>struct tm {&nbsp;&nbsp;<br>int tm_sec; /* 秒 &#8211; 取值区间为[0,59] */&nbsp;&nbsp;<br>int tm_min; /* 分 - 取值区间为[0,59] */&nbsp;&nbsp;<br>int tm_hour; /* 时 - 取值区间为[0,23] */&nbsp;&nbsp;<br>int tm_mday; /* 一个月中的日期 - 取值区间为[1,31] */&nbsp;&nbsp;<br>int tm_mon; /* 月份（从一月开始，0代表一月） - 取值区间为[0,11] */&nbsp;&nbsp;<br>int tm_year; /* 年份，其值等于实际年份减去1900 */&nbsp;&nbsp;<br>int tm_wday; /* 星期 &#8211; 取值区间为[0,6]，其中0代表星期天，1代表星期一，以此类推 */&nbsp;&nbsp;<br>int tm_yday; /* 从每年的1月1日开始的天数 &#8211; 取值区间为[0,365]，其中0代表1月1日，1代表1月2日，以此类推 */&nbsp;&nbsp;<br>int tm_isdst; /* 夏令时标识符，实行夏令时的时候，tm_isdst为正。不实行夏令时的进候，tm_isdst为0；不了解情况时，tm_isdst()为负。*/&nbsp;&nbsp;<br>};&nbsp;&nbsp;<br>#define _TM_DEFINED&nbsp;&nbsp;<br>#endif&nbsp;&nbsp;</p>
<p>ANSI C标准称使用tm结构的这种时间表示为分解时间(broken-down time)。&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;而日历时间（Calendar Time）是通过time_t数据类型来表示的，用time_t表示的时间（日历时间）是从一个时间点（例如：1970年1月1日0时0分0秒）到此时的秒数。在time.h中，我们也可以看到time_t是一个长整型数：&nbsp;&nbsp;</p>
<p>#ifndef _TIME_T_DEFINED&nbsp;&nbsp;<br>typedef long time_t; /* 时间值 */&nbsp;&nbsp;<br>#define _TIME_T_DEFINED /* 避免重复定义 time_t */&nbsp;&nbsp;<br>#endif&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 大 家可能会产生疑问：既然time_t实际上是长整型，到未来的某一天，从一个时间点（一般是1970年1月1日0时0分0秒）到那时的秒数（即日历时间） 超出了长整形所能表示的数的范围怎么办？对time_t数据类型的值来说，它所表示的时间不能晚于2038年1月18日19时14分07秒。为了能够表示 更久远的时间，一些编译器厂商引入了64位甚至更长的整形数来保存日历时间。比如微软在Visual C++中采用了__time64_t数据类型来保存日历时间，并通过_time64()函数来获得日历时间（而不是通过使用32位字的time()函 数），这样就可以通过该数据类型保存3001年1月1日0时0分0秒（不包括该时间点）之前的时间。&nbsp;&nbsp;</p>
<p>在time.h头文件中，我们还可以看到一些函数，它们都是以time_t为参数类型或返回值类型的函数：&nbsp;&nbsp;</p>
<p>double difftime(time_t time1, time_t time0);&nbsp;&nbsp;<br>time_t mktime(struct tm * timeptr);&nbsp;&nbsp;<br>time_t time(time_t * timer);&nbsp;&nbsp;<br>char * asctime(const struct tm * timeptr);&nbsp;&nbsp;<br>char * ctime(const time_t *timer);&nbsp;&nbsp;</p>
<p>此外，time.h还提供了两种不同的函数将日历时间（一个用time_t表示的整数）转换为我们平时看到的把年月日时分秒分开显示的时间格式tm：&nbsp;&nbsp;</p>
<p>struct tm * gmtime(const time_t *timer);&nbsp;&nbsp;<br>struct tm * localtime(const time_t * timer);&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 通 过查阅MSDN，我们可以知道Microsoft C/C++ 7.0中时间点的值（time_t对象的值）是从1899年12月31日0时0分0秒到该时间点所经过的秒数，而其它各种版本的Microsoft C/C++和所有不同版本的Visual C++都是计算的从1970年1月1日0时0分0秒到该时间点所经过的秒数。&nbsp;&nbsp;</p>
<p>4．与日期和时间相关的函数及应用&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 在本节，我将向大家展示怎样利用time.h中声明的函数对时间进行操作。这些操作包括取当前时间、计算时间间隔、以不同的形式显示时间等内容。&nbsp;&nbsp;</p>
<p>4.1 获得日历时间&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 我们可以通过time()函数来获得日历时间（Calendar Time），其原型为：<br>time_t time(time_t * timer);&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 如 果你已经声明了参数timer，你可以从参数timer返回现在的日历时间，同时也可以通过返回值返回现在的日历时间，即从一个时间点（例如：1970年 1月1日0时0分0秒）到现在此时的秒数。如果参数为空（NUL），函数将只通过返回值返回现在的日历时间，比如下面这个例子用来显示当前的日历时间： &nbsp;&nbsp;</p>
<p>#include "time.h"&nbsp;&nbsp;<br>#include "stdio.h"&nbsp;&nbsp;<br>int main(void)&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>struct tm *ptr;&nbsp;&nbsp;<br>time_t lt;&nbsp;&nbsp;<br>lt =time(NUL);&nbsp;&nbsp;<br>printf("The Calendar Time now is %d\n",lt);&nbsp;&nbsp;<br>return 0;&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>运行的结果与当时的时间有关，我当时运行的结果是：&nbsp;&nbsp;</p>
<p>The Calendar Time now is 1122707619&nbsp;&nbsp;</p>
<p>其中1122707619就是我运行程序时的日历时间。即从1970年1月1日0时0分0秒到此时的秒数。&nbsp;&nbsp;</p>
<p>4.2 获得日期和时间&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 这里说的日期和时间就是我们平时所说的年、月、日、时、分、秒等信息。从第2节我们已经知道这些信息都保存在一个名为tm的结构体中，那么如何将一个日历时间保存为一个tm结构的对象呢？&nbsp;&nbsp;</p>
<p>其中可以使用的函数是gmtime()和localtime()，这两个函数的原型为：&nbsp;&nbsp;</p>
<p>struct tm * gmtime(const time_t *timer);&nbsp;&nbsp;<br>struct tm * localtime(const time_t * timer);&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 其 中gmtime()函数是将日历时间转化为世界标准时间（即格林尼治时间），并返回一个tm结构体来保存这个时间，而localtime()函数是将日历 时间转化为本地时间。比如现在用gmtime()函数获得的世界标准时间是2005年7月30日7点18分20秒，那么我用localtime()函数在 中国地区获得的本地时间会比世界标准时间晚8个小时，即2005年7月30日15点18分20秒。下面是个例子：&nbsp;&nbsp;</p>
<p>#include "time.h"&nbsp;&nbsp;<br>#include "stdio.h"&nbsp;&nbsp;<br>int main(void)&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>struct tm *local;&nbsp;&nbsp;<br>time_t t;&nbsp;&nbsp;<br>t=time(NUL);&nbsp;&nbsp;<br>local=localtime(&amp;t);&nbsp;&nbsp;<br>printf("Local hour is: %d\n",local-&gt;tm_hour);&nbsp;&nbsp;<br>local=gmtime(&amp;t);&nbsp;&nbsp;<br>printf("UTC hour is: %d\n",local-&gt;tm_hour);&nbsp;&nbsp;<br>return 0;&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>运行结果是：&nbsp;&nbsp;</p>
<p>Local hour is: 15&nbsp;&nbsp;<br>UTC hour is: 7&nbsp;&nbsp;</p>
<p>4.3 固定的时间格式&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 我们可以通过asctime()函数和ctime()函数将时间以固定的格式显示出来，两者的返回值都是char*型的字符串。返回的时间格式为：&nbsp;&nbsp;</p>
<p>星期几 月份 日期 时:分:秒 年\n\0&nbsp;&nbsp;<br>例如：Wed Jan 02 02:03:55 1980\n\0&nbsp;&nbsp;</p>
<p>其中\n是一个换行符，\0是一个空字符，表示字符串结束。下面是两个函数的原型：&nbsp;&nbsp;</p>
<p>char * asctime(const struct tm * timeptr);&nbsp;&nbsp;<br>char * ctime(const time_t *timer);&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 其 中asctime()函数是通过tm结构来生成具有固定格式的保存时间信息的字符串，而ctime()是通过日历时间来生成时间字符串。这样的话， asctime（）函数只是把tm结构对象中的各个域填到时间字符串的相应位置就行了，而ctime（）函数需要先参照本地的时间设置，把日历时间转化为 本地时间，然后再生成格式化后的字符串。在下面，如果t是一个非空的time_t变量的话，那么：&nbsp;&nbsp;</p>
<p>printf(ctime(&amp;t));&nbsp;&nbsp;</p>
<p>等价于：&nbsp;&nbsp;</p>
<p>struct tm *ptr;&nbsp;&nbsp;<br>ptr=localtime(&amp;t);&nbsp;&nbsp;<br>printf(asctime(ptr));&nbsp;&nbsp;</p>
<p>那么，下面这个程序的两条printf语句输出的结果就是不同的了（除非你将本地时区设为世界标准时间所在的时区）：&nbsp;&nbsp;</p>
<p>#include "time.h"&nbsp;&nbsp;<br>#include "stdio.h"&nbsp;&nbsp;<br>int main(void)&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>struct tm *ptr;&nbsp;&nbsp;<br>time_t lt;&nbsp;&nbsp;<br>lt =time(NUL);&nbsp;&nbsp;<br>ptr=gmtime(&lt;);&nbsp;&nbsp;<br>printf(asctime(ptr));&nbsp;&nbsp;<br>printf(ctime(&lt;));&nbsp;&nbsp;<br>return 0;&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>运行结果：&nbsp;&nbsp;</p>
<p>Sat Jul 30 08:43:03 2005&nbsp;&nbsp;<br>Sat Jul 30 16:43:03 2005&nbsp;&nbsp;</p>
<p>4.4 自定义时间格式&nbsp;&nbsp;</p>
<p>我们可以使用strftime（）函数将时间格式化为我们想要的格式。它的原型如下：&nbsp;&nbsp;</p>
<p>size_t strftime(&nbsp;&nbsp;<br>char *strDest,&nbsp;&nbsp;<br>size_t maxsize,&nbsp;&nbsp;<br>const char *format,&nbsp;&nbsp;<br>const struct tm *timeptr&nbsp;&nbsp;<br>);&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 我们可以根据format指向字符串中格式命令把timeptr中保存的时间信息放在strDest指向的字符串中，最多向strDest中存放maxsize个字符。该函数返回向strDest指向的字符串中放置的字符数。&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 函 数strftime()的操作有些类似于sprintf()：识别以百分号(%)开始的格式命令集合，格式化输出结果放在一个字符串中。格式化命令说明串 strDest中各种日期和时间信息的确切表示方法。格式串中的其他字符原样放进串中。格式命令列在下面，它们是区分大小写的。&nbsp;&nbsp;</p>
<p>%a 星期几的简写&nbsp;&nbsp;<br>%A 星期几的全称&nbsp;&nbsp;<br>%b 月分的简写&nbsp;&nbsp;<br>%B 月份的全称&nbsp;&nbsp;<br>%c 标准的日期的时间串&nbsp;&nbsp;<br>%C 年份的后两位数字&nbsp;&nbsp;<br>%d 十进制表示的每月的第几天&nbsp;&nbsp;<br>%D 月/天/年&nbsp;&nbsp;<br>%e 在两字符域中，十进制表示的每月的第几天&nbsp;&nbsp;<br>%F 年-月-日&nbsp;&nbsp;<br>%g 年份的后两位数字，使用基于周的年&nbsp;&nbsp;<br>%G 年分，使用基于周的年&nbsp;&nbsp;<br>%h 简写的月份名&nbsp;&nbsp;<br>%H 24小时制的小时&nbsp;&nbsp;<br>%I 12小时制的小时&nbsp;&nbsp;<br>%j 十进制表示的每年的第几天&nbsp;&nbsp;<br>%m 十进制表示的月份&nbsp;&nbsp;<br>%M 十时制表示的分钟数&nbsp;&nbsp;<br>%n 新行符&nbsp;&nbsp;<br>%p 本地的AM或PM的等价显示&nbsp;&nbsp;<br>%r 12小时的时间&nbsp;&nbsp;<br>%R 显示小时和分钟：hh:mm&nbsp;&nbsp;<br>%S 十进制的秒数&nbsp;&nbsp;<br>%t 水平制表符&nbsp;&nbsp;<br>%T 显示时分秒：hh:mm:ss&nbsp;&nbsp;<br>%u 每周的第几天，星期一为第一天 （值从0到6，星期一为0）&nbsp;&nbsp;<br>%U 第年的第几周，把星期日做为第一天（值从0到53）&nbsp;&nbsp;<br>%V 每年的第几周，使用基于周的年&nbsp;&nbsp;<br>%w 十进制表示的星期几（值从0到6，星期天为0）&nbsp;&nbsp;<br>%W 每年的第几周，把星期一做为第一天（值从0到53）&nbsp;&nbsp;<br>%x 标准的日期串&nbsp;&nbsp;<br>%X 标准的时间串&nbsp;&nbsp;<br>%y 不带世纪的十进制年份（值从0到99）&nbsp;&nbsp;<br>%Y 带世纪部分的十进制年份&nbsp;&nbsp;<br>%z，%Z 时区名称，如果不能得到时区名称则返回空字符。&nbsp;&nbsp;<br>%% 百分号&nbsp;&nbsp;</p>
<p>如果想显示现在是几点了，并以12小时制显示，就象下面这段程序：&nbsp;&nbsp;</p>
<p>#include &#8220;time.h&#8221;&nbsp;&nbsp;<br>#include &#8220;stdio.h&#8221;&nbsp;&nbsp;<br>int main(void)&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>struct tm *ptr;&nbsp;&nbsp;<br>time_t lt;&nbsp;&nbsp;<br>char str[80];&nbsp;&nbsp;<br>lt=time(NUL);&nbsp;&nbsp;<br>ptr=localtime(&lt;);&nbsp;&nbsp;<br>strftime(str,100,"It is now %I %p",ptr);&nbsp;&nbsp;<br>printf(str);&nbsp;&nbsp;<br>return 0;&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>其运行结果为：&nbsp;&nbsp;<br>It is now 4PM&nbsp;&nbsp;</p>
<p>而下面的程序则显示当前的完整日期：&nbsp;&nbsp;</p>
<p>#include &lt;stdio.h&gt;&nbsp;&nbsp;<br>#include &lt;time.h&gt;&nbsp;&nbsp;</p>
<p>void main( void )&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>struct tm *newtime;&nbsp;&nbsp;<br>char tmpbuf[128];&nbsp;&nbsp;<br>time_t lt1;&nbsp;&nbsp;<br>time( &lt;1 );&nbsp;&nbsp;<br>newtime=localtime(&lt;1);&nbsp;&nbsp;<br>strftime( tmpbuf, 128, "Today is %A, day %d of %B in the year %Y.\n", newtime);&nbsp;&nbsp;<br>printf(tmpbuf);&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>运行结果：&nbsp;&nbsp;</p>
<p>Today is Saturday, day 30 of July in the year 2005.&nbsp;&nbsp;</p>
<p>4.5 计算持续时间的长度&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 有时候在实际应用中要计算一个事件持续的时间长度，比如计算打字速度。在第1节计时部分中，我已经用clock函数举了一个例子。Clock()函数可以精确到毫秒级。同时，我们也可以使用difftime()函数，但它只能精确到秒。该函数的定义如下：&nbsp;&nbsp;</p>
<p>double difftime(time_t time1, time_t time0);&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 虽然该函数返回的以秒计算的时间间隔是double类型的，但这并不说明该时间具有同double一样的精确度，这是由它的参数觉得的（time_t是以秒为单位计算的）。比如下面一段程序：&nbsp;&nbsp;</p>
<p>#include "time.h"&nbsp;&nbsp;<br>#include "stdio.h"&nbsp;&nbsp;<br>#include "stdlib.h"&nbsp;&nbsp;<br>int main(void)&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>time_t start,end;&nbsp;&nbsp;<br>start = time(NUL);&nbsp;&nbsp;<br>system("pause");&nbsp;&nbsp;<br>end = time(NUL);&nbsp;&nbsp;<br>printf("The pause used %f seconds.\n",difftime(end,start));//&lt;-&nbsp;&nbsp;<br>system("pause");&nbsp;&nbsp;<br>return 0;&nbsp;&nbsp;<br>}&nbsp;&nbsp;</p>
<p>运行结果为：&nbsp;&nbsp;<br>请按任意键继续. . .&nbsp;&nbsp;<br>The pause used 2.000000 seconds.&nbsp;&nbsp;<br>请按任意键继续. . .&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 可以想像，暂停的时间并不那么巧是整整2秒钟。其实，你将上面程序的带有&#8220;//&lt;-&#8221;注释的一行用下面的一行代码替换：&nbsp;&nbsp;</p>
<p>printf("The pause used %f seconds.\n",end-start);&nbsp;&nbsp;</p>
<p>其运行结果是一样的。&nbsp;&nbsp;</p>
<p>4.6 分解时间转化为日历时间&nbsp;&nbsp;</p>
<p>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 这里说的分解时间就是以年、月、日、时、分、秒等分量保存的时间结构，在C/C++中是tm结构。我们可以使用mktime（）函数将用tm结构表示的时间转化为日历时间。其函数原型如下：&nbsp;&nbsp;</p>
<p>time_t mktime(struct tm * timeptr);&nbsp;&nbsp;</p>
<p>其返回值就是转化后的日历时间。这样我们就可以先制定一个分解时间，然后对这个时间进行操作了，下面的例子可以计算出1997年7月1日是星期几：&nbsp;&nbsp;</p>
<p>#include "time.h"&nbsp;&nbsp;<br>#include "stdio.h"&nbsp;&nbsp;<br>#include "stdlib.h"&nbsp;&nbsp;<br>int main(void)&nbsp;&nbsp;<br>{&nbsp;&nbsp;<br>struct tm t;&nbsp;&nbsp;<br>time_t t_of_day;&nbsp;&nbsp;<br>t.tm_year=1997-1900;&nbsp;&nbsp;<br>t.tm_mon=6;&nbsp;&nbsp;<br>t.tm_mday=1;&nbsp;&nbsp;<br>t.tm_hour=0;&nbsp;&nbsp;<br>t.tm_min=0;&nbsp;&nbsp;<br>t.tm_sec=1;&nbsp;&nbsp;<br>t.tm_isdst=0;&nbsp;&nbsp;<br>t_of_day=mktime(&amp;t);&nbsp;&nbsp;<br>printf(ctime(&amp;t_of_day));&nbsp;&nbsp;<br>return 0;&nbsp;&nbsp;<br>}&nbsp;&nbsp;<br>运行结果：&nbsp;&nbsp;<br>Tue Jul 01 00:00:01 1997&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp; 现在注意了，有了mktime()函数，是不是我们可以操作现在之前的任何时间呢？你可以通过这种办法算出1945年8月15号是星期几吗？答案是否定的。因为这个时间在1970年1月1日之前，所以在大多数编译器中，这样的程序虽然可以编译通过，但运行时会异常终止。 <br>5．总结 <br>本文介绍了标准C/C++中的有关日期和时间的概念，并通过各种实例讲述了这些函数和数据结构的使用方法。笔者认为，和时间相关的一些概念是相当重要的，理解这些概念是理解各种时间格式的转换的基础，更是应用这些函数和数据结构的基础。</p>
</div>
<img src ="http://www.cppblog.com/Walker/aggbug/81194.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2009-04-27 11:11 <a href="http://www.cppblog.com/Walker/articles/81194.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Debug函数的实现（转）</title><link>http://www.cppblog.com/Walker/articles/80471.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Sun, 19 Apr 2009 13:04:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/80471.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/80471.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/80471.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/80471.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/80471.html</trackback:ping><description><![CDATA[&nbsp;#define DBGPRT(fmt,args...) \<br>&nbsp;&nbsp; do{ \<br>&nbsp;&nbsp;&nbsp; FILE* fp= fopen("/home/debug.log","a+"); \<br>&nbsp;&nbsp;&nbsp; if( fp != NULL ) \<br>&nbsp;&nbsp;&nbsp; { \<br>&nbsp;&nbsp;&nbsp;&nbsp; fprintf(fp," \n %s(%d)-%s: \n",__FILE__,__LINE__,__FUNCTION__); \<br>&nbsp;&nbsp;&nbsp;&nbsp; fprintf(fp,fmt,##args); \<br>&nbsp;&nbsp;&nbsp;&nbsp; fclose(fp); \<br>&nbsp;&nbsp;&nbsp;&nbsp; } \<br>&nbsp;&nbsp; }while(0); 
<img src ="http://www.cppblog.com/Walker/aggbug/80471.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2009-04-19 21:04 <a href="http://www.cppblog.com/Walker/articles/80471.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title> 函数指针与软件设计</title><link>http://www.cppblog.com/Walker/articles/80469.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Sun, 19 Apr 2009 12:49:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/80469.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/80469.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/80469.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/80469.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/80469.html</trackback:ping><description><![CDATA[<p style="TEXT-INDENT: 2em">记得刚开始工作时，一位高手告诉我，说，longjmp和setjmp玩得不熟，就不要自称为C语言高手。当时我半信半疑，为了让自己向高手方向迈进，还是花了一点时间去学习longjmp和setjmp的用法。后来明白那不单是跳来跳去那样简单，而是一种高级的异常处理机制，在某些情况下确实很有用。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">为了显示自己的技巧，也在自己的程序中用过几次。渐渐发现这样的技巧带来的好处是有代价的，破坏了程序的结构化设计，程序变得很难读，尤其对新手来说。终于明白这种技巧不过是一种调味料，在少数情况使用几次，可以简化对问题的处理。如果把调味拿来当饭吃，一定会本末倒置，写出的程序会呈现营养不良之状。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">事实上，longjmp和setjmp玩得熟不熟与是不是C语言高手，不是因果关系。但是，如果可以套用那位高手的话，我倒想说如果函数指针玩得不熟，就不要自称为C语言高手。为什么这么说呢，函数指针有那么复杂吗？当然不是，任何一个稍有编程常识的人，不管他懂不懂C语言，在10分钟内，我想他一定可以明白C语言中的函数指针是怎么回事。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">原因在于，难的不是函数指针的概念和语法本身，而是在什么时候，什么地方该使用它。函数指针不仅是语法上的问题，更重要的是它是一个设计范畴。真正的高手当然不单应该懂得语法层面上的技巧，更应该懂得设计上的方法。不懂设计，能算高手吗？怀疑我在夸大其辞吗？那我们先看看函数指针与哪些设计方法有关：</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em"><strong>与分层设计有关。</strong>分层设计早就不是什么新的概念，分层的好处是众所周知的，比较明显好处就是简化复杂度、隔离变化。采用分层设计，每层都只需关心自己的东西，这减小了系统的复杂度，层与层之间的交互仅限于一个很窄的接口，只要接口不变，某一层的变化不会影响其它层，这隔离了变化。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">分层的一般原则是，上层可以直接调用下层的函数，下层则不能直接调用上层的函数。这句话说来简单，在现实中，下层常常要反过来调用上层的函数。比如你在拷贝文件时，在界面层调用一个拷贝文件函数。界面层是上层，拷贝文件函数是下层，上层调用下层，理所当然。但是如果你想在拷贝文件时还要更新进度条，问题就来了。一方面，只有拷贝文件函数才知道拷贝的进度，但它不能去更新界面的进度条。另外一方面，界面知道如何去更新进度条，但它又不知道拷贝的进度。怎么办？常见的做法，就是界面设置一个回调函数给拷贝文件函数，拷贝文件函数在适当的时候调用这个回调函数来通知界面更新状态。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em"><strong>与抽象有关。</strong>抽象是面向对象中最重要的概念之一，也是面向对象威力强大之处。面向对象只是一种思想，大家都知道，用C语言一样可以实现面向对象的编程。这可不是为了赶时髦，而是一种实用的方法。如果你对此表示怀疑，可以去看看GTK+、linux kernel等开源代码。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">接口是最高级的抽象。在linux kernel里面，接口的概念无处不在，像虚拟文件系统(VFS)，它定义一个文件系统的接口，只要按照这种接口的规范，你可以自己开发一个文件系统挂上去。设备驱动程序更是如此，不同的设备驱动程序有自己一套不同的接口规范。在自己开发设备开发驱动程序时，只要遵循相应的接口规范就行了。接口在C语言中如何表示？很简单，就是一组函数指针。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em"><strong>与接口与实现分开有关</strong>。针对接口编程，而不是针对实现编程，此为《设计模式》的第一条设计准则。分开接口与实现的目标是要隔离变化。软件是变化的，如果不能把变化的东西隔离开来，导致牵一发而动全身，代价是巨大的。这是大家所不愿看到的。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">C语言既然可以实现面向对象的编程，自然可以利用设计模式来分离接口与实现。像桥接模式、策略模式、状态模式、代理模式等等，在C语言中，无一不需要利用函数指针来实现。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em"><strong>与松耦合原则有关</strong>。面向过程与面向对象相比，之所以显得苍白无力，原因之一就是它不像面向对象一样，可以直观的把现实模型映射到计算机中。面向过程讲的是层层控制，而面向对象更强调的对象间的分工合作。现实世界中的对象处于层次关系的较少，处于对等关系的居多。也就是说，对象间的交互往往是双向的。这会加强对象间的耦合性。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">耦合本身没有错，实际上耦合是必不可少的，没有耦合就没有协作，对象之间无法形成一个整体，什么事也做不了。关键在于耦合要恰当，在实现预定功能的前提下，耦合要尽可能的松散。这样，系统的一部分变化对其它部分的影响会很少。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">函数指针是解耦对象关系的最佳利器。Signal(如boost的signal和glib中的signal)机制是一个典型的例子，一个对象自身的状态可能是在变化的（或者会触发一些事件），而其它对象关心它的变化。一旦该对象有变化发生，其它对象要执行相应的操作。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">如果该对象直接去调用其它对象的函数，功能是完成了，但对象之间的耦合太紧了。如何把这种耦合降到最低呢，signal机制是很好的办法。它的原理大致如下：其它关注该对象变化的对象主动注册一个回调函数到该对象中。一旦该对象有变化发生，就调用这些回调函数通知其它对象。功能同样实现了，但它们之间的耦合度降低了。</p>
<p style="TEXT-INDENT: 2em">&nbsp;</p>
<p style="TEXT-INDENT: 2em">在C语言中，要解决以上这些问题，不采用函数指针，将是非常困难的。在编程中，如果你从没有想到用函数指针，很难想像你是一个C语言高手。</p>
<img src ="http://www.cppblog.com/Walker/aggbug/80469.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2009-04-19 20:49 <a href="http://www.cppblog.com/Walker/articles/80469.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title> （转）经典的位运算实例</title><link>http://www.cppblog.com/Walker/articles/80466.html</link><dc:creator>漫步者×&amp;……%￥</dc:creator><author>漫步者×&amp;……%￥</author><pubDate>Sun, 19 Apr 2009 12:44:00 GMT</pubDate><guid>http://www.cppblog.com/Walker/articles/80466.html</guid><wfw:comment>http://www.cppblog.com/Walker/comments/80466.html</wfw:comment><comments>http://www.cppblog.com/Walker/articles/80466.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Walker/comments/commentRss/80466.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Walker/services/trackbacks/80466.html</trackback:ping><description><![CDATA[<p>1) int型变量循环左移k次，即a=a &lt; &lt;k |a&gt;&gt;16-k&nbsp; (设sizeof(int)=16) <br>(2) int型变量a循环右移k次，即a=a&gt;&gt;k |a &lt; &lt;16-k&nbsp; (设sizeof(int)=16) <br>(3)整数的平均值 <br>对于两个整数x,y，如果用 (x+y)/2 求平均值，会产生溢出，因为 x+y 可能会大于INT_MAX，但是我们知道它们的平均值是肯定不会溢出的，我们用如下算法： <br>int average(int x, int y)&nbsp; //返回X,Y 的平均值 <br>{&nbsp;&nbsp;&nbsp; <br>&nbsp;&nbsp;&nbsp; return (x&amp;y)+((x^y)&gt;&gt;1); <br>} <br>(4)判断一个整数是不是2的幂,对于一个数 x &gt;= 0，判断他是不是2的幂 <br>boolean power2(int x) <br>{ <br>&nbsp;&nbsp;&nbsp; return ((x&amp;(x-1))==0)&amp;&amp;(x!=0)； <br>} <br>(5)不用temp交换两个整数 <br>void swap(int x , int y) <br>{ <br>&nbsp;&nbsp;&nbsp; x ^= y; <br>&nbsp;&nbsp;&nbsp; y ^= x; <br>&nbsp;&nbsp;&nbsp; x ^= y; <br>} <br>(6)计算绝对值 <br>int abs( int x ) <br>{ <br>int y ; <br>y = x &gt;&gt; 31 ; <br>return (x^y)-y ;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //or: (x+y)^y <br>} <br>(7)取模运算转化成位运算 (在不产生溢出的情况下) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; a % (2^n) 等价于 a &amp; (2^n - 1) <br>(8)乘法运算转化成位运算 (在不产生溢出的情况下) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; a * (2^n) 等价于 a &lt; &lt; n <br>(9)除法运算转化成位运算 (在不产生溢出的情况下) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; a / (2^n) 等价于 a&gt;&gt; n <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 例: 12/8 == 12&gt;&gt;3 <br>(10) a % 2 等价于 a &amp; 1&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br>(11) if (x == a) x= b; <br>　　&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; else x= a; <br>　　&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 等价于 x= a ^ b ^ x; <br>(12) x 的 相反数 表示为 (~x+1) </p>
<p>(13)求从x位（高）到y位（低）间共有多少个1 </p>
<p>public static int FindChessNum(int x, int y, ushort k) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; { <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; int re = 0; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; for (int i = y; i &lt;= x; i++) <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; { <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; re += ((k &gt;&gt; (i - 1)) &amp; 1); <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; } <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return re; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; } <br>(14)<br>/*将32位数分解为4个8位数处理后再合成32位数返回*/<br>DWORD GetDW(DWORD dw)<br>{<br>&nbsp;DWORD dwRet=0;<br>&nbsp;if (dw!=0)<br>&nbsp;{<br>&nbsp;&nbsp;BYTE b1=(dw&gt;&gt;24)&amp;0xff,b2=(dw&gt;&gt;16)&amp;0xff,b3=(dw&gt;&gt;8)&amp;0xff,b4=dw&amp;0xff;<br>&nbsp;&nbsp;//分别处理 b1,b2,b3,b4<br>&nbsp;&nbsp;dwRet=b1;<br>&nbsp;&nbsp;dwRet=(dwRet&lt;&lt;8)+b2;<br>&nbsp;&nbsp;dwRet=(dwRet&lt;&lt;8)+b3;<br>&nbsp;&nbsp;dwRet=(dwRet&lt;&lt;8)+b4;</p>
<p>&nbsp;&nbsp;return dwRet;<br>&nbsp;}<br>&nbsp;else{<br>&nbsp;&nbsp;return 0;<br>&nbsp;}<br>}<br><br><br>&nbsp;&nbsp;检测一个无符号数是不为2^n-1(^为幂)：&nbsp;&nbsp;&nbsp;x&amp;(x+1)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;将最右侧0位改为1位：&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(x+1)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;二进制补码运算公式：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;-x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;~x&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;1&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;~(x-1)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;~x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;-x-1&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;-(~x)&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x+1&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;~(-x)&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x-1&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x+y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;-&nbsp;&nbsp;&nbsp;~y&nbsp;&nbsp;&nbsp;-&nbsp;&nbsp;&nbsp;1&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x|y)+(x&amp;y)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x-y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;~y&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;1&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x|~y)-(~x&amp;y)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x^y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x|y)-(x&amp;y)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x|y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&amp;~y)+y&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&amp;y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(~x|y)-~x&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x==y:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;~(x-y|y-x)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x!=y:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;x-y|y-x&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&lt;&nbsp;&nbsp;&nbsp;y:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(x-y)^((x^y)&amp;((x-y)^x))&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&lt;=y:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(x|~y)&amp;((x^y)|~(y-x))&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&lt;&nbsp;&nbsp;&nbsp;y:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(~x&amp;y)|((~x|y)&amp;(x-y))//无符号x,y比较&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&lt;=y:&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(~x|y)&amp;((x^y)|~(y-x))//无符号x,y比较&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;使用位运算的无分支代码：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;计算绝对值&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;abs(&nbsp;&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&gt;&gt;&nbsp;&nbsp;&nbsp;31&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;(x^y)-y&nbsp;&nbsp;&nbsp;;//or:&nbsp;&nbsp;&nbsp;(x+y)^y&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;符号函数：sign(x)&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;-1,&nbsp;&nbsp;&nbsp;x&lt;0;&nbsp;&nbsp;&nbsp;0,&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;==&nbsp;&nbsp;&nbsp;0&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;1,&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&gt;&nbsp;&nbsp;&nbsp;0&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;sign(int&nbsp;&nbsp;&nbsp;x)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;(x&gt;&gt;31)&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(unsigned(-x))&gt;&gt;31&nbsp;&nbsp;&nbsp;;//x=-2^31时失败(^为幂)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;三值比较：cmp(x,y)&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;-1,&nbsp;&nbsp;&nbsp;x&lt;y;&nbsp;&nbsp;&nbsp;0,&nbsp;&nbsp;&nbsp;x==y;&nbsp;&nbsp;&nbsp;1,&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&gt;&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;cmp(&nbsp;&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;x,&nbsp;&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;(x&gt;y)-(x-y)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;doz=x-y,&nbsp;&nbsp;&nbsp;x&gt;=y;&nbsp;&nbsp;&nbsp;0,&nbsp;&nbsp;&nbsp;x&lt;y&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;doz(int&nbsp;&nbsp;&nbsp;x,&nbsp;&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;d&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;d&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x-y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;d&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;((~(d^((x^y)&amp;(d^x))))&gt;&gt;31)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;max(int&nbsp;&nbsp;&nbsp;x,&nbsp;&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x-y)&gt;&gt;31&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;~m&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;不使用第三方交换x,y:&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;1.x&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;2.x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x+y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x-y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x-y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;3.x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x-y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;y+x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;y-x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;4.x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;y-x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;y-x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x+y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;双值交换:x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;a,&nbsp;&nbsp;&nbsp;x==b;&nbsp;&nbsp;&nbsp;b,&nbsp;&nbsp;&nbsp;x==a//常规编码为x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x==a&nbsp;&nbsp;&nbsp;?&nbsp;&nbsp;&nbsp;b&nbsp;&nbsp;&nbsp;:a&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;1.x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;a+b-x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;2.x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;a^b^x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;下舍入到2的k次方的倍数:&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;1.x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;((-1)&lt;&lt;k)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;2.(((unsigned)x)&gt;&gt;k)&lt;&lt;k&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;上舍入：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;1.&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(1&lt;&lt;k)-1&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x+t)&amp;~t&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;2.t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(-1)&lt;&lt;k&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x-t-1)&amp;t&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;位计数,统计1位的数量：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;1.&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;pop(unsigned&nbsp;&nbsp;&nbsp;x)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x-((x&gt;&gt;1)&amp;0x55555555)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&amp;0x33333333)&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;((x&gt;&gt;2)&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x33333333&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x+(x&gt;&gt;4))&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x0f0f0f0f&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;(x&gt;&gt;8)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;(x&gt;&gt;16)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x0000003f&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;2.&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;pop(unsigned&nbsp;&nbsp;&nbsp;x)&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;static&nbsp;&nbsp;&nbsp;char&nbsp;&nbsp;&nbsp;table[256]&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;0,1,1,2,&nbsp;&nbsp;&nbsp;1,2,2,3,&nbsp;&nbsp;&nbsp;....,&nbsp;&nbsp;&nbsp;6,7,7,8&nbsp;&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;table[x&amp;0xff]+table[(x&gt;&gt;8)&amp;0xff]+table[(x&gt;&gt;16)&amp;0xff]+table[(x&gt;&gt;24)]&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;奇偶性计算:&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;x&gt;&gt;1&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;x&gt;&gt;2&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;x&gt;&gt;4&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;x&gt;&gt;8&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;x&gt;&gt;16&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;结果中位于x最低位，对无符号x,结果的第i位是原数第i位到最左侧位的奇偶性&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;位反转：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;rev(unsigned&nbsp;&nbsp;&nbsp;x)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x55555555)&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;1&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(x&gt;&gt;1)&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x55555555&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x33333333)&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;2&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(x&gt;&gt;2)&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x33333333&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x0f0f0f0f)&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;4&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(x&gt;&gt;4)&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x0f0f0f0f&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&lt;&lt;24)&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;((x&amp;0xff00)&lt;&lt;8)&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;((x&gt;&gt;8)&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0xff00)&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(x&gt;&gt;24)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;递增位反转后的数：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;inc_r(unsigned&nbsp;&nbsp;&nbsp;x)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;0x80000000&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;if(&nbsp;&nbsp;&nbsp;(int)x&nbsp;&nbsp;&nbsp;&gt;=&nbsp;&nbsp;&nbsp;0&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;do&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;&gt;&gt;=&nbsp;&nbsp;&nbsp;1&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;while(&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&lt;&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;混选位：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;abcd&nbsp;&nbsp;&nbsp;efgh&nbsp;&nbsp;&nbsp;ijkl&nbsp;&nbsp;&nbsp;mnop&nbsp;&nbsp;&nbsp;ABCD&nbsp;&nbsp;&nbsp;EFGH&nbsp;&nbsp;&nbsp;IJKL&nbsp;&nbsp;&nbsp;MNOP-&gt;aAbB&nbsp;&nbsp;&nbsp;cCdD&nbsp;&nbsp;&nbsp;eEfF&nbsp;&nbsp;&nbsp;gGhH&nbsp;&nbsp;&nbsp;iIjJ&nbsp;&nbsp;&nbsp;kKlL&nbsp;&nbsp;&nbsp;mMnN&nbsp;&nbsp;&nbsp;oOpP&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;ps(unsigned&nbsp;&nbsp;&nbsp;x)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(x&gt;&gt;8))&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x0000ff00;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(t&lt;&lt;8)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(x&gt;&gt;4))&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x00f000f0;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(t&lt;&lt;4)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(x&gt;&gt;2))&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x0c0c0c0c;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(t&lt;&lt;2)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(x&gt;&gt;1))&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;0x22222222;&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(t&lt;&lt;1)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;位压缩：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;选择并右移字x中对应于掩码m的1位的位,如：compress(abcdefgh,01010101)=0000bdfh&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;compress_left(x,m)操作与此类似，但结果位在左边:&nbsp;&nbsp;&nbsp;bdfh0000.&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;compress(unsigned&nbsp;&nbsp;&nbsp;x,&nbsp;&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;m)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;mk,&nbsp;&nbsp;&nbsp;mp,&nbsp;&nbsp;&nbsp;mv,&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;i&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&amp;=&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mk&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;~m&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;1&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;for(&nbsp;&nbsp;&nbsp;i&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;0&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;i&nbsp;&nbsp;&nbsp;&lt;&nbsp;&nbsp;&nbsp;5&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;++i&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;mk&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;mk&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;1)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;2&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;4&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;8&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;^=&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;&lt;&lt;&nbsp;&nbsp;&nbsp;16&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mv&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;mp&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;m&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;mv&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(mv&nbsp;&nbsp;&nbsp;&gt;&gt;&nbsp;&nbsp;&nbsp;(1&lt;&lt;i)&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;mv&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;t&nbsp;&nbsp;&nbsp;&gt;&gt;&nbsp;&nbsp;&nbsp;(&nbsp;&nbsp;&nbsp;1&lt;&lt;i)&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;mk&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;mk&nbsp;&nbsp;&nbsp;&amp;&nbsp;&nbsp;&nbsp;~mp&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;位置换：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;用32个5位数表示从最低位开始的位的目标位置，结果是一个32*5的位矩阵，&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;将该矩阵沿次对角线转置后用5个32位字p[5]存放。&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;SAG(x,m)&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;compress_left(x,m)&nbsp;&nbsp;&nbsp;|&nbsp;&nbsp;&nbsp;compress(x,~m)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;准备工作：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;void&nbsp;&nbsp;&nbsp;init(&nbsp;&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;*p&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;p[1]&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;p[1],&nbsp;&nbsp;&nbsp;p[0]&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;p[2]&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;p[2],&nbsp;&nbsp;&nbsp;p[0]),&nbsp;&nbsp;&nbsp;p[1]&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;p[3]&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;p[3],&nbsp;&nbsp;&nbsp;p[0]&nbsp;&nbsp;&nbsp;),&nbsp;&nbsp;&nbsp;p[1]),&nbsp;&nbsp;&nbsp;p[2]&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;p[4]&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;SAG(&nbsp;&nbsp;&nbsp;p[4],&nbsp;&nbsp;&nbsp;p[0]&nbsp;&nbsp;&nbsp;),&nbsp;&nbsp;&nbsp;p[1])&nbsp;&nbsp;&nbsp;,p[2]),&nbsp;&nbsp;&nbsp;p[3]&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;实际置换：&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;rep(&nbsp;&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(x,p[0]);&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(x,p[1]);&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(x,p[2]);&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(x,p[3]);&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;SAG(x,p[4]);&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;二进制码到GRAY码的转换:&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;B2G(unsigned&nbsp;&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(B&gt;&gt;1)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;GRAY码到二进制码:&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;G2B(unsigned&nbsp;&nbsp;&nbsp;G)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;G&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(G&gt;&gt;1)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;G&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(G&gt;&gt;2)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;G&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(G&gt;&gt;4)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;G&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(G&gt;&gt;8)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;G&nbsp;&nbsp;&nbsp;^&nbsp;&nbsp;&nbsp;(G&gt;&gt;16)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;B&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;找出最左0字节的位置:&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;int&nbsp;&nbsp;&nbsp;zbytel(&nbsp;&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;x&nbsp;&nbsp;&nbsp;)&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;static&nbsp;&nbsp;&nbsp;cahr&nbsp;&nbsp;&nbsp;table[16]&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;{&nbsp;&nbsp;&nbsp;4,3,2,2,&nbsp;&nbsp;&nbsp;1,1,1,1,&nbsp;&nbsp;&nbsp;0,0,0,0,&nbsp;&nbsp;&nbsp;0,0,0,0&nbsp;&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;unsigned&nbsp;&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;(x&amp;0x7f7f7f7f)&nbsp;&nbsp;&nbsp;+&nbsp;&nbsp;&nbsp;0x7f7f7f7f&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;y&nbsp;&nbsp;&nbsp;=&nbsp;&nbsp;&nbsp;~(y|x|0x7f7f7f7f)&nbsp;&nbsp;&nbsp;;&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;return&nbsp;&nbsp;&nbsp;table[y*0x00204081&nbsp;&nbsp;&nbsp;&gt;&gt;&nbsp;&nbsp;&nbsp;28]&nbsp;&nbsp;&nbsp;;//乘法可用移位和加完成&nbsp;&nbsp;&nbsp;<br>&nbsp;&nbsp;}&nbsp;&nbsp;&nbsp;<br><br><br></p>
<p>C\C++支持比较低阶的位运算，在是众人皆知的了。每本C\C++的教科书都会说到这部分的内容，不过都很简略，我想会有很多人不知道位运算用在什么地方。这个帖子就简略说说位运算的用处，更进一步的用法要大家自己去体会。而主要说的是操作标志值方面。</p>
<p>&nbsp;</p>
<p>&nbsp;/****************************************/</p>
<p>#define&nbsp;BTI_MSK(bit)&nbsp;&nbsp;&nbsp;&nbsp;(1&nbsp;&lt;&lt;&nbsp;(bit))<br>#define&nbsp;BIT_SET(x,bit)&nbsp;&nbsp;((x)&nbsp;|=&nbsp;&nbsp;BTI_MSK&nbsp;(bit))<br>#define&nbsp;BIT_CLR(x,bit)&nbsp;&nbsp;((x)&nbsp;&amp;=&nbsp;~BTI_MSK&nbsp;(bit))<br>#define&nbsp;BIT_TST(x,bit)&nbsp;&nbsp;((x)&nbsp;&amp;&nbsp;&nbsp;&nbsp;BTI_MSK&nbsp;(bit))</p>
<p>&nbsp;/****************************************/</p>
<p>&nbsp;</p>
<p>考虑一个事物、一个系统、或者一个程序可能会出现一种或者几种状态。为了在不同的状态下，作出不同的行为，你可以设立一些标志值，再根据标志值来做判断。比如C++的文件流，你就可以设定一些标志值，ios::app,&nbsp;ios::ate,&nbsp;ios::binary,&nbsp;ios::in,&nbsp;ios::out,&nbsp;ios::trunc，并且可以将它用|组合起来创建一个恰当的文件流。你可能会将这些标志值定义为bool类型，不过这样要是设置的标志值一多，就会很浪费空间。<br><br>而假如定义一个整型数值，unsigned&nbsp;int&nbsp;flags;&nbsp;在现在的系统，flags应该是32位,&nbsp;用1,2,3....32将位进行编号，我们可以进行这样的判断,&nbsp;当位1取1时，表示用读方式打开文件，当位2取1时，表示用写方式打开文件，当位3取1时，用二进制方式打开文件....因为flags有32位，就可以设置32个不同的状态值，也相当于32个bool类型。这样一方面省了空间,&nbsp;另一方面也多了个好处，就是如前面所说的，可以将标志值组合起来。<br>//&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;<br><br>好啦，上面有点不清不楚的。下面看看到底怎么操作这些标志值。<br>设想C++的类ios这样定义,&nbsp;其实没有这个类，只有ios_basic类，typedef&nbsp;basic_ios&lt;char&gt;&nbsp;ios;<br><br>class&nbsp;ios<br>{<br>public:<br>&nbsp;&nbsp;&nbsp;&nbsp;enum&nbsp;{&nbsp;&nbsp;&nbsp;&nbsp;app&nbsp;=&nbsp;0x0001,&nbsp;ate&nbsp;=&nbsp;0x0002,&nbsp;binary&nbsp;=&nbsp;0x0004,<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;in&nbsp;=&nbsp;0x0008,&nbsp;&nbsp;out&nbsp;=&nbsp;0x0010,&nbsp;trunc&nbsp;=&nbsp;0x0020&nbsp;};<br>&nbsp;&nbsp;&nbsp;&nbsp;....<br>private:<br>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;int&nbsp;flags;<br>};<br><br>注意上面enum语句中，每一个数值只有1位是1，其余是0，这个很重要，你可以将它化成2进制看看。<br><br>现在将flags相应的位设置为1,&nbsp;可以这样做&nbsp;flags&nbsp;|=&nbsp;app。这个等于flags&nbsp;=&nbsp;flags&nbsp;|&nbsp;app,&nbsp;为什么呢?&nbsp;app只有1位是1，其余是0，因为0&nbsp;|&nbsp;1&nbsp;=&nbsp;0，&nbsp;0&nbsp;|&nbsp;0&nbsp;=&nbsp;0，&nbsp;这样0对应的位是不变的。而1&nbsp;|&nbsp;1&nbsp;=&nbsp;1,&nbsp;1&nbsp;|&nbsp;0&nbsp;=&nbsp;1,&nbsp;1对应的位不论原来是什么状态，都一定为1。如果想要将几个位都设置为1，可以这样做&nbsp;flags&nbsp;|=&nbsp;(app&nbsp;|&nbsp;ate&nbsp;|&nbsp;binary)。因为每个enum常数各有一位为1,&nbsp;与运算之后就有3位为1，就如上面的分析，就可以将那3位都设置为1,&nbsp;其余位不变。这个就是标志可以组合起来用的原因。也可以用+组合起来，原因在于(下面的数字是2进制)0001&nbsp;+&nbsp;0010&nbsp;+&nbsp;0100&nbsp;=&nbsp;0111&nbsp;跟与运算结果一样。不过不提倡用+,&nbsp;考虑(app&nbsp;|&nbsp;ate&nbsp;|&nbsp;binary)要是我不小心写多了个标志值，(app&nbsp;|&nbsp;ate&nbsp;|&nbsp;ate&nbsp;|&nbsp;binary)结果还是正确的，如果用+的话，就会产生进位，结果就会错误。通常我们不知道原先已经组合了多少个标志值了，用或运算会安全。<br><br>现在将flags对应的位设置为0,&nbsp;可以这样做&nbsp;flags&nbsp;&amp;=&nbsp;~app。相当于&nbsp;flags&nbsp;=&nbsp;flags&nbsp;&amp;&nbsp;(~app).&nbsp;app取反之后，只有1位是0，其余是1，做与运算之后，1对应的位并不会改变，0对应的为不管原来是1是0，都肯定为0，这样就将对应的位设置了0。同样同时设置几个标志位可以这样做，flags&nbsp;&amp;=&nbsp;~(app&nbsp;|&nbsp;ate&nbsp;|&nbsp;binary)。<br><br>现在将flags对应的位，如果是1就变成0，如果是0就变成1，可以这样做&nbsp;flags&nbsp;^=&nbsp;app。同时设置几个标志位可以写成&nbsp;flags&nbsp;^=&nbsp;(app&nbsp;|&nbsp;ate&nbsp;|&nbsp;binary)。不再做分析了，不然就太罗嗦了。不过也给大家一个例子，你查查Ascii表，会发现对应的大小写字母是相差倒数第6位，可以用这样的函数统一的将大写变成小写，小写变成大写。<br>void&nbsp;xchgUppLow(string&amp;&nbsp;letters)<br>{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;const&nbsp;unsigned&nbsp;int&nbsp;mask&nbsp;=&nbsp;(1&lt;&lt;5);<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;(size_t&nbsp;i=0;&nbsp;i&lt;letters.length();&nbsp;i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;letters[i]&nbsp;^=&nbsp;mask;<br>}<br>前提是输入的string一定要全是字母,&nbsp;而要想是操作字母，可以在原来基础上加个判断。<br><br>好啦，上面已经可以设置flags的对应位值了，要是判断呢？可以这样写&nbsp;if&nbsp;(flags&nbsp;&amp;&nbsp;app)&nbsp;这样可以判断对应的位值是否为1,&nbsp;因为C\C++语言中非0就真。app只有一位是1，其余是0，如果,&nbsp;flags的对应位也是0，在与操作下就得到结果0，反之非0，这样就可以判断标志位了。<br><br>//&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;<br>上面关于标志值的操作就介绍完毕。其实在C++中已经有了个bitset了，没有必要去自己进行低阶的位运算，上面的四个操作在bitset中分别叫做set,&nbsp;reset,&nbsp;flip,&nbsp;test。不过在C中，这样的代码还很常见,&nbsp;反正知道多点也没有坏处。<br><br>用&nbsp;windows&nbsp;API&nbsp;编程，你也经常会碰到这样的标志值，要互相组合，可以用|,&nbsp;也可以用+(只是建议用|，理由上面说了).&nbsp;它的标志值也是这样定义的，不过用#define<br>#define&nbsp;WS_BORDER&nbsp;&nbsp;&nbsp;&nbsp;0x0001<br>#define&nbsp;WS_CAPTION&nbsp;&nbsp;&nbsp;&nbsp;0x0002<br>......<br>当初我就是想不明白为什么可以用|或者用+来组合，现在知道了。<br><br>(注：上面出现的数字是我自己作的，到底实际怎么定义其实没有关系，只要保证只有一位是1，其余是0就可以的了.&nbsp;因为编程的时候用的是常量值，没有人这样笨去直接用数值的)<br><br>//&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;<br>其实，位运算还有很多用处。比如移位相当于乘除2的幂数(不过通常编译器也将乘除2的幂数优化成汇编的移位指令，所以没有必要不要这样卖弄了。汇编的移位指令有两组，分别针对有符号和无符号的,&nbsp;我猜想在C\C++的同一移位运算针对有符号整数和无符号整数的不同，会根据情况编译成不同的汇编移位指令，不过没有去证实),&nbsp;其实移位更用得多的地方是去构造一个掩码,&nbsp;比如上面的mask&nbsp;=&nbsp;(1&lt;&lt;5);<br><br>还有&amp;运算，有时候可以用来求余数。比如&nbsp;value&nbsp;&amp;&nbsp;(1&lt;&lt;4&nbsp;-&nbsp;1)&nbsp;这相当于将value的高位全变成0了，效果等于&nbsp;value&nbsp;%&nbsp;8.&nbsp;<br><br>还有值得一提的是^运算，它有个很特殊的性质。比如&nbsp;A&nbsp;^=&nbsp;B,&nbsp;变成另一个数，跟着再执行A&nbsp;^=&nbsp;B，又变回原来的数了，不信你可以列真值表或者化简逻辑式看看。就因为这个性质，^有很多用途。比如加密，你将原文看成A,&nbsp;用同一个B异或一次，就相当于加密，跟着在用B异或一次，相当于解密。不过这样是很容易破解就是了。要是一个B不够，还可以加个C,&nbsp;比如A&nbsp;^=&nbsp;B,&nbsp;A&nbsp;^=&nbsp;C,&nbsp;A&nbsp;^=&nbsp;C,&nbsp;A&nbsp;^=&nbsp;B,&nbsp;恢复原状。<br><br>下面一个小程序，用异或交换两个数字。<br>int&nbsp;x&nbsp;=&nbsp;3;<br>int&nbsp;y&nbsp;=&nbsp;4;<br><br>x&nbsp;^=&nbsp;y;<br>y&nbsp;^=&nbsp;x;<br>x&nbsp;^=&nbsp;y;<br><br>其实何止交换数字，连交换对象也可以的<br>template&nbsp;&lt;typename&nbsp;T&gt;<br>void&nbsp;swap(T&amp;&nbsp;obj1,&nbsp;T&amp;&nbsp;obj2)<br>{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;const&nbsp;int&nbsp;sizeOfObj&nbsp;=&nbsp;sizeof(T);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;char*&nbsp;pt1&nbsp;=&nbsp;(char*)&amp;obj1;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;char*&nbsp;pt2&nbsp;=&nbsp;(char*)&amp;obj2;<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;(size_t&nbsp;i=0;&nbsp;i&lt;sizeOfObj;&nbsp;i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt1[i]&nbsp;^=&nbsp;pt2[i];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt2[i]&nbsp;^=&nbsp;pt1[i];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;pt1[i]&nbsp;^=&nbsp;pt2[i];<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br>}<br><br>还有异或操作还可以用在图象的光栅操作。我们知道，颜色也是用二进制来表示的，对颜色进行不同的位运算，就可以得到不同的光栅。因为异或的特殊性质，我们用异或操作的光栅画了副图，跟着再在原来的地方画一次，那副图就刷除了。这样可以用来显示动画而不用保存原来的画像信息。以前我写过个双人的贪食蛇，就用了异或光栅。因为背景色是白色的，也就是全1，作A&nbsp;^&nbsp;1&nbsp;=&nbsp;A,&nbsp;所以用画刷画一次是画了设定的颜色，再画一次就恢复。最有趣的是两蛇相交的时候，颜色也会作异或叠加，产生一种新的颜色了，离开的时候也会自动恢复。<br>//&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;<br>好啦，够长了，就停止吧。在最后再给大家一段代码，是用来看看对象在内存中的位值的。可以看看。<br>string&nbsp;bitsOfUChar(unsigned&nbsp;char&nbsp;c)<br>{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;const&nbsp;int&nbsp;numOfBitsInUChar&nbsp;=&nbsp;8;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;int&nbsp;mask&nbsp;=&nbsp;(1&lt;&lt;7);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;string&nbsp;result(8,&nbsp;'0');<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;(size_t&nbsp;i=0;&nbsp;i&lt;numOfBitsInUChar;&nbsp;i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if&nbsp;(&nbsp;mask&nbsp;&amp;&nbsp;c)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;result[i]&nbsp;=&nbsp;'1';<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;mask&nbsp;&gt;&gt;=&nbsp;1;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;result;<br>}<br><br>template&nbsp;&lt;typename&nbsp;T&gt;<br>string&nbsp;bitsInMemory(const&nbsp;T&amp;&nbsp;obj)<br>{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;int&nbsp;sizeOfObj&nbsp;=&nbsp;sizeof(obj);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;char*&nbsp;pt&nbsp;=&nbsp;(unsigned&nbsp;char*)&amp;obj;<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;string&nbsp;result;<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;(size_t&nbsp;i=0;&nbsp;i&lt;sizeOfObj;&nbsp;i++)<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;result&nbsp;+=&nbsp;bitsOfUChar(pt[i]);<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;result&nbsp;+=&nbsp;'&nbsp;';<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;result;<br>}<br><br>比如bitsInMemory(12)，会输出00001100&nbsp;00000000&nbsp;00000000&nbsp;00000000,&nbsp;我就知道我自己的机器是小尾顺序的了。<br></p>
<img src ="http://www.cppblog.com/Walker/aggbug/80466.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Walker/" target="_blank">漫步者×&……%￥</a> 2009-04-19 20:44 <a href="http://www.cppblog.com/Walker/articles/80466.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>