⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tij0168.html

📁 学习java的经典书籍
💻 HTML
📖 第 1 页 / 共 5 页
字号:
  }
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">The
beauty of the <A NAME="Index2782"></A><A NAME="Index2783"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>URL</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
class is how much it shields you from. You can connect to Web servers without
knowing much at all about what&#8217;s going on under the covers.
</FONT><a name="_Toc408018779"></a><P></DIV>
<A NAME="Heading531"></A><H3 ALIGN=LEFT>
The
CGI program in C++
<P><A NAME="Index2784"></A><A NAME="Index2785"></A><A NAME="Index2786"></A></H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">At
this point you could follow the previous example and write the CGI program for
the server using ANSI C. One argument for doing this is that ANSI C can be
found virtually everywhere. However, C++ has become quite ubiquitous,
especially in the form of the <A NAME="Index2787"></A><A NAME="Index2788"></A>GNU
C++ Compiler
</FONT><A NAME="fnB66" HREF="#fn66">[66]</A><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
(
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>g++</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">)</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">that
can be downloaded free from the Internet for virtually any platform (and often
comes pre-installed with operating systems such as Linux). As you will see,
this means that you can get the benefit of object-oriented programming in a CGI
program.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">To
avoid throwing too many new concepts at you all at once, this program will not
be a &#8220;pure&#8221; C++ program; some code will be written in plain C even
though C++ alternatives exist. This isn&#8217;t a significant issue because the
biggest benefit in using C++ for this program is the ability to create classes.
Since what we&#8217;re concerned with when parsing the CGI information is the
field name-value pairs, one class (
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">)</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">will
be used to represent a single name-value pair and a second class (
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CGI_vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">)
will automatically parse the CGI string into 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
objects that it will hold (as a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">)
so you can fetch each 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
out at your leisure.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">This
program is also interesting because it demonstrates some of the pluses and
minuses of <A NAME="Index2789"></A><A NAME="Index2790"></A>C++
in contrast with Java. You&#8217;ll see some similarities; for example the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>class</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
keyword. Access control has identical keywords 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>public</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>private</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
but they&#8217;re used differently: they control a block instead of a single
method or field (that is, if you say 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>private:</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
each following definition is 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>private</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
until you say 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>public:</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">).
Also, when you create a class, all the definitions automatically default to 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>private</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">One
of the reasons for using C++ here is the convenience of the <A NAME="Index2791"></A><A NAME="Index2792"></A><A NAME="Index2793"></A>C++
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>Standard
Template Library
</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
Among other things, the STL contains a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
class. This is a C++ 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>template</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
which means that it will be configured at compile time so it will hold objects
of only a particular type (in this case, 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
objects). Unlike the Java 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
which will accept anything, the C++ 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
template will cause a compile-time error message if you try to put anything but
a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object into the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
and when you get something out of the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
it will automatically be a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object, without casting. Thus, the checking happens at compile time and
produces a more robust program. In addition, the program can run faster since
you don&#8217;t have to perform run-time casts. The 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">also
overloads the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>operator[]
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">so
you have a convenient syntax for extracting 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">objects.
The 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
template will be used in the creation of 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CGI_vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
which you&#8217;ll see is a fairly short definition considering how powerful it
is.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">On
the down side, look at the complexity of the definition of 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
in the following code. 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">has
more method definitions than you&#8217;re used to seeing in Java code, because
the C++ programmer must know how to control copying with the copy-constructor
and assignment with the overloaded 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>operator=</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
As described in Chapter 12, occasionally you need to concern yourself with
similar things in Java, but in C++ you must be aware of them almost constantly.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">The
project will start with a reusable portion, which consists of 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Pair</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CGI_vector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
in a C++ header file. Technically, you shouldn&#8217;t cram this much into a
header file, but for these examples it doesn&#8217;t hurt anything and it will
also look more Java-like, so it will be easier for you to read:
</FONT><P></DIV>

<font color="#990000"><PRE><font color="#009900">//: CGITools.h</font>
<font color="#009900">// Automatically extracts and decodes data</font>
<font color="#009900">// from CGI GETs and POSTs. Tested with GNU C++ </font>
<font color="#009900">// (available for most server machines).</font>
#include &lt;string.h&gt;
#include &lt;vector&gt; <font color="#009900">// STL vector</font>
using namespace std;

<font color="#009900">// A class to hold a single name-value pair from</font>
<font color="#009900">// a CGI query. CGI_vector holds Pair objects and</font>
<font color="#009900">// returns them from its operator[].</font>
<font color="#0000ff">class</font> Pair {
  <font color="#0000ff">char</font>* nm;
  <font color="#0000ff">char</font>* val;
<font color="#0000ff">public</font>:
  Pair() { nm = val = 0; }
  Pair(<font color="#0000ff">char</font>* name, <font color="#0000ff">char</font>* value) {
    <font color="#009900">// Creates new memory:</font>
    nm = decodeURLString(name);
    val = decodeURLString(value);
  }
  <font color="#0000ff">const</font> <font color="#0000ff">char</font>* name() <font color="#0000ff">const</font> { <font color="#0000ff">return</font> nm; }
  <font color="#0000ff">const</font> <font color="#0000ff">char</font>* value() <font color="#0000ff">const</font> { <font color="#0000ff">return</font> val; }
  <font color="#009900">// Test for "emptiness"</font>
  bool empty() <font color="#0000ff">const</font> {
    <font color="#0000ff">return</font> (nm == 0) || (val == 0);
  }
  <font color="#009900">// Automatic type conversion for boolean test:</font>
  operator bool() <font color="#0000ff">const</font> {
    <font color="#0000ff">return</font> (nm != 0) &amp;&amp; (val != 0);
  }
  <font color="#009900">// The following constructors &amp; destructor are</font>
  <font color="#009900">// necessary for bookkeeping in C++.</font>
  <font color="#009900">// Copy-constructor:</font>
  Pair(<font color="#0000ff">const</font> Pair&amp; p) {
    <font color="#0000ff">if</font>(p.nm == 0 || p.val == 0) {
      nm = val = 0;
    } <font color="#0000ff">else</font> {
      <font color="#009900">// Create storage &amp; copy rhs values:</font>
      nm = <font color="#0000ff">new</font> <font color="#0000ff">char</font>[strlen(p.nm) + 1];
      strcpy(nm, p.nm);
      val = <font color="#0000ff">new</font> <font color="#0000ff">char</font>[strlen(p.val) + 1];
      strcpy(val, p.val);
    }
  }
  <font color="#009900">// Assignment operator:</font>
  Pair&amp; operator=(<font color="#0000ff">const</font> Pair&amp; p) {
    <font color="#009900">// Clean up old lvalues:</font>
    delete nm;
    delete val;
    <font color="#0000ff">if</font>(p.nm == 0 || p.val == 0) {
      nm = val = 0;
    } <font color="#0000ff">else</font> {
      <font color="#009900">// Create storage &amp; copy rhs values:</font>
      nm = <font color="#0000ff">new</font> <font color="#0000ff">char</font>[strlen(p.nm) + 1];
      strcpy(nm, p.nm);
      val = <font color="#0000ff">new</font> <font color="#0000ff">char</font>[strlen(p.val) + 1];
      strcpy(val, p.val);
    }
    <font color="#0000ff">return</font> *<font color="#0000ff">this</font>;
  } 
  ~Pair() { <font color="#009900">// Destructor</font>
    delete nm; <font color="#009900">// 0 value OK</font>
    delete val;
  }
  <font color="#009900">// If you use this method outide this class, </font>
  <font color="#009900">// you're responsible for calling 'delete' on</font>
  <font color="#009900">// the pointer that's returned:</font>
  <font color="#0000ff">static</font> <font color="#0000ff">char</font>* 
  decodeURLString(<font color="#0000ff">const</font> <font color="#0000ff">char</font>* URLstr) {
    <font color="#0000ff">int</font> len = strlen(URLstr);
    <font color="#0000ff">char</font>* result = <font color="#0000ff">new</font> <font color="#0000ff">char</font>[len + 1];
    memset(result, len + 1, 0);
    <font color="#0000ff">for</font>(<font color="#0000ff">int</font> i = 0, j = 0; i &lt;= len; i++, j++) {
      <font color="#0000ff">if</font>(URLstr[i] == '+')
        result[j] = ' ';
      <font color="#0000ff">else</font> <font color="#0000ff">if</font>(URLstr[i] == '%') {
        result[j] =

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -