在实际的应用中客户端可能需要和服务器端保持长时间的通信,即服务器需要不断地读取客户端数据,并向客户端写入数据;客户端也需要不断地读取服务器数据,并向服务器写入数据。
简单实现代码如下:
1 public class MyServer { 2 //定义保存所有Socket的ArrayList 3 public staticArrayList socketList = newArrayList(); 4 5 public static voidmain(String[] args) throws IOException { 6 // TODOAuto-generated method stub 7 ServerSocket ss = newServerSocket(30000); 8 while(true){ 9 //此代码会阻塞,将一直等待别人连接 10 Socket s = ss.accept(); 11 socketList.add(s); 12 //每当客户端连接后启动一条ServerThread线程为该客户端服务 13 new Thread(newServerThread(s)).start(); 14 } 15 } 16 } 17 服务端通信线程 18 public classServerThread implements Runnable { 19 //定义当前线程所处理的Socket 20 Socket s = null; 21 //该线程所处理的Socket所对应的输入流 22 BufferedReader br = null; 23 public ServerThread(Socket s) throws IOException { 24 this.s = s; 25 //初始化该Socket对应的输入流 26 br = newBufferedReader(new InputStreamReader(s.getInputStream(), 27 "utf-8")); 28 } 29 @Override 30 public void run() { 31 // TODOAuto-generated method stub 32 try 33 { 34 String content = null; 35 //采用循环不断从Socket中读取客户端发送过来的数据 36 while((content = readFromClient())!=null){ 37 //遍历socketList中的每个Socket 38 //将读到的内容向每个Socket发送一次 39 for(Socket s : MyServer.socketList){ 40 OutputStream os = s.getOutputStream(); 41 os.write((content + " ").getBytes("utf-8"));//注意发送消息的时候一定要加换行符,因为在readLine的时候看的就是换行符 42 } 43 } 44 }catch(IOException e) { 45 e.printStackTrace(); 46 } 47 } 48 49 public String readFromClient() 50 { 51 try{ 52 return br.readLine(); 53 }catch(IOException e){ //如果捕捉到异常,表明该Socket对应的客户端已经被关闭 54 //删除该Socket 55 MyServer.socketList.remove(s); 56 } 57 return null; 58 } 59 }
public classMainActivity extends Activity { EditText input, show; Button send; OutputStream os; Handler handler; @Override protected voidonCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); input = (EditText) findViewById(R.id.input); send = (Button) findViewById(R.id.send); show = (EditText) findViewById(R.id.show); handler = new Handler() { public voidhandleMessage(android.os.Message msg) { if (msg.what == 0x123) { show.append(" " + msg.obj.toString()); } }; }; newAsyncTask(){ @Override protected String doInBackground(String... params) { // TODOAuto-generated method stub Socket s; try { s = new Socket("192.168.1.75", 30000); //客户端启动ClientThread线程,不断读取来自服务器的数据 new Thread(newClientThread(s, handler)).start(); os = s.getOutputStream(); } catch(Exception e) { e.printStackTrace(); } return null; } }.execute(""); send.setOnClickListener(newOnClickListener() { @Override public voidonClick(View v) { // TODOAuto-generated method stub try { //将用户在文本框中输入的内容写入网络 os.write((input.getText().toString() + " ") .getBytes("utf-8")); input.setText(""); } catch(IOException e) { // TODOAuto-generated catch block e.printStackTrace(); } } }); } } 客户端通信线程 public classClientThread implements Runnable { private Socket s; //该线程负责处理的Socket private Handler handler; //该线程所处理的Socket对应的输入流 BufferedReader br = null; public ClientThread(Socket s, Handler handler) throws IOException { this.s = s; this.handler = handler; br = newBufferedReader(new InputStreamReader(s.getInputStream())); } @Override public void run() { // TODOAuto-generated method stub try { String content = null; //不断读取Socket输入流中的内容 while ((content = br.readLine()) != null) { //每当读到来自服务器的数据后,发送消息通知程序界面显示数据 Message msg = newMessage(); msg.what = 0x123; msg.obj = content; handler.sendMessage(msg); } } catch(Exception e) { e.printStackTrace(); } } }
原文地址:http://i.cnblogs.com/EditPosts.aspx?opt=1
参考地址:
android中对服务端的长连接【socket】
http://blog.csdn.net/yaya_soft/article/details/11778593
http://www.cnblogs.com/asi24/archive/2013/06/05/3119444.html
http://coach.iteye.com/blog/2024444
http://gstarwd.iteye.com/blog/619171
Android学习笔记(七)之Android socket通信-解决中文乱码
http://www.2cto.com/kf/201209/155337.html