什么是p2p

author author     2023-04-27     400

关键词:

什么是P2P?

P2P是peer-to-peer的缩写,peer在英语里有"(地位、能力等)同等者"、"同事"和"伙伴"等意义。这样一来,P2P也就可以理解为"伙伴对伙伴"的意思,或称为对等联网。目前人们认为其在加强网络上人的交流、文件交换、分布计算等方面大有前途.
简单的说,P2P直接将人们联系起来,让人们通过互联网直接交互。P2P使得网络上的沟通变得容易、更直接共享和交互,真正地消除中间商。P2P就是人可以直接连接到其他用户的计算机、交换文件,而不是像过去那样连接到服务器去浏览与下载。P2P另一个重要特点是改变互联网现在的以大网站为中心的状态、重返"非中心化",并把权力交还给用户。 P2P看起来似乎很新,但是正如B2C、B2B是将现实世界中很平常的东西移植到互联网上一样,P2P并不是什么新东西。在现实生活中我们每天都按照P2P模式面对面地或者通过电话交流和沟通。
即使从网络看,P2P也不是新概念,P2P是互联网整体架构的基础。互联网最基本的协议TCP/IP并没有客户机和服务器的概念,所有的设备都是通讯的平等的一端。在十年之前,所有的互联网上的系统都同时具有服务器和客户机的功能。当然,后来发展的那些架构在TCP/IP之上的软件的确采用了客户机/服务器的结构:浏览器和Web服务器,邮件客户端和邮件服务器。但是,对于服务器来说,它们之间仍然是对等联网的。以email为例,互联网上并没有一个巨大的、唯一的邮件服务器来处理所有的email,而是对等联网的邮件服务器相互协作把email传送到相应的服务器上去。另外用户之间email则一直对等的联络渠道。
事实上,网络上现有的许多服务可以归入P2P的行列。即时讯息系统譬如ICQ、AOL Instant Messenger、Yahoo Pager、微软的MSN Messenger以及国内的OICQ是最流行的P2P应用。它们允许用户互相沟通和交换信息、交换文件。用户之间的信息交流不是直接的,需要有位于中心的服务器来协调。但这些系统并没有诸如搜索这种对于大量信息共享非常重要的功能,这个特征的缺乏可能正为什么即时讯息出现很久但是并没有能够产生如Napster这样的影响的原因之一。

参考资料:http://zhidao.baidu.com/question/44070.html?fr=qrl3

参考技术A 在如今的网络应用中,文件的传送是重要的功能之一,也是共享的基础。一些重要的协议像HTTP,FTP等都支持文件的传送。尤其是FTP,它的全称就是“文件传送协议”,当 初的工程师设计这一协议就是为了解决网络间的文件传送问题,而且以其稳定,高速,简单而一直保持着很大的生命力。作为一个程序员,使用这些现有的协议传送文件相当简单,不过,它们只适用于服务器模式中。这样,当我们想在点与点之间传送文件就不适用了或相当麻烦,有一种大刀小用的意味。笔者一直想寻求一种简单有效,且具备多线程断点续传的方法来实现点与点之间的文件传送问题,经过大量的翻阅资料与测试,终于实现了,现把它共享出来,与大家分享。
我写了一个以此为基础的实用程序(网络传圣,包含源代码),可用了基于TCP/IP的电脑上,供大家学习。
upload/2004_06/04062118541204.gif

(本文源代码运行效果图)

实现方法(VC++,基于TCP/IP协议)如下:
仍采用服务器与客户模式,需分别对其设计与编程。
服务器端较简单,主要就是加入待传文件,监听客户,和传送文件。而那些断点续传的功能,以及文件的管理都放在客户端上。

一、服务器端

