IP地址
在互联网中,一个IP地址用于唯一标识一个网络接口(Network Interface)。一台联入互联网的计 算机肯定有一个IP地址,但也可能有多个IP地址。
IP地址分为IPv4和IPv6两种。
IPv4采用32位地址,类似 101.202.99.12 ,而IPv6采用128位地址, 类似 2001:0DA8:100A:0000:0000:1020:F2F3:1428 。
IPv4地址总共有232个(大约42亿),而IPv6 地址则总共有2128个(大约340万亿亿亿亿),IPv4的地址目前已耗尽,而IPv6的地址是根本用不完的。
IP地址分类:
A类:1.0.0.1 ~ 127.255.255.254 1个网络号段 + 3个主机号段
B类:128.0.0.1 ~ 191.255.255.254 2个网络号段 + 2个主机号段
C类:192.0.0.1 ~ 223.255.255.254 3个网络号段 + 1个主机号段
D类:224.0.0.1 ~ 239.255.255.254 E类:240.0.0.1 ~ 247.255.255.254
IP地址又分为公网IP地址和内网IP地址。
公网IP地址可以直接被访问,内网IP地址只能在内网访问。
内网IP地址类似于:
- 192.168.x.x
- 172.16.x.x
- 10.x.x.x
有一个特殊的IP地址,称之为本机地址,它总是 127.0.0.1 。
端口号
物理端口号指的是网卡口,逻辑端口号指的就是逻辑端口。
- 每个网络程序都会至少有一个逻辑端口
- 用于标识进程的逻辑地址,不同进程的表示
- 有效端口:0~65535,其中 0~1024系统使用或保留端口
网络模型
- 应用层,提供应用程序之间的通信;
- 表示层:处理数据格式,加解密等等;
- 会话层:负责建立和维护会话;
- 传输层:负责提供端到端的可靠传输;
- 网络层:负责根据目标地址选择路由来传输数据;
- 链路层和物理层负责把数据进行分片并且真正通过物理网络传输,例如,无线网、光纤等。
网络号越少,主机号越多,可绑定的电脑就越多
C类,是目前使用最多的,前三段是网络号,最后一段是主机号
nat技术,共享ip地址
子网掩码:255.255.255.0
socket简介:套接字编程
UDP编程
UDP网络协议下的socket对象
代码示例:
public class TestSocket {
public static final String DES_IP = "127.0.0.1";
public static final int DES_PORT = 8080;
public static void main(String[] args) {
Socket socket = new Socket();
try {
socket.connect(new InetSocketAddress(DES_IP, DES_PORT));
System.out.println("成功连接到服务器");
InputStream is = socket.getInputStream();
String msg = null;
BufferedReader br = new BufferedReader(new InputStreamReader(is));
while ((msg = br.readLine()) != null ) {
System.out.println("接受到服务器端传递过来的数据,数据是:"+ msg);
}
PrintWriter out = new PrintWriter(socket.getOutputStream(), true);
out.println("我是一个客户端,我上来了,服务器,你好着吗?");
out.println("第二条数据");
} catch (IOException e) {
e.printStackTrace();
}
}
}
UDP(User Datagram Protocol):用户数据报协议
特点:
1.无连接的传输层协议
2.不可靠的,只管数据发送,不管是否对方接收
3.不安全的,数据传输中没有任何保证
4.追求速度的网络协议
代码示例:
public class TestUDP {
public static void main(String[] args) {
DatagramSocket datagramSocket = null;
try {
// 注意,创建一个udp socket对象,默认占据了8080
datagramSocket = new DatagramSocket(8080);
String msg = "你好啊,socket对象";
byte[] bytes = msg.getBytes();
// 数据报对象
DatagramPacket packet = new DatagramPacket(bytes, 0, bytes.length, new InetSocketAddress("127.0.0.1", 8888));
// 发送数据
datagramSocket.send(packet);
System.out.println("数据已经成功发送");
} catch (IOException e) {
e.printStackTrace();
} finally {
datagramSocket.close();
}
}
}
TCP编程
TCP:传输控制协议
特点:安全、可靠、有连接的、点对点、长连接的
代码示例:
public class Server {
public static void main(String[] args) throws IOException {
ServerSocket ss = new ServerSocket(6666); // 监听指定端口
System.out.println("server is running...");
for (;;) {
Socket sock = ss.accept();
System.out.println("connected from " + sock.getRemoteSocketAddress());
Thread t = new Handler(sock);
t.start();
}
}
}
class Handler extends Thread {
Socket sock;
public Handler(Socket sock) {
this.sock = sock;
}
@Override
public void run() {
try (InputStream input = this.sock.getInputStream()) {
try (OutputStream output = this.sock.getOutputStream()) {
handle(input, output);
}
} catch (Exception e) {
try {
this.sock.close();
} catch (IOException ioe) {
}
System.out.println("client disconnected.");
}
}
private void handle(InputStream input, OutputStream output) throws IOException {
var writer = new BufferedWriter(new OutputStreamWriter(output,
StandardCharsets.UTF_8));
var reader = new BufferedReader(new InputStreamReader(input,
StandardCharsets.UTF_8));
writer.write("hello\n");
writer.flush();
for (;;) {
String s = reader.readLine();
if (s.equals("bye")) {
writer.write("bye\n");
writer.flush();
break;
}
writer.write("ok: " + s + "\n");
writer.flush();
}
}
HTTP编程
因为浏览器也是一种HTTP客户端,所以,客户端的HTTP编程,它的行为本质上和浏览器是一样 的,即发送一个HTTP请求,接收服务器响应后,获得响应内容。只不过浏览器进一步把响应内容解析后 渲染并展示给了用户,而我们使用Java进行HTTP客户端编程仅限于获得响应内容 。 代码示例:
URL url = new URL("http://www.example.com/path/to/target?a=1&b=2");
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setUseCaches(false);
conn.setConnectTimeout(5000); // 请求超时5秒
// 设置HTTP头:
conn.setRequestProperty("Accept", "*/*");
conn.setRequestProperty("User-Agent", "Mozilla/5.0 (compatible; MSIE 11; Windows NT
5.1)");
// 连接并发送HTTP请求:
conn.connect();
// 判断HTTP响应是否200:
if (conn.getResponseCode() != 200) {
throw new RuntimeException("bad response");
}
// 获取所有响应Header:
Map<String, List<String>> map = conn.getHeaderFields();
for (String key : map.keySet()) {
System.out.println(key + ": " + map.get(key));
}
// 获取响应内容:
InputStream input = conn.getInputStream();
...
三次握手:加强安全
ddos攻击,浪费资源