socket套接字编程
socket编程换句话说是套接字编程,像一个套子将两个计算机进行连接。
服务端的代码编写流程如下:WSAsocket()->bind()->listen()->accept()->send()/recv()->closesocket()->WSACleanup()
客户端的代码编写流程如下:WSAsocket()->socket()->connect()->recv()/send()->closesocket()->WSACleanuo()
基于C语言Winsock-TCP的通信
以下两个程序,需要在vc++6.0中,选择Win32 Console Application中的简单hello world或者空项目,然后先运行server,后运行client。便可以实现基本的socket通信。记住修改相应的IP和端口。
server:
client:
输入任意信息后:
//tcp_client
#include "stdafx.h"
#include <stdio.h>
#include <winsock2.h>
#pragma comment (lib, "ws2_32")
int main() {
WSADATA wsaData;
WSAStartup(MAKEWORD(2, 2), &wsaData);
SOCKET clientSocket;
struct sockaddr_in serverAddr;
// Create socket
clientSocket = socket(AF_INET, SOCK_STREAM, 0);
if (clientSocket == INVALID_SOCKET) {
perror("socket creation failed");
WSACleanup();
return 1;
}
// Set server address
serverAddr.sin_family = AF_INET;
serverAddr.sin_port = htons(1234); // Use the same port as the server
serverAddr.sin_addr.s_addr = inet_addr("192.168.137.1"); // Replace with the server's IP address
// Connect to the server
if (connect(clientSocket, (struct sockaddr*)&serverAddr, sizeof(serverAddr)) == SOCKET_ERROR) {
perror("connection failed");
closesocket(clientSocket);
WSACleanup();
return 1;
}
printf("Connected to the server\n");
char buffer[1024];
while (1) {
printf("Enter a message (or 'quit' to exit): ");
gets(buffer);
// Send the message to the server
send(clientSocket, buffer, strlen(buffer), 0);
if (strcmp(buffer, "quit") == 0) {
break; // Exit the loop if the user enters 'quit'
}
}
// Close socket and cleanup
closesocket(clientSocket);
WSACleanup();
return 0;
}
//tcp_server
#include "stdafx.h"
#include <stdio.h>
#include <winsock2.h>
#pragma comment (lib, "ws2_32")
int main() {
WSADATA wsaData;
WSAStartup(MAKEWORD(2, 2), &wsaData);
// 创建套接字
SOCKET sLisent = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
// 对sockaddr_in结构体填充地址、端口等信息
struct sockaddr_in ServerAddr;
ServerAddr.sin_family = AF_INET;
ServerAddr.sin_addr.s_addr = INADDR_ANY; // Listen on all available network interfaces
ServerAddr.sin_port = htons(1234);
// 绑定套接字与地址信息
bind(sLisent, (SOCKADDR *)&ServerAddr, sizeof(ServerAddr));
// 端口监听
listen(sLisent, SOMAXCONN);
printf("Server is listening...\n");
// 获取连接请求
struct sockaddr_in ClientAddr;
int nSize = sizeof(ClientAddr);
SOCKET sClient = accept(sLisent, (SOCKADDR *)&ClientAddr, &nSize);
printf("Client connected\n");
// 接收消息并显示在屏幕上
char buffer[1024];
while (1) {
int bytesReceived = recv(sClient, buffer, sizeof(buffer), 0);
if (bytesReceived <= 0) {
break;
}
buffer[bytesReceived] = '\0';
printf("Received from client: %s\n", buffer);
// 发送消息到客户端(可选,如果要回应客户端)
// send(sClient, buffer, bytesReceived, 0);
}
// 关闭套接字
closesocket(sClient);
closesocket(sLisent);
WSACleanup();
return 0;
}
基于python语言Winsock-TCP的通信
#server
import socket
sk = socket.socket()
#maybe? waiting test
ip_port = ('192.168.137.1', 55555)
#bind listen
sk.bind(ip_port)
#the max number of connection
sk.listen(5)
#waring message
print('Running')
#get data
conn, address = sk.accept()
while True:
print(conn.recv(1024).decode())
#close connection
conn.close()
#client
import socket
sk = socket.socket()
#bind ip and port
ip_port = ('192.168.137.1', 55555)
#connect server
sk.connect(ip_port)
#get server data
while True:
send = input('What :')
sk.send(send.encode())
发送任意信息:
socket编程下的可视化python程序(基于UDP模式)
需要先进行本地和目标IP设置,然后进行发送,有时候需要关闭计算机的防火墙。
参考#https://blog.csdn.net/qq_41500251/article/details/90114802
import tkinter as tk
import socket
import threading
sk_recv = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sk_send = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
ip_port_recv = ('127.0.0.1',55555)
ip_port_send = ('127.0.0.1',55555)
def loop():
while True:
var = sk_recv.recv(1024).decode()
t.insert('insert', var + '\n')
root = tk.Tk()
root.title('通信系统')
root.geometry('800x600')
root.config(background='#F8FEEE')
labe = tk.Label(root, text='消息框:')
labe.pack()
t = tk.Text(root, height=10)
t.pack()
#config my ip
def conf_ip():
#create sub windon
top = tk.Toplevel()
top.title('设置本地 IP')
top.geometry('300x100')
#a entry
e = tk.Entry(top)
e.pack()
#the function of button
def confirm():
global ip_port_recv, var_ip, sk_recv
var = e.get()
#change ip
ip_port_recv = (var, 55555)
#change label var
var_ip.set('本地IP:' + var)
#bing port
sk_recv.bind(ip_port_recv)
#loop to recive data
t1 = threading.Thread(target=loop)
t1.setDaemon(True)
t1.start()
#close subwindon
top.destroy()
#a button
b = tk.Button(top, text='确定', command=confirm)
b.pack()
#config his/her id
def conf_send():
top = tk.Toplevel()
top.title('设置目标IP')
top.geometry('300x100')
e = tk.Entry(top)
e.pack()
def confirm():
global ip_port_send, var_send
var = e.get()
ip_port_send = (var, 55555)
var_send.set('目标IP:' + var)
top.destroy()
b = tk.Button(top, text='确定', command=confirm)
b.pack()
#Edit my id
def edit_id():
top = tk.Toplevel()
top.title('设置 ID')
top.geometry('300x100')
e = tk.Entry(top)
e.pack()
def confirm():
global var_name, name
var_name.set('我的ID:' + e.get())
name.set(e.get())
top.destroy()
b = tk.Button(top, text='确定', command=confirm)
b.pack()
#create menu
menubar = tk.Menu(root)
ip_menu = tk.Menu(menubar, tearoff=0)
#config menu and add submenu
menubar.add_cascade(label='设置', menu=ip_menu)
ip_menu.add_command(label='设置本地 IP', command=conf_ip)
ip_menu.add_command(label='设置目标 IP', command=conf_send)
ip_menu.add_command(label='设置 ID', command=edit_id)
#show menu
root.config(menu = menubar)
#a friendly label
label = tk.Label(root, text='输入框:')
label.pack()
entry = tk.Entry(root)
entry.pack()
def insert_point():
global name
var = entry.get()
message = name.get() + ' : ' + var
t.insert('insert', message + '\n')
sk_send.sendto(message.encode(), ip_port_send)
entry.delete(0, tk.END)
button = tk.Button(root, text='发送', command=insert_point)
button.pack()
#some var
#my ip
var_ip = tk.StringVar()
#his/her ip
var_send = tk.StringVar()
#my id
var_name = tk.StringVar()
name = tk.StringVar()
#some friendly labels
label1 = tk.Label(root, textvariable=var_ip)
label2 = tk.Label(root, textvariable=var_send)
label3 = tk.Label(root, textvariable=var_name)
label1.pack()
label2.pack()
label3.pack()
root.mainloop()
对于代码的个人解释: