20165203实验五 网络编程与安全

任务一

两人一组结对编程:

  1. 参考(http://www.cnblogs.com/rocedu/p/6766748.html#SECDSA)
  2. 结对实现中缀表达式转后缀表达式的功能 MyBC.java
  3. 结对实现从上面功能中获取的表达式中实现后缀表达式求值的功能,调用MyDC.java
  4. 上传测试代码运行结果截图和码云链接

一、实验过程:

1.根据娄老师的博客,我们先了解前缀表示法、中缀表示法和后缀表示法的概念:

表达式Exp = S1 + OP + S2(S1 ,S2是两个操作数,OP为运算符)有三种标识方法:

OP + S1 + S2 为前缀表示法
S1 + OP + S2 为中缀表示法
S1 + S2 + OP 为后缀表示法
例如:Exp = a * b + (c - d / e) * f

前缀式: + * a b * - c / d e f
中缀式: a * b + c - d / e * f
后缀式: a b * c d e / - f * +

2.中缀表达式转化成后缀表达式的过程:

  • 设立一个栈,存放运算符,首先栈为空;
  • 从左到右扫描中缀式,若遇到操作数,直接输出,并输出一个空格作为两个操作数的分隔符;
  • 若遇到运算符,则与栈顶比较,比栈顶级别高则进栈,否则退出栈顶元素并输出,然后输出一个空格作分隔符;
  • 若遇到左括号,进栈;若遇到右括号,则一直退栈输出,直到退到左括号止。
  • 当栈变成空时,输出的结果即为后缀表达式。

3.中缀表达式转化成后缀表达式代码实现:

import java.util.*;public class NewMyBC {String beforeExpression;//未转化的中缀表达式String afterExpression = "";//转化后的后缀表达式int left = 0;//定义左括号数int right = 0;//定义右括号数//判断符号的级别public int judgeGrade(char chi) {int grade = 0;switch (chi) {//左括号是第一级case '(':grade = 1;break;//+和-是第二级case '+':case '-':grade = 2;break;//*和÷是第三级case '*':case '÷':grade = 3;break;// "/"是第四级case '/':grade = 4;break;//右括号是第五级case ')':grade = 5;break;default:grade = 0;}return grade;}public void setBeforeExpression(String exp) {beforeExpression=exp;}public String transformWay() {Stack stack = new Stack();//新建一个空栈int i = 0;char op;while (i < beforeExpression.length()) {op = beforeExpression.charAt(i);//op存放从中缀表达式中取到的元素if (op >= '0' && op <= '9') {afterExpression = afterExpression + op;//如果是数字,则直接输出至后缀表达式} else if (op == '+' || op == '-' || op == '*' || op == '÷') {afterExpression = afterExpression + ' ';//有运算符,在数字之间加空格// 如果栈为空,则运算符直接入栈if (stack.empty()) {stack.push(op);}//根据符号的级别判断操作else if (judgeGrade(op) > judgeGrade((char) stack.peek())) {stack.push(op);//比栈顶级别高或相等,直接入栈} else {afterExpression = afterExpression + String.valueOf(stack.pop()) + ' ';//否则直接输出i--;}} else if (op == '(') {left++;stack.push(op);//左括号直接入栈} else if (op == ')') {afterExpression += " ";right++;while ((char) stack.peek() != '(') {//右括号,出栈,直到左括号为止afterExpression = afterExpression + String.valueOf(stack.pop()) + " ";}stack.pop();}i++;}afterExpression += " ";while(!stack.empty()){afterExpression=afterExpression+String.valueOf(stack.pop())+" ";}if (left != right) {System.out.println("括号有误");System.exit(0);}return afterExpression;}
}

4.后缀表达式求值的步骤:

  • 设置一个操作数栈,开始栈为空;
  • 从左到右扫描后缀表达式,遇操作数,进栈;
  • 若遇运算符,则从栈中退出两个元素,先退出的放到运算符的右边,后退出的放到运算符左边,运算后的结果再进栈,直到后缀表达式扫描完毕。
    此时,栈中仅有一个元素,即为运算的结果。

5.求值代码:


import java.util.Stack;public class MyDC {/*** constant for addition symbol*/private final char ADD = '+';/*** constant for subtraction symbol*/private final char SUBTRACT = '-';/*** constant for multiplication symbol*/private final char MULTIPLY = '*';/*** constant for division symbol*/private final char DIVIDE = '÷';/*** the stack*/private Stack<Integer> stack;//存放操作数的栈public MyDC() {stack = new Stack<Integer>();}public int evaluate(String expr) {int op1, op2, result = 0;String token;StringTokenizer tokenizer = new StringTokenizer(expr);//划分表达式while (tokenizer.hasMoreTokens()) {token = tokenizer.nextToken();//将算数表达式分解的if (isOperator(token))//见下方isOperateor方法,当是运算符的时候进入if语句{op2 = (stack.pop()).intValue();op1 = (stack.pop()).intValue();//弹出最上面两个操作数result = evalSingleOp(token.charAt(0), op1, op2);//见下方evaSingleOp方法stack.push(new Integer(result));//将计算结果压栈} else{stack.push(new Integer(Integer.parseInt(token)));//操作数入栈}}return result;//输出结果}private boolean isOperator(String token)//判断是否为运算符,注意用equal语句比较字符串{return (token.equals("+") || token.equals("-") ||token.equals("*") || token.equals("÷"));}private int evalSingleOp(char operation, int op1, int op2) {int result = 0;switch (operation) {case ADD:result = op1 + op2;break;case SUBTRACT:result = op1 - op2;break;case MULTIPLY:result = op1 * op2;break;case DIVIDE:result = op1 / op2;}return result;}
}

6.测试代码如下:


import java.util.Scanner;public class MyDCTest {public static void main(String[] args) {String expression, again;int result;try {Scanner in = new Scanner(System.in);do {MyDC evaluator = new MyDC();System.out.println("Enter a valid postfix expression: ");expression = in.nextLine();result = evaluator.evaluate(expression);System.out.println();System.out.println("That expression equals " + result);System.out.print("Evaluate another expression [Y/N]? ");again = in.nextLine();System.out.println();}while (again.equalsIgnoreCase("y"));} catch (Exception IOException) {System.out.println("Input exception reported");}}
}  

二、实验截图:

三、码云链接

任务二

结对编程:1人负责客户端,一人负责服务器

  1. 注意责任归宿,要会通过测试证明自己没有问题
  2. 基于Java Socket实现客户端/服务器功能,传输方式用TCP
  3. 客户端让用户输入中缀表达式,然后把中缀表达式调用MyBC.java的功能转化为后缀表达式,把后缀表达式通过网络发送给服务器
  4. 服务器接收到后缀表达式,调用MyDC.java的功能计算后缀表达式的值,把结果发送给客户端
  5. 客户端显示服务器发送过来的结果
  6. 上传测试结果截图和码云链接

一、实验过程:

1.经过与搭档协商,我负责客户端(Client.java)部分,搭档负责服务端(Server.java)部分。

2.客户端部分的代码如下:


import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.*;
import java.net.*;
import java.util.*;public class Client {public static void main(String[] args) {Socket socket;//套接字对象DataInputStream in=null;//输入流DataOutputStream out=null;//输出流//中缀表达式的输入String str;Scanner scanner=new Scanner(System.in);System.out.println("请输入中缀表达式:");str=scanner.nextLine();try {socket=new Socket("localhost",5203);in=new DataInputStream(socket.getInputStream());out=new DataOutputStream(socket.getOutputStream());out.writeUTF(str);String s=in.readUTF();System.out.println("结果为:\n"+s);}catch (Exception e) {System.out.println("服务器已断开"+e);}}
}

二、实验截图:

三、码云链接

任务三

加密结对编程:1人负责客户端,一人负责服务器

  1. 注意责任归宿,要会通过测试证明自己没有问题
  2. 基于Java Socket实现客户端/服务器功能,传输方式用TCP
  3. 客户端让用户输入中缀表达式,然后把中缀表达式调用MyBC.java的功能转化为后缀表达式,把后缀表达式用3DES或AES算法加密后通过网络把密文发送给服务器
  4. 服务器接收到后缀表达式表达式后,进行解密(和客户端协商密钥,可以用数组保存),然后调用MyDC.java的功能计算后缀表达式的值,把结果发送给客户端
  5. 客户端显示服务器发送过来的结果
  6. 上传测试结果截图和码云链接

一、实验过程:

1.我负责客户端,负责编写Client.java.

2.根据娄老师的密码学算法博客,我和搭档所共同完成的DES算法代码如下:

import java.io.*;
import javax.crypto.*;
public class Skey_DES{public static void main(String args[]) throws Exception{KeyGenerator kg=KeyGenerator.getInstance("DESede");kg.init(168);SecretKey k=kg.generateKey( );FileOutputStream  f=new FileOutputStream("key1.dat");ObjectOutputStream b=new  ObjectOutputStream(f);b.writeObject(k);}
}  

3.Client.java代码如下:

在之前的代码上,增加如下代码:

import java.io.*;
import java.net.*;
import java.util.Scanner;public class Client {public static void main(String[] args) {String mess;Scanner scanner=new Scanner(System.in);System.out.println("请输入问题");mess=scanner.nextLine();String key="";int n=-1;byte [] a=new byte[128];try{  File f=new File("key1.dat");InputStream in = new FileInputStream(f);while((n=in.read(a,0,100))!=-1) {key=key+new String (a,0,n);}in.close();}catch(IOException e) {System.out.println("File read Error"+e);}System.out.println("客户端提出的问题为:"+mess);NewMyBC mybc=new NewMyBC();String str;mybc.setBeforeExpression(mess);str=mybc.transformWay();String mi=EncryptDecrypt.AESEncode(key,str);System.out.println("客户端加密后密文为:"+mi);Socket socket;DataInputStream in=null;DataOutputStream out=null;try{  socket=new Socket("localhost",5006);in=new DataInputStream(socket.getInputStream());out=new DataOutputStream(socket.getOutputStream());BufferedReader in1=new BufferedReader(new InputStreamReader(socket.getInputStream()));PrintWriter writer=new PrintWriter(socket.getOutputStream());out.writeUTF(mi);String  s=in.readUTF();   //in读取信息,堵塞状态System.out.println("客户收到服务器的回答为:"+s);Thread.sleep(500);}catch(Exception e) {System.out.println("服务器已断开"+e);}}
}

二、实验截图:

三、码云链接

任务四

密钥分发结对编程:1人负责客户端,一人负责服务器

  1. 注意责任归宿,要会通过测试证明自己没有问题
  2. 基于Java Socket实现客户端/服务器功能,传输方式用TCP
  3. 客户端让用户输入中缀表达式,然后把中缀表达式调用MyBC.java的功能转化为后缀表达式,把后缀表达式用3DES或AES算法加密通过网络把密文发送给服务器
  4. 客户端和服务器用DH算法进行3DES或AES算法的密钥交换
  5. 服务器接收到后缀表达式表达式后,进行解密,然后调用MyDC.java的功能计算后缀表达式的值,把结果发送给客户端
  6. 客户端显示服务器发送过来的结果
  7. 上传测试结果截图和码云链接

一、实验过程:

1.我负责客户端,搭档负责服务器端。

2.根据娄老师的密码学算法博客,我和搭档共同完成的DES算法代码如下:


import java.security.PublicKey;
import java.security.PrivateKey;
import java.io.*;
import javax.crypto.KeyAgreement;
import javax.crypto.spec.*;public class KeyAgree{public static void main(String args[ ]) throws Exception{// 读取对方的DH公钥File file=new File("Ckey.dat");FileInputStream f1=new FileInputStream("Apub.dat");ObjectInputStream b1=new ObjectInputStream(f1);PublicKey  pbk=(PublicKey)b1.readObject( );
//读取自己的DH私钥FileInputStream f2=new FileInputStream("Bpri.dat");ObjectInputStream b2=new ObjectInputStream(f2);PrivateKey  prk=(PrivateKey)b2.readObject( );// 执行密钥协定KeyAgreement ka=KeyAgreement.getInstance("DH");ka.init(prk);ka.doPhase(pbk,true);//生成共享信息byte[ ] sb=ka.generateSecret();for(int i=0;i<sb.length;i++){System.out.print(sb[i]+",");}OutputStream out=new FileOutputStream(file);out.write(sb);out.close();SecretKeySpec k=new  SecretKeySpec(sb,"AES");}
}
public class Dapart {String dapartstring(String str){String s="";char c[]=str.toCharArray();for(int i=0;i<c.length;i++){s=s+c[i]+" ";}return s;}
}

部分代码,具体代码见码云链接
3.客户端的代码在实验二的基础上增加如下代码:

 import java.io.*;
import java.net.*;
import java.util.Scanner;public class Client {public static void main(String[] args)throws IOException{String key="";int n=-1;byte [] a=new byte[128];try{  File f=new File("Ckey.dat");InputStream in = new FileInputStream(f);while((n=in.read(a,0,100))!=-1) {key=key+new String (a,0,n);}in.close();}catch(IOException e) {System.out.println("File read Error"+e);}String mess;Scanner scanner=new Scanner(System.in);System.out.println("请输入问题:");mess=scanner.nextLine();NewMyBC mybc=new NewMyBC();String str;mybc.setBeforeExpression(mess);str=mybc.transformWay();String m=EncryptDecrypt.AESEncode(key, str);System.out.println("客户加密之后的密文为:"+m);Socket mysocket;DataInputStream in=null;DataOutputStream out=null;try{  mysocket=new Socket("localhost",6006);in=new DataInputStream(mysocket.getInputStream());out=new DataOutputStream(mysocket.getOutputStream());out.writeUTF(m);String  s=in.readUTF();   //in读取信息,堵塞状态System.out.println("客户收到服务器的回答为:"+s);Thread.sleep(500);}catch(Exception e) {System.out.println("服务器已断开"+e);}}
}

二、实验截图:

三、码云链接

任务五

实验五 网络编程与安全-5
完整性校验结对编程:1人负责客户端,一人负责服务器

  1. 注意责任归宿,要会通过测试证明自己没有问题
  2. 基于Java Socket实现客户端/服务器功能,传输方式用TCP
  3. 客户端让用户输入中缀表达式,然后把中缀表达式调用MyBC.java的功能转化为后缀表达式,把后缀表达式用3DES或AES算法加密通过网络把密文和明文的MD5値发送给服务器
  4. 客户端和服务器用DH算法进行3DES或AES算法的密钥交换
  5. 服务器接收到后缀表达式表达式后,进行解密,解密后计算明文的MD5值,和客户端传来的MD5进行比较,一致则调用MyDC.java的功能计算后缀表达式的值,把结果发送给客户端
  6. 客户端显示服务器发送过来的结果
  7. 上传测试结果截图和码云链接

一、实验过程:

1.我负责客户端,搭档负责服务器端。

2.根据娄老师的密码学算法博客,我和搭档共同完成的算法代码如下:

import java.security.*;
public class DigestPass{static String md5(String str) throws Exception{MessageDigest m=MessageDigest.getInstance("MD5");m.update(str.getBytes("UTF8"));byte s[ ]=m.digest( );String result="";for (int i=0; i<s.length; i++){result+=Integer.toHexString((0x000000ff & s[i]) |0xffffff00).substring(6);}return result;}
}  

3.客户端代码如下:

就之前实验二的代码添加如下代码:

 import java.net.*;
import java.util.Scanner;public class Client {public static void main(String[] args) throws Exception {String key = "";int n = -1;byte[] a = new byte[128];try {File f = new File("Ckey.dat");InputStream in = new FileInputStream(f);while ((n = in.read(a, 0, 100)) != -1) {key = key + new String(a, 0, n);}in.close();} catch (IOException e) {System.out.println("File read Error" + e);}String mess;Scanner scanner = new Scanner(System.in);System.out.println("请输入问题为:");mess = scanner.nextLine();NewMyBC mybc = new NewMyBC();String str;mybc.setBeforeExpression(mess);str = mybc.transformWay();String md5 = DigestPass.md5(str);String mw = EncryptDecrypt.AESEncode(key, str);System.out.println("客户端提供的MD—5为:" + md5);System.out.println("客户加密之后的密文为:" + mw);Socket mysocket;DataInputStream in = null;DataOutputStream out = null;try {mysocket = new Socket("localhost", 2010);in = new DataInputStream(mysocket.getInputStream());out = new DataOutputStream(mysocket.getOutputStream());out.writeUTF(mw);out.writeUTF(md5);String answer = in.readUTF();   //in读取信息,堵塞状态System.out.println("客户收到服务器的回答为:" + answer);Thread.sleep(500);} catch (Exception e) {System.out.println("服务器已断开" + e);}}
}

部分代码,具体代码见码云链接

二、实验截图:

三、码云链接

实验过程中遇到的问题及解决办法

Q:在运行代码时,提示Error:(1, 1) java: 非法字符: '\ufeff',该怎么做?

A:我百度了一下,找到了一篇博客,根据博客里的步骤,解决了问题。

步骤 耗时(h) 百分比
设计 2 20%
代码实现 5 50%
测试 5 20%
分析总结 1 10%

实验体会总结

本次实验,我主要负责客户端代码,搭档负责服务器端代码,许多算法也是我们根据娄老师的博客共同研究出来的。本次实验是最后一次实验了,本学期的确受Java折磨不少,但是还是感谢娄老师给我们提供了很多新的学习方法,相信以后Java会帮助我们很多的。

转载于:https://www.cnblogs.com/20165203-xyx/p/9101016.html

20165203实验五 网络编程与安全相关推荐

  1. java 网络实验_Java实验五网络编程与安全

    实验五 网络编程与安全 实验准备 活动一 两人一组结对编程: 0. 参考http://www.cnblogs.com/rocedu/p/6766748.html#SECDSA 1. 结对实现中缀表达式 ...

  2. 20165201 实验五 网络编程与安全

    ##20165201 实验五 网络编程与安全 网络编程与安全-1 实验目的与要求: 两人一组结对编程: 参考http://www.cnblogs.com/rocedu/p/6766748.html#S ...

  3. 2017-2018-2 20165329 实验五 网络编程与安全

    2017-2018-2 20165329 实验五 网络编程与安全 实验报告封面 课程:Java程序设计 班级:1653班 姓名:何佳伟 学号:20165329 指导教师:娄嘉鹏 实验日期:2018年5 ...

  4. #20175201 实验五 网络编程与安全

    一.实验五 网络编程与安全-1 1.实验要求: 两人一组结对编程: (1)参考http://www.cnblogs.com/rocedu/p/6766748.html#SECDSA : (2)结对实现 ...

  5. 实验五 网络编程与安全-----实验报告

    一.实验五 网络编程与安全-1 1.实验要求: 两人一组结对编程: (1)参考http://www.cnblogs.com/rocedu/p/6766748.html#SECDSA : (2)结对实现 ...

  6. java小球碰撞实验报告_20155317 《Java程序设计》实验五网络编程与安全实验报告...

    20155317 <Java程序设计>实验五网络编程与安全实验报告 遇到问题 在刚开始启动客户端或者服务端时,出现了一系列的错误情况,总是提示异常信息 后来经过询问同学,反应将端口号修改一 ...

  7. 2016-2017-2 20155322 实验五 网络编程与安全

    2016-2017-2 20155322 实验五 网络编程与安全 目录 1. 目录 1.1 实践一 1.2 实践二 1.3 实践二 1.4 实践二 1.5 实践二 2.实验心得与体会 3.PSP(Pe ...

  8. 实验五 网络编程与安全

    一.实验报告封面 课程:Java程序设计 班级:1653班 姓名:高君天 学号:20165319 指导教师:娄嘉鹏 实验日期:2018年5月28日 实验时间:13:45 - 3:25 实验序号:实验五 ...

  9. 20155207 实验五 网络编程与安全

    20155207 实验五 网络编程与安全 实验内容 任务一 两人一组结对编程: 参考http://www.cnblogs.com/rocedu/p/6766748.html#SECDSA 结对实现中缀 ...

最新文章

  1. 兑换量子计算机,阅读 | 【量子计算机】构造置换量子门
  2. 英特尔在移动芯片为何衰败 看完此文豁然开朗
  3. Linux中的基础和小工具
  4. Java反射机制简单使用
  5. 95 后大学生利用漏洞免费吃肯德基获刑
  6. 万级K8s集群背后etcd稳定性及性能优化实践
  7. MariaDB基础(二)
  8. C++中const、volatile、mutable的用法
  9. sqlserver2000内存突破4g_友商都上16G,华为手机为何一直用8G内存?网友:效仿iOS...
  10. 下载的代码找不到rt.jar中的类
  11. jQuery.ajax处理继续响应:“成功:”还是“ .done”?
  12. 【转】每天一个linux命令(11):nl命令
  13. Android下如何使用smem工具获取进程的内存分布
  14. 前端项目使用阿里图标
  15. POJO, VO什么的是个什么鬼?
  16. RabbitMQ极速入门
  17. Linux代理服务器 Centos Nginx安装、反向代理配置、Nginx开机自启动及日志每天自动分割压缩
  18. python数据分析的交叉分析和分组分析 -第三次笔记
  19. win2008r2用户账户控制什么意思_养老保险统筹账户是什么意思?有什么用?
  20. 访问控制模型详细介绍

热门文章

  1. DHCP服务搭建及常见错误解决方法
  2. APP生存法则:教你如何快速找到APP运营推广的捷径
  3. c99什么意思_C语言中“=,=,=,^=,|=”分别表示什么意思?请举例说明
  4. 设计模式之命令模式详解(附应用举例实现)
  5. 再遇淘宝造物节,一个90后的“奇市江湖”
  6. Others12_瞳距测量的方法大全
  7. $.ajax同步请求,Vue ajax 同步请求
  8. abaqus批命令使用心得
  9. java为啥要stw_【JVM 学习】ParNew 为什么要STW
  10. 【运维心得】Mysql8白名单设置