首先介绍服务器端:
最开始我们要定义一个简单的协议,也就是定义一个服务器端与客户端听得懂的语言。而为了把问题简化,我就让服务器只要听懂两句话,一就是客户说“我要读文件信息”,二就是“我准备好了,可以传文件了”。
由于要实现多线程,必须把功能独立出来,且包装成线程,首先建一个监听线程,主要负责接入客户,并启动另一个客户线程。我用VC++实现如下:

DWORD WINAPI listenthread(LPVOID lpparam)


//由主函数传来的套接字
SOCKET pthis=(SOCKET)lpparam;
//开始监听
int rc=listen(pthis,30);
//如果错就显示信息
if(rc<0)
CString aaa;
aaa="listen错误\n";
AfxGetMainWnd()->SendMessageToDescendants(WM_AGE1,(LPARAM)aaa.GetBuffer(0),1);
aaa.ReleaseBuffer();
return 0;

//进入循环,并接收到来的套接字
while(1)
//新建一个套接字,用于客户端
SOCKET s1;
s1=accept(pthis,NULL,NULL);

//给主函数发有人联入消息
CString aa;
aa="一人联入!\n";
AfxGetMainWnd()->SendMessageToDescendants(WM_AGE1,(LPARAM)aa.GetBuffer(0),1);
aa.ReleaseBuffer();
DWORD dwthread;
//建立用户线程
::CreateThread(NULL,0,clientthread,(LPVOID)s1,0,&dwthread);

return 0;

接着我们来看用户线程:
先看文件消息类定义:

struct fileinfo

int fileno;//文件号
int type;//客户端想说什么(前面那两句话,用1,2表示)
long len;//文件长度
int seek;//文件开始位置,用于多线程

char name[100];//文件名
;
用户线程函数:

DWORD WINAPI clientthread(LPVOID lpparam)

//文件消息
fileinfo* fiinfo;
//接收缓存
char* m_buf;
m_buf=new char[100];
//监听函数传来的用户套接字
SOCKET pthis=(SOCKET)lpparam;
//读传来的信息
int aa=readn(pthis,m_buf,100);
//如果有错就返回
if(aa<0)
closesocket (pthis);
return -1;

//把传来的信息转为定义的文件信息
fiinfo=(fileinfo*)m_buf;
CString aaa;
//检验客户想说什么
switch(fiinfo->type)

//我要读文件信息
case 0:
//读文件
aa=sendn(pthis,(char*)zmfile,1080);
//有错
if(aa<0)
closesocket (pthis);
return -1;

//发消息给主函数
aaa="收到LIST命令\n";
AfxGetMainWnd()->SendMessageToDescendants(WM_AGE1,(LPARAM)aaa.GetBuffer(0),1);
break;
//我准备好了,可以传文件了

case 2:
//发文件消息给主函数
aaa.Format("%s 文件被请求!%s\n",zmfile[fiinfo->fileno].name,nameph[fiinfo->fileno]);
AfxGetMainWnd()->SendMessageToDescendants(WM_AGE1,(LPARAM)aaa.GetBuffer(0),1);
//读文件,并传送
readfile(pthis,fiinfo->seek,fiinfo->len,fiinfo->fileno);
//听不懂你说什么

default:
aaa="接收协议错误!\n";
AfxGetMainWnd()->SendMessageToDescendants(WM_AGE1,(LPARAM)aaa.GetBuffer(0),1);
break;


return 0;
读文件函数

void readfile(SOCKET so,int seek,int len,int fino)

//文件名
CString myname;
myname.Format("%s",nameph[fino]);
CFile myFile;
//打开文件
myFile.Open(myname, CFile::modeRead | CFile::typeBinary|CFile::shareDenyNone);
//传到指定位置
myFile.Seek(seek,CFile::begin);
char m_buf[SIZE];
int len2;
int len1;
len1=len;
//开始接收,直到发完整个文件
while(len1>0)
len2=len>SIZE?SIZE:len;
myFile.Read(m_buf, len2);
int aa=sendn(so,m_buf,len2);
if(aa<0)
closesocket (so);
break;

