0 0

下面两种定义变量的方法为什么会导致本质上的不同呢?0

这是一个简单的聊天系统模型:
ChatClient.java
<code>import java.awt.*;
import java.awt.event.*;
import java.io.*;
import java.net.*;

public class ChatClient extends Frame {

TextField input = new TextField();
TextArea display = new TextArea();
Socket s = null;
boolean bConnected = false;
DataOutputStream dos = null;
DataInputStream dis = null;

public static void main(String[] args) {
new ChatClient().launchFrame();
}

// 定义创建窗体方法
public void launchFrame() {
setLocation(768, 384);
setSize(400, 300);
addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
System.exit(0);
}
});
input.addActionListener(new InputListener());
add(input, BorderLayout.SOUTH);
add(display, BorderLayout.NORTH);
pack();
setResizable(false);
setVisible(true);
connect();
new Thread(new RecvThread()).start();

}

// 创建方法,连接到服务器
public void connect() {
try {
s = new Socket("127.0.0.1", 3000);
bConnected = true;
dos = new DataOutputStream(s.getOutputStream());
dis = new DataInputStream(s.getInputStream());
} catch (IOException e) {
e.printStackTrace();
}
}

// 监听器类,用于监听输入框动作
private class InputListener implements ActionListener {
public void actionPerformed(ActionEvent e) {
String str = input.getText().trim();
// display.setText(str);
input.setText("");
try {
dos.writeUTF(str);
dos.flush();
} catch (IOException e1) {
e1.printStackTrace();
}
}

}

