zoukankan      html  css  js  c++  java
  • 关于CRC循环冗余校验的总结(C#)

    1. 实验要求

    (1)通过CRC(循环冗余校对)序列的计算,掌握C#语言中类的静态方法与动态方法的区别。

    (2)ShellWindows Form 的通信作为扩展提高内容。

    2. 实验内容

    •  主要工作是:设计算法实现CRC序列的计算

                CRC的计算过程总结如下:

               1、  设置CRC寄存器,并给其赋值0xffff

               2、  读数据文件,并将数据的第一个8-bit字符与16CRC寄存器的低8位进行异或,并把 结果存入到CRC寄存器中。

               3、  将CRC寄存器的数据右移一位,高位补零,并检查溢出位。

               4、  如果移出位为0,重复第三步;若低位为1CRC寄存器与多项式码(此处取0xA001 即二进制1010 0000 0000 0001)相异或。

               5、  重复第3步与第4步直到8次移位全部完成。此时一个8-bit数据处理完毕。

               6、  重复第2至第5步直到所有数据所有数据全部处理完毕。

               7、  最后将寄存器的高8位数值与寄存器的低8位数值交换位置,即得到CRC的最终值。

    • 使用静态方法与动态方法,并比较区别
    • 设计windows 窗口程序

    3. 详细设计

    l 需要设计的主要内容如下:

    1) 需要设计计算一次8-bit数据的算法calculate( byte data)

    2) 使用文件输入流打开指定路径的文件,并使用readByte()方法,逐字节读入文件,调用上述calculate方法,直到文件尾;

    3) 将最终CRC计算数值,高低位换位置,并将结果转化为16进制

    l 设计好程序流程图如下:

        

    l 因此,重点为设计calculate算法:

    Calculate()代码如下:以静态方法为例

            static ushort CRC = 0xffff;

            static string result;

            // 静态函数计算CRC

            public static void calculate(byte y)

            {

                int count = 0;    // 统计移位次数

                ushort z = (ushort)(CRC ^ y);

                int temp = z;       // 移位前的数

                int temp2;

                while (count < 8)

                {

                    temp2 = temp >> 1;  // 移位后的数

                    count++;

                    if (temp2 * 2 == temp) // 溢出的为0

                    {

                        temp = temp2;

                    }

                    else  // 溢出的为1

                    {

                        temp = temp2 ^ 0xA001;

                    }

                }

                CRC = (ushort)temp;

            }

    l 剩下的只需在main 函数中打开输入文件流,并读入数据,迭代计算即可

    4. 上机实验步骤

    l 调试的过程:

    1、打开文件输出流,创建文本文件,将byte a = 02byte b = 07, 输出到该文件中,准备测试。

     

     

    2、程序调试结果为:

    多组数据验证了程序的正确性。

    5. 实验结果

    • 源程序代码如下:

    using System;

    using System.Collections.Generic;

    using System.IO;

    using System.Linq;

    using System.Text;

    using System.Threading.Tasks;

    namespace CALCULATING_CRC

    {

        class Program

        {

            static ushort CRC = 0xffff;

            static string result;

            // 静态函数计算CRC

            public static void calculate(byte y)

            {

                int count = 0;    // 统计移位次数

                ushort z = (ushort)(CRC ^ y);

                int temp = z;       // 移位前的数

                int temp2;

                while (count < 8)

                {

                    temp2 = temp >> 1;  // 移位后的数

                    count++;

                    if (temp2 * 2 == temp) // 溢出的为0

                    {

                        temp = temp2;

                    }

                    else  // 溢出的为1

                    {

                        temp = temp2 ^ 0xA001;

                    }

                }

                CRC = (ushort)temp;

            }

            // 非静态函数计算CRC

            public void calculation(byte y)

            {

                int count = 0;

                ushort z = (ushort)(CRC ^ y);

                int temp = z;       // 移位前的数

                int temp2;

                while (count < 8)

                {

                    temp2 = temp >> 1;  // 移位后的数

                    count++;

                    if (temp2 * 2 == temp) // 溢出的为0

                    {

                        temp = temp2;

                    }

                    else  // 溢出的为1

                    {

                        temp = temp2 ^ 0xA001;

                    }

                }

                CRC = (ushort)temp;

            }

            // 静态函数将10进制数转化为16进制

            public static char changeToH(ref int num1)

            {

                if (num1 > 9)

                {

                    return (char)('A' + num1 - 10);

                }

                else

                    return (char)('0' + num1);

            }

            static void Main(string[] args)

            {

                Program example = new Program();

                ushort x = 0xffff;

                Console.WriteLine("请输入打开文件的路径:");

                string filePath = Console.ReadLine();

                while(!File.Exists(@filePath))  // 打开文件失败

                {

                    Console.WriteLine("请重新输入打开文件的路径:");

                    filePath = Console.ReadLine();

                } 

                // 文件存在

                FileStream Myfile = new FileStream(filePath, FileMode.Open, FileAccess.Read);

                int readByte = 0;

                readByte = Myfile.ReadByte();

                while (readByte != -1)

                {

                    //Program.calculate((byte)readByte);   // 调用静态函数

                    example.calculation((byte)readByte);   // 调用非静态函数,需要通过对象实 例调用

                    readByte = Myfile.ReadByte();

                }

                Myfile.Close();

                int n1 = CRC % 16;

                CRC /= 16;

                int n2 = CRC % 16;

                CRC /= 16;

                int n3 = CRC % 16;

                CRC /= 16;

                int n4 = CRC % 16;

                // 交换高低位并产生CRC结果

                Program.result = (Program.changeToH(ref n2) + "" + Program.changeToH(ref n1) 

                  + "" + Program.changeToH(ref n4) + "" + Program.changeToH(ref n3));

                Console.WriteLine("CRC运算结果:" + Program.result);

            }

        }

    }

    l 控制台应用程序测试数据及结果:(打开文件test2

        

    l Windows窗口程序测试及结果:(打开文件test2

     

    6. 结论

    过程中遇到的问题:

     

    •  对与byte int short 数据类型的困惑,最后明白异或时对高位不会产生影响,因为int short而言高位补0,0不影响异或结果。
    •  看不懂题,所以百度了循环校验,好费劲
    •  可能在C#中有内置方法方便计算,由于缺乏了解,用到方法都是自己定义

    学到的东西

    •   对windows 窗体应用程序的基本结构及开发有了初步的了解
    •   关于静态方法与动态方法:

              1.静态的方法在整个应用程序其间存储在内存中,速度快,但占用内存.  

              2.动态的方法在先声明类实例才能调用类中的方法. 

              3.一般使用频繁的方法用静态方法,用的少的方法用动态的。静态的速度快,占内存。动态的速度相对慢些,但调用完后,立即释放类,可以节省内存,可以根据自己的需要选择是用动态方法还是静态方法。

  • 相关阅读:
    【纯水题】POJ 1852 Ants
    【树形DP】BZOJ 1131 Sta
    【不知道怎么分类】HDU
    【树形DP】CF 1293E Xenon's Attack on the Gangs
    【贪心算法】CF Emergency Evacuation
    【思维】UVA 11300 Spreading the Wealth
    【树形DP】NOI2003 逃学的小孩
    【树形DP】BZOJ 3829 Farmcraft
    【树形DP】JSOI BZOJ4472 salesman
    【迷宫问题】CodeForces 1292A A NEKO's Maze Game
  • 原文地址:https://www.cnblogs.com/1995hxt/p/4396177.html
Copyright © 2011-2022 走看看