昨天写了两篇socket的,今天继续,一步一步解决我们需要解决的问题。第一篇简单的介绍了下Socket,让大家对socket有个大致的概念,初步的印象。第二遍里给了socket通信的简单demo,实现了socket客服端和服务端的简单通信,相当于隧道的两端已经打通了,现在要做的就是在这基础上不断的完善我们的程序,让程序去实现我们想要实现的想法,去解决我们需要解决的问题.今天我们在昨天的基础上,修改程序实现传输文件,不只是字符直接的传输与现实。
服务端
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Net;
using System.IO;
namespace Bose.XueLeCN.COM.FileReceiveControl
{
public class FileOut
{
public void Fileout()
{
int Port = 8001;
//string Ip = "192.168.1.20";
IPEndPoint ipep = new IPEndPoint(IPAddress.Any,Port);
EndPoint ep = (EndPoint)ipep;
Socket sc = new Socket(AddressFamily.InterNetwork,SocketType.Dgram,ProtocolType.Udp);
sc.Bind(ep);
Console.WriteLine("this is server");
Console.WriteLine("waiting for a connect");
IPEndPoint ipepClient = new IPEndPoint(IPAddress.Any,0);
EndPoint epClient = (EndPoint)ipepClient;
int rec;
byte[] data=new byte[1024];
//==========获取客户端发送过来的 文件 byte 的大小
rec = sc.ReceiveFrom(data,ref epClient);
//==========这里的getstring()方法一定要加 其实偏移量,和长度,不然 得到的字符串中会有很多\0出现
int Length = int.Parse(Encoding.ASCII.GetString(data, 0, data.Length));
Console.WriteLine("Data is "+Encoding.ASCII.GetString(data,0,rec));
//===========将得到的数据返回个客户端,进行通信,这里看似没太大的意义,但是是为了方便以后判断是否丢包和要求回发做准备
sc.SendTo(data,data.Length,SocketFlags.None,epClient);
data=new byte[Length];
//===========接收客户端发送过来的文件数据
rec = sc.ReceiveFrom(data,ref epClient);
//===========将文件写入到磁盘
File.WriteAllBytes(@"E:\1.jpg",data);
//===========死循环 方便调试 避免直接退出
while (true)
{
}
}
}
}
客户端
程序中需要注意的地方都加了注释,应该可以很清楚的看明白。在客户端和服务端的端口必须一样,否则会报错。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.IO;
namespace FileDistributeControl
{
public class FileOut
{
public void Fileout()
{
IPEndPoint ipep = new IPEndPoint(IPAddress.Parse("192.168.1.20"), 8001);
// EndPoint ep = (EndPoint)ipep;
Socket sc = new Socket(AddressFamily.InterNetwork,SocketType.Dgram,ProtocolType.Udp);
// sc.Bind(ep);//客服端 不需要绑定 endpoint
Console.WriteLine("this is client");
Console.WriteLine("client is connecting");
// 开始 传图片
string Path = @"F:\2.jpg";
// FileInfo fino = new FileInfo(Path);
//=====读取文件,将文件读取成数据流
FileStream fs = new FileStream(Path,FileMode.Open,FileAccess.Read);
byte[] FileBytes=new byte[fs.Length];
fs.Read(FileBytes,0,FileBytes.Length);
IPEndPoint ipClient = new IPEndPoint(IPAddress.Any, 0);
EndPoint epClient = (EndPoint)ipClient;
int rec;
byte[] b = new byte[1024];
b = Encoding.ASCII.GetBytes(fs.Length.ToString());
//=======发送文件的byte数组大小
sc.SendTo(b,b.Length,SocketFlags.None,ipep);
b=new byte[1024];
//=======接受服务端 发送过来的 信息... rec 是byte 的大小,服务端发送过来的 数据是 b这个字节数组
rec = sc.ReceiveFrom(b, ref epClient);
Console.Write("receive from server:" + Encoding.ASCII.GetString(b, 0, rec).Trim());
//=======发送文件
sc.SendTo(FileBytes,FileBytes.Length,SocketFlags.None,ipep);
//=======加一个死循环是方便调试,避免程序运行完毕 直接退出
while (true)
{
}
}
}
}