Android与JavaSocket的简单示例

开头

最近忙于比赛,遇到一个长连接的难题,第一想到就是Socket。比赛中是不会提供第三方框架,经常依赖第三方网络框架的我重新使用Socket发现很多问题,从而总结了这篇文章。方法用意都在注释里。

服务端

  1. 绑定本地IP端口。
  2. serverSocket.accept()方法中获取clientSocket
  3. 获取输出/输入字节流
public class Main {

    private static Socket clientSocket = null;

    public static void main(String[] args) {
        new Thread(new Runnable() {

            public void run() {
                ServerSocket serverSocket = null;
                try {
                    serverSocket = new ServerSocket(8888);//绑定本地IP的8888端口
                    while (true) {
                        clientSocket = serverSocket.accept();//阻塞获取客户端Socket
                        while (true) {//不断读取客户端Socket的消息
                            byte[] b = new byte[1024];
                            int n = clientSocket.getInputStream().read(b);
                            String s = new String(b, 0, n);
                            if (s.equals("close")) {//客户端通知关闭的标识,中止死循环,等待下个客户端Socket
                                break;
                            }
                            System.out.println(s);
                        }
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                } finally {
                    //资源释放
                    try {
                        if (serverSocket != null) {
                            serverSocket.close();
                        }
                        if (clientSocket != null) {
                            clientSocket.close();
                        }
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        }).start();

        Scanner scanner = new Scanner(System.in);
        while (true) {
            String s = scanner.next();//从控制台上输入
            OutputStream os;
            try {
                os = clientSocket.getOutputStream();
                os.write(s.getBytes());
                os.flush();//将输入的文字发给客户端
            } catch (IOException e) {
                e.printStackTrace();
            }

        }
    }
}

手机客户端

  1. 监听远程服务端IP端口。
  2. 获取输出/输入字节流

public class MainActivity extends Activity {

    private TextView tvLog;
    private Socket socket;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        tvLog = (TextView) findViewById(R.id.tv_log);
        findViewById(R.id.btn_send).setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View arg0) {
                if (socket != null) {
                    try {
                        OutputStream os = socket.getOutputStream();
                        os.write("Hello!".getBytes());
                        os.flush();//将输入的文字发给服务端
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        });

        new Thread(new Runnable() {

            @Override
            public void run() {
                try {
                    socket = new Socket("10.0.2.2", 8888);//监听服务端IP的8888端口
                    while (true) {//不断读取服务端的消息
                        byte[] b = new byte[1024];
                        int n = socket.getInputStream().read(b);
                        if (n > 0) {
                            final String s = new String(b, 0, n);
                            runOnUiThread(new Runnable() {

                                @Override
                                public void run() {
                                    tvLog.setText(s+"\n");
                                }
                            });
                        }
                    }
                } catch (UnknownHostException e) {
                    e.printStackTrace();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }).start();
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        //关闭时通知服务端关闭
        try {
            socket.getOutputStream().write("close".getBytes());
            if (socket != null) {
                socket.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

注意事项

  1. serverSocket.accept()方法有阻塞作用,直到有客户端进入连接。
  2. 服务端不断读取客户端数据时,断开最好通知服务端关闭clientSocket。
  3. 数据传输就getOutputStream和getInputStream方法,客户端只要不关闭就不要关闭流,不然传输不到数据。
  4. 用哪种方法输入输出流都可以,本人偏向字节流,什么数据都可以传输。
  5. 服务端要比客户端先启动。
  6. 上面的例子是为了简单的演示,只了解核心就好了。

不足之处望指教。

评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值