《CSU计算机网络实验报告(共21页).doc》由会员分享,可在线阅读,更多相关《CSU计算机网络实验报告(共21页).doc(21页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。
1、精选优质文档-倾情为你奉上计算机网络实验报告学号: 姓名: 班级: 学院:信息科学与工程学院指导老师: 实验一:距离向量路由算法的实现1.1实验目的模拟距离向量路由算法的路由表交换过程,演示每轮交换后路由表的变化。1.2实验内容要求编程实现距离矢量路由算法的路由表交换过程,并动态演示每轮交换过后路由表的变化情况。1.3实验原理距离向量路由算法,使用这个算法的路由器必须掌握这个距离表(它是一个一维排列,即一个向量),它告诉在网络中每个节点的最远和最近距离。在距离表中的这个信息是根据临近接点信息的改变而时时更新的。表中数据的量和在网络中的所有的接点(除了它自己本身)是等同的。这个表中的列代表直接和
2、它相连的邻居,行代表在网络中的所有目的地。每个数据包括传送数据包到每个在网上的目的地的路径和距离/时间在那个路径上来传输(我们叫这个为“成本”)。这个在那个算法中的度量公式是跳跃的次数,等待时间,流出数据包的数量等等。在距离向量路由算法中,相邻路由器之间周期性地相互交换各自的路由表备份。当网络拓扑结构发生变化时,路由器之间也将及时地相互通知有关变更信息。每个路由器维护了一张路由表,它以子网中的每个路由器为索引,并且每个路由器对应一个表项。该表项包含两部分:为了达到该目标路由器而使用的输出线路,以及到达该目标路由器的时间估计值或者距离估计值。距离矢量路由算法在理论中可以工作,但在实践中有一个严重
3、的缺陷:虽然它总是能够达到正确的答案,但是它收敛到正确答案的速度非常慢,尤其是,它对于好消息的反应非常快,但是对于坏消息的反应非常迟缓。1.4实验步骤1.4.1编写程序程序的源代码如下:#include stdio.h#include stdlib.h#include alloc.h#define ROUTNUM 7typedef structint dis;int from;RoutNode;RoutNode dataROUTNUMROUTNUM;/*路由表*/void InitData(FILE* pfile);/*从数据文件读取数据,初始化路由表*/void OutputRoutData
4、();/*输出所有的路由表*/void Communication(int recv, int send);/*send点向recv点发送自己的路由表*/void Exchange();/*所有节点进行一次数据交换, 更新路由表*/void main()int start, end, i, j;FILE *pfile;pfile = fopen(1.txt, r);if (pfile = NULL)printf(文件打开错误,按任意键退出.n);getch();return;elseInitData(pfile);fclose(pfile);printf(n路由表初始:n);for (i =
5、0; iROUTNUM; i+)printf(%c|, i + 65);for (j = 0; j 0)printf( , j + 65, dataij.dis);printf(n);for (i = 0; i ROUTNUM; i+)Exchange();printf(n路由表交换:n);OutputRoutData();printf(输入起始路由节点(%d-%d) : , 0, ROUTNUM - 1);scanf(%d, &start);printf(输入终点路由节点(%d-%d) : , 0, ROUTNUM - 1);scanf(%d, &end);if (start = end |
6、 start 6 | end 6)printf(n输入错误,请按任意键退出n);getch();return;elseint cur = start;int total = 0;if (datastartend.dis , cur + 65);while (datacurend.from = 0)total += datacurdatacurend.from.dis;printf(%c-, datacurend.from + 65);cur = datacurend.from; /*end of while*/total += datacurend.dis;printf(%cn总的路由距离 =
7、 %d, end + 65, total);getch();return; /*end of else*/void InitData(FILE* pfile)char num10;int i = 0;char c;int m, n;fseek(pfile, 0, 0);for (m = 0; !feof(pfile) & m 7; m+)for (n = 0; !feof(pfile) & n = 0 & c = 9) | c = -) /*如果读到数字或符号*/numi+ = c; /*end of else if*/ /*end of while*/ /*end of for (n = 0
8、*/ /*end of for (m = 0*/void OutputRoutData()int i, j;printf( );for (i = 0; i ROUTNUM; i+)printf( %c , i + 65);printf(n);for (i = 0; i ROUTNUM; i+)printf(%c , i + 65);for (j = 0; j ROUTNUM; j+)if (dataij.dis = 10)printf( %d, dataij.dis);elseprintf( %d, dataij.dis);if (dataij.from 0)/*如果未经过其它节点*/prin
9、tf( - );elseprintf( %c , dataij.from + 65); /*end of for (j = 0*/printf(n); /*end of for (i = 0*/void Communication(int recv, int send)int i;for (i = 0; i 0)/*如果send节点到i号节点有路线*/if (datarecvi.dis datasendi.dis + datarecvsend.dis)/*如果现有路径比新路径远*/datarecvi.dis = datasendi.dis + datarecvsend.dis;datarecv
10、i.from = send; /*end of if*/ /*end of for*/void Exchange()int i, j;for (i = 0; i ROUTNUM; i+)for (j = 0; j 0)/*如果两个节点之间有路径*/Communication(j, i);/*将i号节点的路由表发送给j号节点*/ /*end of if*/ /*end of for (j = 0*/ /*end of for (i = 0*/1.4.2设计思路程序先定义了一个路由表RoutNode dataROUTNUMROUTNUM,路由表的初始信息存储在文件中,程序运行是先调用函数InitD
11、ata(FILE* pfile)从文件中读取路由表的初始信息,然后输出初始路由表的信息,Communication(int recv, int send)函数主要是向邻近节点发送自己的路由表信息,Exchange()函数则根据新路由表信息更新自己的路由表。当所有的路由表节点都更新一遍后,整个路由表更新完毕。1.5实验结果分析1.5.1结果截图1.5.2结果分析路由表初始信息从文件读取,根据距离向量路由算法系统自动完成路由表的更新操作,最后任意输入两个路由表接点,则可得出两接点之间的最短路径。1.6实验心得体会实验是对我们应用知识的考察,通过它我们能更加了解自己的能 力。这次的实验是网络课实验中
12、最简单的一次,但我做得一点都不好,还没有写软件的概念和思想,程序也写得不好,还没有再实验课上完成的,是后来到寝室才完成的,没有通过老师的检查,幸亏我们的老师心地善良,说不用检查也可以通过。这个程序只能实现主要的功能,没有界面,也没有什么操作,因能力有限,只能做到这个样子,还望老师见谅。有空的话我一定好好学习一种编程软件。实验二 网络聊天窗口2.1实验目的1, 进一步加深对网络底层数据传输过程的理解2, 通过自己动手编写具体的代码,实现实验的要求,提高学生的编程能力3, 熟悉socket编程接口,初步掌握用socket编程接口开发面向连接的网络应用程序的方法。4, 熟悉socket编程接口,初步
13、掌握用socket编程接口开发无连接的网络应用程序的方法。2.2实验原理为实现网络聊天的功能,采用Windows Socket编程,服务器与客户端采用了TCP/IP连接方式,在设计聊天方案时,实行将所有信息发往服务器端,再由服务器进行分别处理的思路,服务器端是所有信息的中心。由于服务器端要保存用户信息,我们暂时利用文件保存来实现这一功能,这是为了保存较好的可移植性,在没装相应数据库的机子上也能顺利地运行。在客户端保存用户号码这一功能的实现中,采用了文件系统设计。在不同的客户间可以实现文件的传输,其原理与信息传送差不多,只不过传输的内容是文件字节流。服务器及客户端的功能可划分为以下模块:客户端:
14、1) 登陆功能:建立与服务器的连接并登陆,能显示登陆错误信息。(由于本项目是作者09年时出于兴趣自己开始做的,所以界面中显示的是QQ2009)用用户名字登录。密码都默认为123其中,点击界面上的“注册新账号”会出现下图:在里面填写相应的名字和密码即可注册,当然服务器也要开启相应的端口,如下:2) 界面显示:将在线好友显示在好友列表中,并实现系统托盘,加入工具栏便于操作。本界面中左边和右边都是截图所得,这些按钮没有实际功能,只为了模仿QQ。3) 聊天功能:与好友聊天。本界面做的时候有点bug,就是聊天窗口中只有一个有个人形象展示,如上, 在左边打开的窗口中没有,右边有。这一个bug有空会改过来的
15、。4) 发送文件:能发送任一文件,当然文件不能过大,否则可能会出问题。收到的图片可以正常打开 5) 信息提示:闪动托盘图标提示到来信息,并播放不同音乐来提示。6) 其他: 用户登陆成功,将保存其号码,以便下次登陆时,不必再输入而可以直接选择,显示登陆时间。登陆到服务器客户端申请新的号码显示在线用户接收各种信息保存用户号码发送文件服务器端:写上一个合适的端口后点击开启端口,就可以开启 一个端口用来专门接收用户的连接。当有用户上线进,就会把相应的用户列在列表中。向各个客户端发布系统消息。接受来自客户端的各种信息并分别处理。1) 登陆信息:检查登陆信息是否正确,并向客户端返回登陆信息,如信息正确。就
16、将在线用户发给该用户,并将该用户的状态发给各在线用户。同时在服务器端显示出来。2) 聊天信息:转发给消息指定的用户。3) 申请信息:自动分配8位用户号码,并保存该用户,同时将信息返回给客户端。4) 用户下线:将此用户下线消息发给各客户端,并改写用户在服务器端的状态。服务器端处理申请信息转发聊天信息处理登陆信息发布系统消息2.3实验具体实现1、 服务器端:服务器端启动时,先初始化服务端界面,之后开启一个端口用来监听客户端的连接:ChatServer.java文件里面:public void setUpServer() try System.out.println(port);/ 创建服务端套接字
17、server = new .ServerSocket(port);MakeLog.writeLog(成功创建了一个套接字,ChatServer);/ 进入一个循环来等待客户端while (true) if (server != null) .Socket client = server.accept();/ 开一个线程ServerThread newThread = new ServerThread(client);MakeLog.writeLog(已经创建一个线程连接. 客户端地址:+ client.getRemoteSocketAddress(),ChatServer);listSock.
18、add(client);/ 启动线程newThread.start(); catch (Exception e) e.printStackTrace();MakeLog.writeError(e.getMessage(),ChatServer);然后,当有一个客户端连接上来的时候,就开启一个线程分配给该用户,用来管理该用户的连接及一些相关的操作。(其它知识点与本实验无关,这里就不再写了,下面看客户端)2、 客户端:客户端一启动时,先构造出登陆界面,当点击登陆按钮时,先做一下简单的判断,看是否账号或密码为空, 当它们都合法的时候就进入下一步:/* * 对登陆按钮作出回应 */public voi
19、d react()if (null != tf_name.getText() | null != tf_psw. getText() name = tf_name.getText().trim();psw = tf_psw.getText().trim();System.out.println(name:+name+ psw:+psw);/ 创建一个连接,连接服务器 connServer(serverIp, port); ClientMng.manage(client);/ 登陆if(ClientMng.logon(name, psw)ClientThread threadCl=new Cli
20、entThread();threadCl.start();elsejavax.swing.JOptionPane.showMessageDialog(jf,登陆失败!用户名已登陆或密码或用户名错误!); else javax.swing.JOptionPane.showMessageDialog(null,对不起,用户名和密码不能为空!);kk=0;jf.dispose(); /最后把登陆界面关掉。分析代码。先用客户端内置的预设的服务器地址和端口 进行socket连接信尝试,连接成功时,客户端马上给服务器发送相关的用户名和密码,服务器验证通过的时候会向客户端返回一条确认信息,客户端如果接到该确
21、认信息说明已经登陆成功了,他们就有了一个永久性的连接,直到其中的一方关闭连接为止。其实在这过程中,还有一些环节:/* * 登陆用的函数 * param name:登陆用户名 * param psw:登陆密码 * return:是否登陆成功,true登陆成功,false登陆失败 */public static boolean logon(String name, String psw) myName = name;String namePsw;if (clientSock != null) namePsw = name + # + psw;sendMsg(namePsw, system);/ 发
22、送用户名和密码try msg = readPackage();if (msg.equals(系统说:对不起,您的用户名可能为空或未注册或已登陆!) / javax.swing.JOptionPane.showMessageDialog(MainClient.getFrame(),/ 对不起,您的用户名可能为空或未注册或已登陆!);return false;if (msg.equals(系统说:登陆失败!密码错误!) javax.swing.JOptionPane.showMessageDialog(MainClient.getFrame(), 登陆失败!密码错误!);return false;
23、sendMsg(OK!, system);msg = readPackage();sendMsg(OK!, system);/ 接收服务器发过来的在线用户列表names = readPackage();/处理服务器刚发过来的在线用户列表if (names != null & !names.equals() String s = names.split(说:);String allName = s1.split(#);for (int i = 0; i allName.length; i+) if (!allNamei.equals() & allNamei != null& !exists(a
24、llNamei) listUser.add(allNamei);/ 发送一条消息告诉服务器,是否需要它发送分组信息过来if (needToSendTeamInfo() sendMsg(发过来, system);/ 接收服务器发过来的分组信息并保存/msg = readPackage(); SaveFileAfterRecievingTeamInfo(); else sendMsg(不用发, system);initial(); catch (Exception ef) ef.printStackTrace();return true;return true;当客户端发送了用户名和密码之后,如果
25、收到的信息是:“对不起,您的用户名可能为空或未注册或已登陆!”则说明重复登陆,登陆失败。如果收到的信息是:“登陆失败!密码错误!”则说明是密码错误,当然也有可能是不存在这个用户。收到的信息如果 是其它的情况,则登陆成功,这时,双方还会再各发条“OK”信息来确认双方的连接并协调步伐。之后,客户端会判断本地是否已经有相关的列表信息,如果有,则会直接读取本地好友列表信息,如果没有的话,会请求服务器发送相关的好友列表。收到好友列表后,再解析,并构建成一棵树,显示在界面的列表项中。客户端有一个工具类,里面有一个读取消息并分解消息的方法:/* * 按协议来读数据,包括XX说: * return:读包结果
26、* throws IOException */public static String readPackage() throws IOException / 开始读数据if (dins != null) int msgLength = dins.readInt();/ int,长度if(clientSock.isClosed()System.exit(1);byte type = dins.readByte();/ byte,类型byte toWhom=new byte10;dins.readFully(toWhom);/ byte10,给谁String flag=new String(toW
27、hom);byte identify = new byte12;dins.readFully(identify);/byte12,特殊字段String ident=new String(identify);/ 判断线程是否被关了if (!clientSock.isClosed() System.out.println(msgLength+ +type+ +flag+ +ident);if (type = 1) / 1.表示要传送消息byte content = new bytemsgLength - 4 - 1 - 10-12;dins.readFully(content);/ byte剩下,
28、消息内容String msg = new String(content);System.out.println(长度: + msgLength + 类型: + type+ 给谁: + flag.trim() + 内容: + msg.trim();String theMsg=msg.trim().split(说:)1;theSender=msg.trim().split(说:)0;if (flag.trim().equals(注册者) if(msg.trim().equals(系统说:注册成功)javax.swing.JOptionPane.showMessageDialog(null, 注册成
29、功!,系统消息, 2);elsejavax.swing.JOptionPane.showMessageDialog(null, 注册失败,已有此用户名!,系统消息, 2);else/发送者是系统,也是要返回msg.trim(),所以一样的处理isNewLogon(msg.trim();if (发文件.equals(ident.trim() String realMsg = theMsg.split(#)1;String fakeName = realMsg.split(nt)0;if (!fakeName.equals(发送者: + myName) acceptFile = javax.swi
30、ng.JOptionPane.showConfirmDialog(ChatUI.getFrame(),有文件,是否接收? + realMsg, 文件消息,1);String senderFilePath = theMsg.split(#)0;if (acceptFile = 0) sendMsg(接收# + senderFilePath,theSender); else sendMsg(不接收# + senderFilePath,theSender);return msg.trim(); else if (type = 2) / 2.表示要传文件byte fileName = new byte
31、100;dins.readFully(fileName);/ byte100,文件名System.out.println(&+new String(fileName).trim();/解析出“说:“String s=new String(fileName);String strs=s.split(说:);theSender=strs0;String fname;if (strs.length 2) fname = 空文件; else fname = strs1;byte content = new bytemsgLength - 4 - 1 - 10 -12- 100;/ byte剩下,文本内
32、容dins.readFully(content);/获得接收时的时间java.util.Date date = new java.util.Date();java.text.SimpleDateFormat st = new java.text.SimpleDateFormat(yyyy-MM-dd hh:mm:ss);String time = st.format(date);/弹出对话框javax.swing.JOptionPane.showMessageDialog(null,收到文件,请选择一个存放路径 , 消息, 2);javax.swing.JFileChooser fcho=ne
33、w JFileChooser();fcho.setDialogTitle(选择文件);/设置只能选文件夹fcho.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY); int returnVal = fcho.showOpenDialog(null);if (returnVal = JFileChooser.APPROVE_OPTION)File selFile = fcho.getSelectedFile();String filePath=selFile.getPath();/获得选中的路径FileOutputStream localWr
34、i = new FileOutputStream(filePath+ +fname.trim();System.out.println(文件:+filePath+ fname.trim();localWri.write(content);localWri.flush();localWri.close();recieveFile(theSender,fname,time,filePath);return myName+说:File saved successfully!; else return 收到未知数据包!; else return error,Socket has bean closed
35、!; else return error,DataInputStream is shut;return 系统说:文件发送成功!;在这里面完成了注册、聊天信息、发接文件信息的处理。当然,发送消息也有一个相关的打包函数,限于篇幅,这里就不贴出来 了。服务器也有相应的函数。聊天的实现:客户端向服务器发送一个消息包,里面包含了消息类型、接收人和发送人等信息,服务器接到的时候先判断,如果是聊天消息,就取出其中的接收人信息,并在自己的线程池里面查找相应的线程,找到时把消息(包含发送人和消息内容等)通过这个线程发送出去。这样对方就可以接到这个消息。对方如果要回复的话,也可以把发送人和接收人及聊天消息等信息包
36、装起来发送给服务器,服务器再用之前一样的方法来处理这个信息,这样的话,双方就可以通过服务器实现单聊了。2.4实验结论Socket通信是网络通信中的重要环节,本实验中主要实现了TCP/IP的通信,传递相应的信息来完成各种不同的交互功能。聊天工具功能很强大,看起来很复杂,其实底层最基本的实现原理都是一样的。基于TCP/IP协议的连接是比较可靠的,它先通过“三次握手”建立彼此间的一条通路,之后,两者就可以通过这条通路有效地传递信息了。另一方面,两端要传送信息时,也可以通过第三方来转发,这样,我们就可以把各种连接都建立到同一个端点上,构成一个星形的结构,然后通过这个端点的转发,就可以任何两端之间的通信。2.5心得体会通过“计算机网络基础”自己对网络的基础知识也打下了很好的基础。这次网络实验可以说是在理解网络的基础上对Windows Socket 编程的一次学习过程,虽然做的不好,但也学到了很多知识,对自己以后进行网络开发有很大的帮助。专心-专注-专业