len1=len1-aa;
len=len-aa;

myFile.Close();

服务器端最要的功能各技术就是这些,下面介绍客户端。

二、客户端

客户端最重要,也最复杂,它负责线程的管理,进度的记录等工作。

大概流程如下:
先连接服务器,接着发送命令1(给我文件信息),其中包括文件长度,名字等,然后根据长度决定分几个线程下载,并初使化下载进程,接着发送命令2(可以给我传文件了),并记录文件进程。最后,收尾。
这其中有一个十分重要的类,就是cdownload类,定义如下:

class cdownload

public:
void createthread();//开线程
DWORD finish1();//完成线程
int sendlist();//发命令1
downinfo doinfo;//文件信息(与服务器定义一样)
int startask(int n);开始传文件n
long m_index;
BOOL good[BLACK];
int filerange[100];
CString fname;
CString fnametwo;
UINT threadfunc(long index);//下载进程

int sendrequest(int n);//发文件信息
cdownload(int thno1);
virtual ~cdownload();
;下面先介绍sendrequest(int n),在开始前,向服务器发获得文件消息命令,以便让客户端知道有哪些文件可传

int cdownload::sendrequest(int n)

//建套接字
sockaddr_in local;
SOCKET m_socket;

int rc=0;
//初使化服务器地址
local.sin_family=AF_INET;
local.sin_port=htons(1028);
local.sin_addr.S_un.S_addr=inet_addr(ip);
m_socket=socket(AF_INET,SOCK_STREAM,0);

int ret;
//联接服务器
ret=connect(m_socket,(LPSOCKADDR)&local,sizeof(local));
//有错的话
if(ret<0)
AfxMessageBox("联接错误");
closesocket(m_socket);
return -1;

//初使化命令
fileinfo fileinfo1;
fileinfo1.len=n;
fileinfo1.seek=50;
fileinfo1.type=1;
//发送命令
int aa=sendn(m_socket,(char*)&fileinfo1,100);
if(aa<0)
closesocket(m_socket);
return -1;

//接收服务器传来的信息
aa=readn(m_socket,(char*)&fileinfo1,100);
if(aa<0)
closesocket(m_socket);
return -1;

//关闭
shutdown(m_socket,2);
closesocket(m_socket);

return 1;
有了文件消息后我们就可以下载文件了。在主函数中,用法如下:

//下载第clno个文件,并为它建一个新cdownload类
down[clno]=new cdownload(clno);
//开始下载,并初使化
type=down[clno]->startask(clno);
//建立各线程
createthread(clno);下面介绍开始方法:

//开始方法
int cdownload::startask(int n)

//读入文件长度
doinfo.filelen=zmfile[n].length;
//读入名字
fname=zmfile[n].name;
CString tmep;
//初使化文件名
tmep.Format("\\temp\\%s",fname);

//给主函数发消息
CString aaa;
aaa="正在读取 "+fname+" 信息,马上开始下载。。。\n";
AfxGetMainWnd()->SendMessageToDescendants(WM_AGE1,(LPARAM)aaa.GetBuffer(0),1);
aaa.ReleaseBuffer();
//如果文件长度小于0就返回
if(doinfo.filelen<=0) return -1;
//建一个以.down结尾的文件记录文件信息
CString m_temp;
m_temp=fname+".down";

doinfo.name=m_temp;
FILE* fp=NULL;
CFile myfile;
//如果是第一次下载文件,初使化各记录文件

if((fp=fopen(m_temp,"r"))==NULL)
filerange[0]=0;
//文件分块
for(int i=0;i<BLACK;i++)

if(i>0)
filerange[i*2]=i*(doinfo.filelen/BLACK+1);
filerange[i*2+1]=doinfo.filelen/BLACK+1;

filerange[BLACK*2-1]=doinfo.filelen-filerange[BLACK*2-2];

myfile.Open(m_temp,CFile::modeCreate|CFile::modeWrite | CFile::typeBinary);

