Android中,可以通过Socket、Http获取网络数据。我们首先搞清楚它们分别是什么,再看在Android中,它们如何实现。
1、什么是Socket
Socket 是传输层上的编程接口。它是实现计算机之间网络通信的基石。每一种可用于网络编程的语言都会实现这个接口。Java提供了ServerSocket类、Socket类给程序员来实现客户端与服务端的通信。
当我们使用Socket时,我们可以指定传输层上使用什么传输协议(TCP或UDP),一般常用的是TCP了。
大致上说,使用Socket通信的流程是这样的:
第一、服务端建立一个Socket,指定它监听某个端口。
第二、客户端也建立一个Socket,通过地址和端口向服务端Socket发出信息
第三、服务端Socket接收到信息,并立即创建一个新的Socket与客户端Socket通信,这个新的Socket的端口是任意的空闲端口,不需要程序员关心。
第四、服务端与服务端都打开输入输出流,就可以相互收发信息了。直到一方关闭了Socket,通信才结束了。
2、什么是Http
Http是一种协议,在ISO网络模型中,它属于应用层。可以将它理解为TCP协议的子协议,它将TCP进行了一定的包装,设置了每次通信后即断开。
它是应答式的。客户端发个请求,服务器就响应一下。客户端不发消息时,服务器端不会知道客户端的存在。
3、使用Socket与服务器通信
以下实现的是,客户端输入内容提交到服务器后,服务器返回信息,只能操作一次。如果希望多次操作,那就要加While循环了。具体怎么加,有需要的话再讲吧。
服务端代码:
public class ServerTest {
public static void main(String[] args){
ServerSocket server = null;
Socket request = null;
BufferedReader reader = null;
PrintWriter writer = null;
/**
* 接收一次客户端消息并回复
*/
try {
// 创建Socket,指定端口号
server = new ServerSocket(5555);
// 阻塞在此处,监听端口,直到客户端发来请求才会执行后面的代码
request = server.accept();
// 创建输入流
reader = new BufferedReader(new InputStreamReader(request.getInputStream()));
// 创建输出流,第二个参数为true,表示会在调用println、printf、format 方法时自动flush,即清空缓冲区
writer = new PrintWriter(request.getOutputStream(), true);
String input = reader.readLine();
// 向客户端发送消息
writer.println(input+" has received");
System.out.println(input+"has received");
writer.close();
reader.close();
request.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
客户端关键代码:
public void bySocket(){
try {
// 发送连接Socket请求,第一个参数是服务端地址,第二个是服务端端口号
// 注意的是,地址这里不能写localhost之类的,因为手机会理解为自身。所以一定要写电脑的IP地址
socket = new Socket("192.168.1.110", 5555);
// 打开输入流
in = new BufferedReader(new InputStreamReader(socket.getInputStream()));
// 打开输出流
out = new PrintWriter(socket.getOutputStream(),true);
out.println(etOut.getText());
tvIn.setText(in.readLine());
out.close();
in.close();
socket.close();
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
效果图:
输入内容后点”send"可收到服务端发回来的信息:hello has received。
4、使用Http与服务器通信
可以使用Java本来就有的那一套,也可以使用专属于Android的那一套。
Java原本就有的方法:
URL url = null;
try {
url = new URL("http://www.baidu.com");
} catch (MalformedURLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
try {
// 建立连接
URLConnection conn = url.openConnection();
// 设置参数,如要Post的内容
// conn.addRequestProperty(key, value);
DataInputStream dis = new DataInputStream(conn.getInputStream());
PrintWriter writer = new PrintWriter(conn.getOutputStream());
String str = "";
while(str != null){
str = dis.readUTF();
System.out.println(str);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
Android专属的方法:
HttpClient client = new DefaultHttpClient();
// HTTP GET
HttpGet get = new HttpGet();
URI uri = null;
try {
uri = new URI("http://www.baidu.com");
} catch (URISyntaxException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
get.setURI(uri);
try {
HttpResponse result = client.execute(get);
InputStream input = result.getEntity().getContent();
DataInputStream dis = new DataInputStream(input);
String ss = dis.readLine();
tvIn.setText(ss);
} catch (ClientProtocolException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
// HTTP POST
HttpPost httpRequest = new HttpPost(uri);
List<NameValuePair> postParameters = null;
try {
httpRequest.setEntity(new UrlEncodedFormEntity(postParameters,HTTP.UTF_8));
} catch (UnsupportedEncodingException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
try {
HttpResponse httpresponse = new DefaultHttpClient().execute(httpRequest);
} catch (ClientProtocolException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}