📄 tij0167.html
字号:
object:
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getOutputStream( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getInputStream( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
From this point on, all you need to consider is sending data to the stream
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>nameList</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and getting the results from
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>addResult</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">As
before, a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>DatagramSocket</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
is connected to a port. Inside the infinite
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>while</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
loop, the program calls
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>receive( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
which blocks until a datagram shows up. When the datagram appears, its contents
are extracted into the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>String
rcvd
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
This is trimmed to remove white space at each end and sent to the C program in
the line:
</FONT><P></DIV><DIV ALIGN=LEFT><TT><FONT FACE="Courier New" SIZE=3 COLOR="Black">nameList.println(rcvd.trim());</FONT></TT><P></DIV><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">This
is only possible because Java’s
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>exec( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
provides access to any executable that reads from standard input and writes to
standard output. There are other ways to talk to non-Java code, which are
discussed in Appendix A.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Capturing
the result from the C program is slightly more complicated. You must call <A NAME="Index2720"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>read( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and provide a buffer where the results will be placed. The return value for
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>read( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
is the number of bytes that came from the C program, and if this value is -1 it
means that something is wrong. Otherwise, the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>resultBuf</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
is turned into a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>String</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and the spaces are trimmed off. This string is then placed into a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>DatagramPacket</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
as before and shipped back to the same address that sent the request in the
first place. Note that the sender’s address is part of the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>DatagramPacket</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
we received.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Remember
that although the C program must be compiled on the Web server, the Java
program can be compiled anywhere since the resulting byte codes will be the
same regardless of the platform on which the program will be running.
</FONT><a name="_Toc408018774"></a><P></DIV>
<A NAME="Heading524"></A><H3 ALIGN=LEFT>
The
NameSender applet
</H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">As
mentioned earlier, the applet must be written with Java 1.0<A NAME="Index2721"></A>
so that it will run on the largest number of browsers, so it’s best if
the number of classes produced is minimized. Thus, instead of using the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Dgram</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
class developed earlier, all of the <A NAME="Index2722"></A><A NAME="Index2723"></A>datagram
manipulations will be placed in line. In addition, the applet needs a thread to
listen for the reply from the server, and instead of making this a separate
thread it’s integrated into the applet by implementing the <A NAME="Index2724"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Runnable</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
interface. This isn’t as easy to read, but it produces a one-class (and
one-server-hit) applet:
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#009900">//: NameSender.java</font>
<font color="#009900">// An applet that sends an email address</font>
<font color="#009900">// as a datagram, using Java 1.02.</font>
<font color="#0000ff">import</font> java.awt.*;
<font color="#0000ff">import</font> java.applet.*;
<font color="#0000ff">import</font> java.net.*;
<font color="#0000ff">import</font> java.io.*;
<font color="#0000ff">public</font> <font color="#0000ff">class</font> NameSender <font color="#0000ff">extends</font> Applet
<font color="#0000ff">implements</font> Runnable {
<font color="#0000ff">private</font> Thread pl = <font color="#0000ff">null</font>;
<font color="#0000ff">private</font> Button send = <font color="#0000ff">new</font> Button(
"Add email address to mailing list");
<font color="#0000ff">private</font> TextField t = <font color="#0000ff">new</font> TextField(
"type your email address here", 40);
<font color="#0000ff">private</font> String str = <font color="#0000ff">new</font> String();
<font color="#0000ff">private</font> Label
l = <font color="#0000ff">new</font> Label(), l2 = <font color="#0000ff">new</font> Label();
<font color="#0000ff">private</font> DatagramSocket s;
<font color="#0000ff">private</font> InetAddress hostAddress;
<font color="#0000ff">private</font> <font color="#0000ff">byte</font>[] buf =
<font color="#0000ff">new</font> <font color="#0000ff">byte</font>[NameCollector.BUFFER_SIZE];
<font color="#0000ff">private</font> DatagramPacket dp =
<font color="#0000ff">new</font> DatagramPacket(buf, buf.length);
<font color="#0000ff">private</font> <font color="#0000ff">int</font> vcount = 0;
<font color="#0000ff">public</font> <font color="#0000ff">void</font> init() {
setLayout(<font color="#0000ff">new</font> BorderLayout());
Panel p = <font color="#0000ff">new</font> Panel();
p.setLayout(<font color="#0000ff">new</font> GridLayout(2, 1));
p.add(t);
p.add(send);
add("North", p);
Panel labels = <font color="#0000ff">new</font> Panel();
labels.setLayout(<font color="#0000ff">new</font> GridLayout(2, 1));
labels.add(l);
labels.add(l2);
add("Center", labels);
<font color="#0000ff">try</font> {
<font color="#009900">// Auto-assign port number:</font>
s = <font color="#0000ff">new</font> DatagramSocket();
hostAddress = InetAddress.getByName(
getCodeBase().getHost());
} <font color="#0000ff">catch</font>(UnknownHostException e) {
l.setText("Cannot find host");
} <font color="#0000ff">catch</font>(SocketException e) {
l.setText("Can't open socket");
}
l.setText("Ready to send your email address");
}
<font color="#0000ff">public</font> <font color="#0000ff">boolean</font> action (Event evt, Object arg) {
<font color="#0000ff">if</font>(evt.target.equals(send)) {
<font color="#0000ff">if</font>(pl != <font color="#0000ff">null</font>) {
<font color="#009900">// pl.stop(); Deprecated in Java 1.2</font>
Thread remove = pl;
pl = <font color="#0000ff">null</font>;
remove.interrupt();
}
l2.setText("");
<font color="#009900">// Check for errors in email name:</font>
str = t.getText().toLowerCase().trim();
<font color="#0000ff">if</font>(str.indexOf(' ') != -1) {
l.setText("Spaces not allowed in name");
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
<font color="#0000ff">if</font>(str.indexOf(',') != -1) {
l.setText("Commas not allowed in name");
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
<font color="#0000ff">if</font>(str.indexOf('@') == -1) {
l.setText("Name must include '@'");
l2.setText("");
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
<font color="#0000ff">if</font>(str.indexOf('@') == 0) {
l.setText("Name must preceed '@'");
l2.setText("");
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
String end =
str.substring(str.indexOf('@'));
<font color="#0000ff">if</font>(end.indexOf('.') == -1) {
l.setText("Portion after '@' must " +
"have an extension, such as '.com'");
l2.setText("");
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
<font color="#009900">// Everything's OK, so send the name. Get a</font>
<font color="#009900">// fresh buffer, so it's zeroed. For some </font>
<font color="#009900">// reason you must use a fixed size rather</font>
<font color="#009900">// than calculating the size dynamically:</font>
<font color="#0000ff">byte</font>[] sbuf =
<font color="#0000ff">new</font> <font color="#0000ff">byte</font>[NameCollector.BUFFER_SIZE];
str.getBytes(0, str.length(), sbuf, 0);
DatagramPacket toSend =
<font color="#0000ff">new</font> DatagramPacket(
sbuf, 100, hostAddress,
NameCollector.COLLECTOR_PORT);
<font color="#0000ff">try</font> {
s.send(toSend);
} <font color="#0000ff">catch</font>(Exception e) {
l.setText("Couldn't send datagram");
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
l.setText("Sent: " + str);
send.setLabel("Re-send");
pl = <font color="#0000ff">new</font> Thread(<font color="#0000ff">this</font>);
pl.start();
l2.setText(
"Waiting <font color="#0000ff">for</font> verification " + ++vcount);
}
<font color="#0000ff">else</font> <font color="#0000ff">return</font> <font color="#0000ff">super</font>.action(evt, arg);
<font color="#0000ff">return</font> <font color="#0000ff">true</font>;
}
<font color="#009900">// The thread portion of the applet watches for</font>
<font color="#009900">// the reply to come back from the server:</font>
<font color="#0000ff">public</font> <font color="#0000ff">void</font> run() {
<font color="#0000ff">try</font> {
s.receive(dp);
} <font color="#0000ff">catch</font>(Exception e) {
l2.setText("Couldn't receive datagram");
<font color="#0000ff">return</font>;
}
l2.setText(<font color="#0000ff">new</font> String(dp.getData(),
0, 0, dp.getLength()));
}
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">The
UI for the applet is quite simple. There’s a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>TextField</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
in which you type your email address, and a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Button</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
to send the email address to the server. Two
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -