写了两段代码,JAVA充当服务端,C#充当客户端,JAVA先跑起来,等待C#的来信,但是如果C#一旦断掉,JAVA端就报错,帮忙看看了。
服务端public class ServerForOpenSim extends Thread {
ServerSocket serverSocket;
// MAS -> OpenSim port 11001
// OpenSim -> MAS port 11000
int port = 11001;
Socket so; // 保存从 OpenSim 发来的信息
private Vector<String> m_arrayListMsg = new Vector();
private Object locker = new Object();
public void copyOutReceiveMsg( Vector<String> _VecMsg ) {
synchronized (locker) {
int size = this.m_arrayListMsg.size();
for (int i = 0; i < size; i++) {
_VecMsg.add(this.m_arrayListMsg.elementAt(i));
}
this.m_arrayListMsg.clear();
}
}
public ServerForOpenSim() {
try {
this.serverSocket = new ServerSocket(this.port);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} }
public void run() {
System.out.println("[ServerForOpenSim]: Started");
try {
byte[] buff = new byte[1024];
try {
so = this.serverSocket.accept();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
while (true) {
Thread.sleep(300);
synchronized (locker) { int read = so.getInputStream().read(buff);
System.out.println("[ServerForOpenSim]: Receive information");
System.out.println(new String(buff));
String ss = new String(buff, 0, read);
this.m_arrayListMsg.add(ss);
}
}
} catch (Exception ex) {
ex.printStackTrace();
}
finally {
try {
so.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}客户端 class MainClient
{
#region Field
TcpClient client;
int port = 11001;
List<string> msgVec;// ColorOutPut m_cop; Thread t_sendMsgToMAS; //用于不断准备发射消息的线程 object locker = new object(); // the object class that used to bool start = false;
#endregion
public MainClient()
{
// m_cop = new ColorOutPut("MainClient", ConsoleColor.DarkGreen);
this.msgVec = new List<string>();
}
// 启动对于MAS的客户端
public void StartListening()
{
client = new TcpClient("localhost", this.port);
t_sendMsgToMAS = new Thread(new ThreadStart(sendMsgToMAS));
t_sendMsgToMAS.Name = "sendMsgToMAS";
this.t_sendMsgToMAS.Start();
this.start = true;
}
// 停止监听
public void StopListening()
{
if (!start) return;
this.t_sendMsgToMAS.Abort();
} public void setMsg(string _msg)
{
if (_msg == null)
return; // lock the msgVec when any avatar is trying to add message into the msgVec
lock (locker)
{
//Monitor.Enter(this.msgVec);
this.msgVec.Add(_msg);
//Monitor.Exit(this.msgVec);
} } private void sendMsgToMAS()
{ while (true)
{
Thread.Sleep(300);
lock (locker) {
if (this.msgVec.Count > 0)
{
int size = this.msgVec.Count;
for (int i = 0; i < size; i++)
{
NetworkStream ns = client.GetStream();
string msg = (string)this.msgVec[i];
byte[] b = System.Text.Encoding.ASCII.GetBytes(msg);
ns.Write(b, 0, b.Length);
ns.Flush();
this.msgVec.RemoveAt(i);
}
}
} } }
}启动客户端的代码 class Program
{
static void Main(string[] args)
{ MainClient mc = new MainClient();
mc.StartListening(); mc.setMsg("message 1");
Thread.Sleep(5000);
mc.setMsg("message 2");
}
}
服务端public class ServerForOpenSim extends Thread {
ServerSocket serverSocket;
// MAS -> OpenSim port 11001
// OpenSim -> MAS port 11000
int port = 11001;
Socket so; // 保存从 OpenSim 发来的信息
private Vector<String> m_arrayListMsg = new Vector();
private Object locker = new Object();
public void copyOutReceiveMsg( Vector<String> _VecMsg ) {
synchronized (locker) {
int size = this.m_arrayListMsg.size();
for (int i = 0; i < size; i++) {
_VecMsg.add(this.m_arrayListMsg.elementAt(i));
}
this.m_arrayListMsg.clear();
}
}
public ServerForOpenSim() {
try {
this.serverSocket = new ServerSocket(this.port);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} }
public void run() {
System.out.println("[ServerForOpenSim]: Started");
try {
byte[] buff = new byte[1024];
try {
so = this.serverSocket.accept();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
while (true) {
Thread.sleep(300);
synchronized (locker) { int read = so.getInputStream().read(buff);
System.out.println("[ServerForOpenSim]: Receive information");
System.out.println(new String(buff));
String ss = new String(buff, 0, read);
this.m_arrayListMsg.add(ss);
}
}
} catch (Exception ex) {
ex.printStackTrace();
}
finally {
try {
so.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}客户端 class MainClient
{
#region Field
TcpClient client;
int port = 11001;
List<string> msgVec;// ColorOutPut m_cop; Thread t_sendMsgToMAS; //用于不断准备发射消息的线程 object locker = new object(); // the object class that used to bool start = false;
#endregion
public MainClient()
{
// m_cop = new ColorOutPut("MainClient", ConsoleColor.DarkGreen);
this.msgVec = new List<string>();
}
// 启动对于MAS的客户端
public void StartListening()
{
client = new TcpClient("localhost", this.port);
t_sendMsgToMAS = new Thread(new ThreadStart(sendMsgToMAS));
t_sendMsgToMAS.Name = "sendMsgToMAS";
this.t_sendMsgToMAS.Start();
this.start = true;
}
// 停止监听
public void StopListening()
{
if (!start) return;
this.t_sendMsgToMAS.Abort();
} public void setMsg(string _msg)
{
if (_msg == null)
return; // lock the msgVec when any avatar is trying to add message into the msgVec
lock (locker)
{
//Monitor.Enter(this.msgVec);
this.msgVec.Add(_msg);
//Monitor.Exit(this.msgVec);
} } private void sendMsgToMAS()
{ while (true)
{
Thread.Sleep(300);
lock (locker) {
if (this.msgVec.Count > 0)
{
int size = this.msgVec.Count;
for (int i = 0; i < size; i++)
{
NetworkStream ns = client.GetStream();
string msg = (string)this.msgVec[i];
byte[] b = System.Text.Encoding.ASCII.GetBytes(msg);
ns.Write(b, 0, b.Length);
ns.Flush();
this.msgVec.RemoveAt(i);
}
}
} } }
}启动客户端的代码 class Program
{
static void Main(string[] args)
{ MainClient mc = new MainClient();
mc.StartListening(); mc.setMsg("message 1");
Thread.Sleep(5000);
mc.setMsg("message 2");
}
}
服务端的run方法里个while(true)死循环,一旦客户端断开,就会不停的抛出错误。
// 还有这段应该写在一个while循环里去,才能继续接受客户端的连接
try {
so = this.serverSocket.accept();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}服务端你可以分成2个线程来做,一个线程用于上面的不断的accept,另一个线程用来处理客户端的请求。
ServerSocket serverSocket;
// MAS -> OpenSim port 11001
// OpenSim -> MAS port 11000
int port = 11001;
Socket so;
boolean isRun = true; // 保存从 OpenSim 发来的信息
private Vector<String> m_arrayListMsg = new Vector();
private Object locker = new Object();
public void copyOutReceiveMsg( Vector<String> _VecMsg ) {
synchronized (locker) {
int size = this.m_arrayListMsg.size();
for (int i = 0; i < size; i++) {
_VecMsg.add(this.m_arrayListMsg.elementAt(i));
}
this.m_arrayListMsg.clear();
}
}
public ServerForOpenSim() {
try {
this.serverSocket = new ServerSocket(this.port);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void run() {
System.out.println("[ServerForOpenSim]: Started");
while(isRun){
try {
so = this.serverSocket.accept();
new HandlerThread(so,m_arrayListMsg).start();
} catch (IOException e) {
// TODO Auto-generated catch block
isRun = false;
e.printStackTrace();
}
}
}
}下面是处理线程:class HandlerThread extends Thread{
boolean isRun = true;
Socket so = null;
Vector<String> m_arrayListMsg = null;
public HandlerThread(Socket so,Vector<String> m_arrayListMsg){
this.so = so;
}
public void run() {
byte[] buff = new byte[1024];
while (isRun) {
try {
Thread.sleep(300);
int read = so.getInputStream().read(buff);
System.out.println("[ServerForOpenSim]: Receive information");
System.out.println(new String(buff));
String ss = new String(buff, 0, read);
this.m_arrayListMsg.add(ss);
} catch (Exception ex) {
ex.printStackTrace();
isRun = false;
}
}
try {
so.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}这里要说一下,Vector是线程安全的,他里面的方法都是加了synchronized 修饰的,
所以this.m_arrayListMsg.add(ss); 没有必要再加到synchronized块里。