//写入文件长度
myfile.Write(&doinfo.filelen,sizeof(int));
myfile.Close();

CString temp;
for(int ii=0;ii<BLACK;ii++)
//初使化各进程记录文件信息(以.downN结尾)

temp.Format(".down%d",ii);
m_temp=fname+temp;
myfile.Open(m_temp,CFile::modeCreate|CFile::modeWrite | CFile::typeBinary);
//写入各进程文件信息
myfile.Write(&filerange[ii*2],sizeof(int));
myfile.Write(&filerange[ii*2+1],sizeof(int));
myfile.Close();


((CMainFrame*)::AfxGetMainWnd())->m_work.m_ListCtrl->AddItemtwo(n,2,0,0,0,doinfo.threadno);

else
//如果文件已存在,说明是续传,读上次信息
CString temp;

m_temp=fname+".down0";
if((fp=fopen(m_temp,"r"))==NULL)
return 1;
else fclose(fp);

int bb;
bb=0;
//读各进程记录的信息
for(int ii=0;ii<BLACK;ii++)

temp.Format(".down%d",ii);
m_temp=fname+temp;

myfile.Open(m_temp,CFile::modeRead | CFile::typeBinary);
myfile.Read(&filerange[ii*2],sizeof(int));
myfile.Read(&filerange[ii*2+1],sizeof(int));
myfile.Close();

bb = bb+filerange[ii*2+1];
CString temp;

if(bb==0) return 1;
doinfo.totle=doinfo.filelen-bb;

((CMainFrame*)::AfxGetMainWnd())->m_work.m_ListCtrl->AddItemtwo(n,2,doinfo.totle,1,0,doinfo.threadno);



//建立下载结束进程timethread,以管现各进程结束时间。
DWORD dwthread;
::CreateThread(NULL,0,timethread,(LPVOID)this,0,&dwthread);

return 0;
下面介绍建立各进程函数,很简单:

void CMainFrame::createthread(int threadno)

DWORD dwthread;
//建立BLACK个进程
for(int i=0;i<BLACK;i++)

m_thread[threadno][i]= ::CreateThread(NULL,0,downthread,(LPVOID)down[threadno],0,&dwthread);

downthread进程函数

DWORD WINAPI downthread(LPVOID lpparam)

cdownload* pthis=(cdownload*)lpparam;
//进程引索+1
InterlockedIncrement(&pthis->m_index);
//执行下载进程
pthis->threadfunc(pthis->m_index-1);
return 1;

下面介绍下载进程函数,最最核心的东西了

UINT cdownload::threadfunc(long index)

//初使化联接
sockaddr_in local;
SOCKET m_socket;

int rc=0;

local.sin_family=AF_INET;
local.sin_port=htons(1028);
local.sin_addr.S_un.S_addr=inet_addr(ip);
m_socket=socket(AF_INET,SOCK_STREAM,0);

int ret;
//读入缓存
char* m_buf=new char[SIZE];
int re,len2;
fileinfo fileinfo1;
//联接
ret=connect(m_socket,(LPSOCKADDR)&local,sizeof(local));
//读入各进程的下载信息
fileinfo1.len=filerange[index*2+1];
fileinfo1.seek=filerange[index*2];
fileinfo1.type=2;
fileinfo1.fileno=doinfo.threadno;

re=fileinfo1.len;

//打开文件
CFile destFile;
FILE* fp=NULL;
//是第一次传的话
if((fp=fopen(fname,"r"))==NULL)
destFile.Open(fname, CFile::modeCreate|CFile::modeWrite | CFile::typeBinary|CFile::shareDenyNone);
else
//如果文件存在,是续传
destFile.Open(fname,CFile::modeWrite | CFile::typeBinary|CFile::shareDenyNone);
//文件指针移到指定位置
destFile.Seek(filerange[index*2],CFile::begin);
//发消息给服务器,可以传文件了
sendn(m_socket,(char*)&fileinfo1,100);