// 新建线程类来接受服务器发送过来的数据
private class RecvThread implements Runnable {

public void run() {
try {
while (bConnected) {
String str = dis.readUTF();
// System.out.println("客户端发送的数据:"+str);
display.setText(str);
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}</code>

ChatServer.java
第一种:
<code>import java.io.*;
import java.net.*;
import java.util.*;

public class ChatServer {
// 用集合将客户端对象保存起来
List<Client> clients = new ArrayList<Client>();
DataInputStream dis = null;
DataOutputStream dos = null;
boolean bConnected = false;
    Socket s =null;
    boolean started = false;
   
public static void main(String[] args) {
new ChatServer().start();
}

// 创建启动方法
public void start() {
try {
ServerSocket ss = new ServerSocket(3000);
started = true;
// 循环,不断接受来自客户端的连接
while (started) {
s = ss.accept();
// 测试
System.out.println("a client connected!!!");
//bConnected = true;
Client c = new Client(s);
new Thread(c).start();
clients.add(c);
}
} catch (IOException e) {
e.printStackTrace();
}
}

// 定义线程类,处理多个连接
private class Client implements Runnable {
private Socket s;
// 构造器为s赋值
public Client(Socket s) {
this.s = s;
try {
dos = new DataOutputStream(s.getOutputStream());
dis = new DataInputStream(s.getInputStream());
bConnected = true;
} catch (IOException e) {
e.printStackTrace();
}
}

// 发送信息到客户端的方法
private void send(String str) {
try {
dos.writeUTF(str);
dos.flush();
} catch (IOException e) {
e.printStackTrace();
}
}

// 启动线程
public void run() {
try {
while (bConnected) {
String str = dis.readUTF();
for (int i = 0; i < clients.size(); i++) {
Client c = clients.get(i);
c.send(str);
}
}
} catch (IOException e) {
e.printStackTrace();
}

}
}
}</code>

第二种:
<code>import java.io.*;
import java.net.*;
import java.util.*;

public class ChatServer {
// 用集合将客户端对象保存起来
List<Client> clients = new ArrayList<Client>();
DataInputStream dis = null;
DataOutputStream dos = null;
boolean bConnected = false;
    Socket s =null;
    boolean started = false;
   
public static void main(String[] args) {
new ChatServer().start();
}

// 创建启动方法
public void start() {
try {
ServerSocket ss = new ServerSocket(3000);
started = true;
// 循环,不断接受来自客户端的连接
while (started) {
s = ss.accept();
// 测试
System.out.println("a client connected!!!");
//bConnected = true;
Client c = new Client(s);
new Thread(c).start();
clients.add(c);
}
} catch (IOException e) {
e.printStackTrace();
}
}

// 定义线程类,处理多个连接
private class Client implements Runnable {
private Socket s;
/*  private DataOutputStream dos;
    private DataInputStream dis ; */
// 构造器为s赋值
public Client(Socket s) {
this.s = s;
try {
dos = new DataOutputStream(s.getOutputStream());
dis = new DataInputStream(s.getInputStream());
bConnected = true;
} catch (IOException e) {
e.printStackTrace();
}
}

// 发送信息到客户端的方法
private void send(String str) {
try {
dos.writeUTF(str);
dos.flush();
} catch (IOException e) {
e.printStackTrace();
}
}

// 启动线程
public void run() {
try {
while (bConnected) {
String str = dis.readUTF();
for (int i = 0; i < clients.size(); i++) {
Client c = clients.get(i);
c.send(str);
}
}
} catch (IOException e) {
e.printStackTrace();
}

}
}
}</code>
2013年3月17日 21:29
目前还没有答案

相关推荐

    JavaScript全局变量的本质及页面共享问题 -页面

    这两个API允许开发者在用户的浏览器上存储键值对,但它们的生命周期和使用场景各有不同:localStorage的数据在浏览器关闭后仍然保留,而sessionStorage的数据仅在当前会话期间有效。 总之,理解JavaScript全局变量...

    C学习深入学习总结

    1.5 全局变量为什么不允许定义在头文件中?有何危害? 3 2 Static 4 2.1 static的三个主要作用是什么? 4 2.2 static的修饰的局部变量是保存在什么地方的?全局变量哪? 5 2.3 static修饰的全局变量和函数,在其他的...

    在Python中居然可以定义两个同名通参数的函数

    为了更好地理解为什么Python允许这样的覆盖行为,我们需要回顾一下Python的作用域规则。Python采用LEGB规则来查找变量: 1. **Local** (局部作用域):当前函数体内的变量。 2. **Enclosing** (封闭作用域):对于嵌套...

    Jdk环境变量中classpath和path变量实质与设置.pdf

    本文将详细解释PATH和CLASSPATH这两个关键环境变量的实质和设置方法。 首先,PATH环境变量是操作系统用来查找可执行文件(如javac.exe)的路径列表。当你在命令行输入一个命令时,系统会在PATH变量定义的各个目录中...

    C++_作业_7_答案1

    Lambda表达式实质上是一个对象,它可以赋值给一个变量(在这里是`f`),并且可以作为参数传递。 4. **类模板实例化**:类模板是泛型编程的基础,它可以通过两种方式实例化:显式实例化和隐式实例化。显式实例化是...

    PLSQL绑定变量用法小结归纳.pdf

    在Oracle中,对于一个提交的SQL语句,存在两种可选的解析过程,一种叫做硬解析,一种叫做软解析。硬解析需要经解析、制定执行路径、优化访问计划等许多的步骤,硬解释不仅仅耗费大量的CPU,更重要的是会占据重要的...

    python交换两个变量的值方法

    Python提供了一种更加简洁且高效的方法来交换两个变量的值,即使用元组赋值的方式。这种方式不需要任何临时变量,代码更为简洁。 **代码示例:** ```python # 定义两个变量 a = 10 b = 20 # 交换变量a和b的值 (a,...

    第8章 指针-2指针变量作函数参数 - 典型实例 - 两数交换new1

    首先,我们来看一个简单的两数互换的例子,这里涉及到两种不同的函数调用方式:按值传递(Call by Value)和按引用传递(Call by Reference)。在C语言中,函数参数的传递默认是按值传递,这意味着函数接收到的是...

    C/C++中static,const,inline三种关键字详细总结

    引出原因:函数内部定义的变量,在程序执行到它的定义处时,编译器为它在栈上分配空间,大家知道,函数在栈上分配的空间在此函数执行结束时会释放掉,这样就产生了一个问题: 如果想将函数中此变量的值保存至下一次...

    详细介绍了渐进方法的定义、理论、应用等

    这两种方法分别处理不同类型的扰动问题,下面将详细介绍这两种理论及其应用场景。 #### 正则扰动理论 正则扰动理论适用于那些扰动项对系统的影响可以被线性化处理的情况。在这种情况下,原始方程可以通过引入一个...

    宏定义和函数调用的区别

    在探讨宏定义与函数调用的区别时,我们深入解析它们在C语言编程中的特性、应用场景以及潜在风险,以便更全面地理解这两种编程机制。 ### 宏定义与函数调用的本质区别 #### 宏定义(#define) 宏定义是预处理器的一...

    c语言中头文件的建立与使用-函数、全局变量、全局数组

    头文件本质上是一个包含了函数声明、变量声明、常量定义、宏定义等的文本文件。通过使用头文件,可以在多个源文件(`.c`文件)之间共享这些定义。创建头文件的方法非常简单,只需要使用文本编辑器编写相应的代码,并以...

    100多个javescript函数[定义].pdf

    变量的作用域无非就是两种:全局变量和局部变量。Javascript语言的特殊之处就在于函数内部可以直接读取全局变量。 例如: ```javascript var n = 999; function f1() { alert(n); } f1(); // 999 ``` 然而,在函数...

    SeDuMi优化方法书籍

    Lorentz锥定义为在n维空间内满足第一个分量大于等于其余分量的平方和的平方根的点的集合,而旋转Lorentz锥则在形式上略有不同,但本质上也是锥体结构。这两种锥体在SOCP问题中占据着重要的地位。 SeDuMi的使用指南...

    C语言程序设计标准教程

    1. 从函数定义的角度看,函数可分为库函数和用户定义函数两种。 (1)库函数  由C系统提供,用户无须定义, 也不必在程序中作类型说明,只需在程序前包含有该函数原型的头文件即可在程序中直接调用。在前面各章的...

    单片机宏定义学习手记

    宏定义通常用在需要反复使用某段代码,且这些代码本质上不会改变的情况下。在单片机编程中,宏定义可以用于简化寄存器操作、控制硬件、配置I/O口等操作。在本文中,作者通过EM78P260单片机的宏定义实践,展示了宏...

    c代码-枚举类型的定义和枚举变量的说明

    尽管枚举类型提供了一种方便的方式来表示和操作一组相关的整数值,但它们本质上仍然是整数类型。这意味着你可以进行类型转换,将枚举值与整数互换: ```c int colorValue = (int)myColor; // 将枚举变量转换为整数 ...

    随机试验和随机变量.pdf

    《随机试验和随机变量》是统计学的基础章节,旨在引导学生理解随机现象的本质以及如何通过随机试验和随机变量来描述和分析这些现象。本章涵盖了以下几个核心知识点: 1. **随机现象**:随机现象指的是在特定条件下...

Global site tag (gtag.js) - Google Analytics