---------------------- ASP.Net+Android+IO开发S、.Net培训、期待与您交流! ----------------------
网络编程
网络模型
网络通信要素
1.ip地址 InetAddress
网络中设备的标识
不易记忆,可用主机名
本地回环地址:127.0.0.1 主机名:localhost
2.端口号
用于标识进程的逻辑地址,不同进程的标识
有效端口:0~65535,其中0~1024为系统使用或保留端口
3.传输协议
通讯的规则
常用协议:TCP、UDP
TCP、UDP区别
UDP
将数据及源和目的封装成数据包,不需要建立连接。
每个数据大小限制在64k内。
因为无连接,是不可靠协议。
不需要建立连接,速度快。
(聊天、游戏、视频)
TCP
建立连接,形成传输数据的通道。
在连接中进行大数据量传输
通过三次握手完成连接,是可靠协议
必须建立连接,效率会稍低。
基于上述特性,不难得到结论,TCP协议适用于对效率要求相对低,但对准确性要求相对高的场景下,或者是有一种连接概念的场景下。
而UDP协议适用于对效率要求相对高,对准确性要求相对低的场景。
TCP一般用于文件传输(对数据准确性要求高,速度可以相对慢),发送或接收邮件,远程登陆等等;
UDP一般用于即时通信,在线视频,网络电话,游戏等等。
网络通信:
1.找到对方IP
2.数据要发送到对方指定的应用程序上。为了标识这些应用程序,所以给这些网络应用程序
都用数字进行标识。称之为端口。逻辑端口。
3.定义通信规则。这个通信规则称为协议。国际组织定义了通用协议TCP/IP。
import java.net.*;
class IpDemo{
public static void main(String[] args)throws Exception{
InetAddress ia = InetAddress.getLocalHost();//得到InetAddress对象
System.out.println(ia.getHostAddress());//得到地址
System.out.println(ia.getHostName());//得到主机名
InetAddress i = InetAddress.getByName("www.baidu.com");
System.out.println(i);
}
}
UDP
Socket就是为网络服务提供的一种机制。
通信的两端都有Socket。
网络通信其实就是Socket间的通信。
数据在两个Socket间是通过IO传输。
通过UDP方式,将一段文字发送出去。
思路:
1.建立UDP Socket服务。
2.提供数据,并将数据封装在数据包中
3.通过Socket服务的发送功能,将数据发送出去
4.关闭资源。
通过UDP方式,接收传输的数据。
思路:
1.建立UDP Socket服务。
2.定义一个数据包,因为要存储接收到的字节数据。因为数据包中有更多功能可以提取字节数据中的不同数据信息。
3.通过Socket的receive方法将收到的数据存入已定义的数据包中。
4.通过数据包对象的特有功能。将这些不同的数据取出。打印在控制台上。
5.关闭资源。
/*
需求:通过UDP方式,将一段文字发送出去。
思路:
1.建立UDP Socket服务。
2.提供数据,并将数据封装在数据包中
3.通过Socket服务的发送功能,将数据发送出去
4.关闭资源。
*/
import java.net.*;
class SendDemo{
public static void main(String[] args) throws Exception{
//建立UDP Socket服务。
DatagramSocket s = new DatagramSocket(9999);
//提供数据,并将数据封装在数据包中
byte[] buf = "welecome to java".getBytes();
int length = buf.length;
DatagramPacket p = new DatagramPacket(buf,length,InetAddress.getByName("114.214.106.23"),2222);
//通过Socket服务的发送功能,将数据发送出去
s.send(p);
//关闭资源
s.close();
}
}
/*
需求:通过UDP方式,接收传输的数据。
思路:
1.建立UDP Socket服务。
2.定义一个数据包,因为要存储接收到的字节数据。
因为数据包中有更多功能可以提取字节数据中的不同数据信息。
3.通过Socket的receive方法将收到的数据存入已定义的数据包中。
4.通过数据包对象的特有功能。将这些不同的数据取出。打印在控制台上。
5.关闭资源。
*/
class ReceiveDemo{
public static void main(String[] args) throws Exception{
//建立UDP Socket服务。建立端点
DatagramSocket s = new DatagramSocket(2222);
//定义数据包,用于存储数据。
byte[] buf = new byte[20];
int length = 20;
DatagramPacket p = new DatagramPacket(buf,length);
//通过receive方法将收到的数据存入数据包中。
s.receive(p);
//通过数据包的方式获取其中数据
String ip = p.getAddress().getHostAddress();//发送端ip
String name = p.getAddress().getHostName();
String data = new String(p.getData());//发送数据
int port = p.getPort();//发送端端口
System.out.println("ip:"+ip);
System.out.println("port:"+port);
System.out.println("name:"+name);
System.out.println("data:"+data);
//关闭资源
s.close();
}
}
根据上面的程序,加以扩展,可以实现键盘输入:
import java.net.*;
import java.io.*;
class SendDemo{
public static void main(String[] args) throws Exception{
//建立UDP Socket服务。
DatagramSocket s = new DatagramSocket(9999);
//提供数据,并将数据封装在数据包中
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String line = null;
while((line=br.readLine())!=null){
if("886".equals(line))
break;
byte[] buf = line.getBytes();
DatagramPacket p = new DatagramPacket(buf,buf.length,InetAddress.getByName("114.214.106.23"),2222);
s.send(p);
}
s.close();
}
}
class ReceiveDemo{
public static void main(String[] args) throws Exception{
//建立UDP Socket服务。建立端点
DatagramSocket s = new DatagramSocket(2222);
while(true){
//定义数据包,用于存储数据。
byte[] buf = new byte[1024];
int length = buf.length;
DatagramPacket p = new DatagramPacket(buf,buf.length);
//通过receive方法将收到的数据存入数据包中。
s.receive(p);
//通过数据包的方式获取其中数据
String ip = p.getAddress().getHostAddress();//发送端ip
String name = p.getAddress().getHostName();
String data = new String(p.getData(),0,p.getLength());//发送数据
int port = p.getPort();//发送端端口
System.out.println("ip:"+ip+": "+data);
}
}
}
编写一个聊天程序。
有收数据的部分,和发数据的部分。
这两部分需要同时执行。
那就需要用到多线程技术。一个线程控制收,一个线程控制发。
因为收和发的动作是不一致的,所以定义两个run方法。
而且这两个方法呀封装到不同的类中。
import java.io.*;
import java.net.*;
//定义发送线程
class Send implements Runnable{
private DatagramSocket ds;
//构造函数
public Send(DatagramSocket ds){
this.ds = ds;
}
public void run(){
try
{
//建立键盘输入流
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String line = null;
//读取写入的数据,并发送到指定地址和端口
while((line = br.readLine())!=null){
byte[] buf = line.getBytes();
DatagramPacket dp = new DatagramPacket(buf,buf.length,InetAddress.getByName("114.214.106.23"),5555);
ds.send(dp);
}
//br.close();
//关闭资源
ds.close();
}
catch (Exception e)
{
throw new RuntimeException("输入操作无法完成");
}
}
}
//定义收线程
class Rece implements Runnable{
private DatagramSocket ds;
public Rece(DatagramSocket ds){
this.ds = ds;
}
public void run(){
try
{
//无限循环等待接收数据
while(true){
byte[] buf = new byte[1024];
//定义数据包
DatagramPacket dp = new DatagramPacket(buf,buf.length);
//将接收的信息写入数据包
ds.receive(dp);
String ip = dp.getAddress().getHostAddress();
String data = new String (dp.getData(),0,dp.getLength());
System.out.println(ip+" : "+data);
}
}
catch (Exception e)
{
throw new RuntimeException("读取操作无法完成");
}
}
}
class ChatDemo{
public static void main(String[] args)throws Exception{
//定义UDP的Socket
DatagramSocket send = new DatagramSocket();
DatagramSocket rece = new DatagramSocket(5555);
//定义线程,并且开始线程
new Thread(new Send(send)).start();
new Thread(new Rece(rece)).start();
}
}
---------------------- ASP.Net+Android+IOS开发、.Net培训、期待与您交流! ----------------------
详情请查看:http://edu.csdn.net