CFile myfile;
CString temp;
temp.Format(".down%d",index);
m_temp=fname+temp;

//当各段长度还不为0时
while(re>0)
len2=re>SIZE?SIZE:re;

//读各段内容
int len1=readn(m_socket,m_buf,len2);
//有错的话
if(len1<0)
closesocket(m_socket);
break;


//写入文件
destFile.Write(m_buf, len1);

//更改记录进度信息

filerange[index*2+1]-=len1;
filerange[index*2]+=len1;
//移动记录文件指针到头
myfile.Seek(0,CFile::begin);
//写入记录进度
myfile.Write(&filerange[index*2],sizeof(int));
myfile.Write(&filerange[index*2+1],sizeof(int));

//减去这次读的长度
re=re-len1;

//加文件长度
doinfo.totle=doinfo.totle+len1;
;

//这块下载完成,收尾

myfile.Close();
destFile.Close();
delete [] m_buf;
shutdown(m_socket,2);

if(re<=0) good[index]=TRUE;
return 1;
到这客户端的主要模块和机制已基本介绍完。希望好好体会一下这种多线程断点续传的方法本回答被提问者采纳
参考技术B   P2P理财即P2P网贷,收益高,门槛低,投资灵活,是近年比较受追捧的理财方式。P2P理财指个人与个人之间的借贷,指以平台为中介机构,把这借贷双方对接起来实现各自的借贷需求。借款方可以是无抵押贷款或是有抵押贷款,投资者通过平台投资给借款方,而中介一般是收取双方或单方的手续费为盈利目的或者是赚取一定息差为盈利目的的新型理财模式。
  

什么是p2p技术

什么是P2P peer-to-peer简称P2P,即点对点技术。又称对等互联网络技术,是一种网络新技术,依赖网络中参与者的计算能力和带宽,而不是把依赖都聚集在较少的几台服务器上。 简单的说,P2P直接将人们联系起来,让人们通... 查看详情

区块链实战什么是p2p网络,区块链和p2p网络有什么关系

...块链节点与P2P的关系区块链节点功能分类P2P网络特征三、什么是P2P网络,区块链式使用P2P网络做什么1、P2P网络概念2、P2P网络节点特征3、P2P与区块链4、网络节点功能一、简介在白皮书中,中本聪就已经说明了这个系统的... 查看详情

什么是p2p

什么是P2P?P2P是peer-to-peer的缩写,peer在英语里有"(地位、能力等)同等者"、"同事"和"伙伴"等意义。这样一来,P2P也就可以理解为"伙伴对伙伴"的意思,或称为对等联网。目前人们认为其在加强网络... 查看详情

p2p是啥技术

p2p是什么(技术)?它的原理是什么,比如:下载,它和其他的下载软件工具有什么区别呀?用它下载快些,如快的原因是什么,对硬件要做哪些维护呀?如不快那是什么原因,怎么让它快,在硬盘不被损坏的情况下。P2P是peer-to-pe... 查看详情

什么叫做p2p

常常听别人在互联网上说什么P2P。请问什么是P2P未来互联网发展趋势是什么?(这个可以不回答。呵呵)下载——鼠标轻点几下即可完成的操作!迅雷、Bitcomet、电骡、风播.......大家使用的下载工具五花八门,但仔细研究这些主... 查看详情

端游下载的时候现在很多都是采用http传输,为什么不是p2p传输?

...载,还有推荐下载,也有一些是写着HTTP高速下载这些有什么区别?既然P2P传输的功能像你说到俺么强大,为什么他们不使用P2P技术,而是HTTP传输呢?对于这个问题,首先它并不是正确的,并不是所有的端游都用http传输,p2p传输... 查看详情

p2p的原理

p2p的原理是什么??急!!!急!!!急!!!!P2P软件是基于P2P技术工作的1、什么是p2pP2P是一种技术,但更多的是一种思想,有着改变整个互联网基础的潜能的思想。(1)p2p的概念P2P是peer-to-peer的缩写,peer在英语里有“(地... 查看详情

第六章p2p技术及应用

...内容进行归纳。文章中的Why表示产生的背景,也就是说为什么会产生该技术,What表示该技术是什么,How表示该技术是如何使用的。以下将用字母表示各问题。 1)P2P技术:Why:早期非对等结构网络操作系统主要共享的资源是 查看详情

什么是ptop技术

什么是PTOP技术,这种技术有那些优势,P2P即PeertoPeer,称为对等连接或对等网络,P2P技术主要指由硬件形成连接后的信息控制技术,其代表形式是软件。技术背景P2P起源于最初的联网通信方式,如在建筑物内PC通过局域网互联,不... 查看详情

“云”技术和p2p技术有什么区别?

云的概念就是服务器在一个云里,有很多服务器可以提供了某种服务。基于此意义,p2p技术就是一种云服务。P2P如果用来做传输分发,比如用BT部署自己的分发系统,这种就可以视为云分发。因为p2p背后也是支持很多服务器提供... 查看详情

p2p综述

原文参见:http://www.lotushy.com/?p=113[TOC]什么是P2PP2P全称是Peer-to-peer。P2P计算或P2P网络是一种分布式应用架构。它将任务或负载分发给Peers。在应用中,Peers是平等的、对等的参与者。从资源角度来讲,Peers将它们拥有的资源如cpu、... 查看详情

有关p2p技术问题

现在一些视频软件都用什么P2P技术,到底这个P2P技术是怎么样一个原理啊,请各位给讲一下?1P2P技术原理什么是对等网络(P2P)技术?P2P技术属于覆盖层网络(OverlayNetwork)的范畴,是相对于客户机/服务器(C/S)模式来说的一种网络信... 查看详情

今天可能取代 JXTA 和 P2P 的标准是啥?

...ardthatmighthavereplacedJXTAandP2P?今天可能取代JXTA和P2P的标准是什么?【发布时间】:2012-07-2405:30:21【问题描述】:我已经构建了一个即时消息应用程序+语音聊天(目前正在开发中),它被设计为集中式网络。但是当我第一次开始构... 查看详情

比特币存在哪里?区块链是什么?

第一篇文章《比特币:中本聪为什么设计比特币?》简单分享了比特币的起源。既然比特币可以脱离物理介质,仅通过互联网就可以流通,那么比特币到底存在哪?比特币是怎么交易的?区块链到底是什么... 查看详情

区块链跟p2p究竟有什么关系?

区块链这种技术在欧美国家会相对发展快一点,目前国内只能说处于早期接触和探索的阶段,但要说真正应用的,估计没有一个企业敢说已经把它变为一种生产力了,就目前来看,只是镜花水月。建安小谢 2016/06/0110:06浏览22.... 查看详情

常见又陌生的名词

P2P、P2C、O2O、B2C、B2B、C2C什么是P2PP2P借贷是一种将非常小额度的资金聚集起来借贷给有资金需求人群的一种民间小额借贷模式。P2P是“Peer-to-Peer”的简写,个人对个人的意思,P2P借贷指个人通过第三方平台(P2P公司)在收取一定服... 查看详情

P2P技术比较

...有其他技术,例如ICE、UPnP和teredo谁能告诉我这些技术有什么区别。哪一种是近年来用于P2P的最新技术/协议。如果能提供各种基于UDP的P2P协议的对比分析就好了。任何链接或建议将不胜感 查看详情

在 Wi-Fi 直连中一起连接到 P2P 组

...是独立的P2P组。我很想知道如果两个P2P组彼此靠近会发生什么?【问题讨论】:是P2P还是AP/客户端?我的意思是两个P2P组,每个组都有一个GO和一个对应的客户端。【参考方案1】:T 查看详情