当前位置: 代码迷 >> C# >> C#串口数据接收有关问题
  详细解决方案

C#串口数据接收有关问题

热度:65   发布时间:2016-05-05 05:05:41.0
C#串口数据接收问题
我用c#编写了一个串口数据接收软件,接收的数据为16进制的6个字符,每秒一次,我软件接受到的数据中大部分是对的,但会有一部分错误,不知道什么原因,发送的数据肯定没有问题,用其他串口调试助手试过,不知道程序是哪的问题,求大神帮我看看,谢谢!

private void comm_DataReceived_1(object sender, SerialDataReceivedEventArgs e)
        {
            yanshi++;
            if (yanshi < 10) return;   //仪器的初始化
            Data_Receive.Clear();
            Thread.Sleep(100);         //读取速度太慢,加Sleep延长读取时间, 不可缺少            
            byte[] buf = new byte[6];  //声明一个临时数组存储当前来的串口数据
            received_count += 1;       //增加接收计数
            comm.Read(buf, 0, 6);      //读取缓冲数据           
            comm.DiscardInBuffer();    //清空缓存,避免下次的数据相互干扰
    }

上面是代码,请大神帮我看看,buf中的数据会不定时出现几个与发送不同的数据
------解决思路----------------------
我们更不知道了,你和上游通信,先制定好协议,然后调整串口参数,把你接收到的内容跟上游作对比,看看是接收问题还是发送问题
------解决思路----------------------
串口本来也并不保证数据一定能够正常接收到
它本身是利用电路的高低电平切换来实现通信的
TCP协议底层封装好了校验的方法,如果数据出错,数据包会被丢弃
而串口通信是一个字节一个字节发送,一个字节一个字节接收,并没有"包"的概念
需要你自己制定协议来校验什么样算一组数据,同一组数据通过什么来检测它是否完整,是否有错误

参考SUM校验,CRC校验,MODBUS RTU协议
------解决思路----------------------
引用:
我用串口调试助手接收数据都没有问题,应该不是发送的问题,应该是接收的问题,跟协议应该没有关系,请大家再帮我看看

你用串口调试助手跟踪了多长时间发现没有问题?
你的程序中不定时发生问题又是多长时间?
不要以为串口调试助手1分钟没有问题,再过5小时就都不会有问题
------解决思路----------------------
我好奇怪哦,读取的时候,很多人都是尽快的读取数据,还没有看到需要延时读取的。
------解决思路----------------------
引用:
我好奇怪哦,读取的时候,很多人都是尽快的读取数据,还没有看到需要延时读取的。

延时读取逻辑简单,不用考虑分包接包的问题
正规的做法应该是接收到数据后判断是否完整,不完整继续读取,然后自己拼接
------解决思路----------------------
  comm.DiscardInBuffer();    //清空缓存,避免下次的数据相互干扰
为什么要Discard,把这行去掉试试
------解决思路----------------------
引用:
  comm.DiscardInBuffer();    //清空缓存,避免下次的数据相互干扰
为什么要Discard,把这行去掉试试

如果楼主说收到的数据丢失了几个字节,可能是由于这个原因,否则跟它没什么关系,清不清里面也没有数据的
如果是数据错误,这个跟串口通信本身的硬件机制有关系,本来就很可能造成数据错误
------解决思路----------------------
比如串口线附近有个大电机启动了,一个强电磁干扰很可能使你的数据全部变成0xff
------解决思路----------------------

好久没来了,看到这个楼主写的那个接收方法明显有问题,comm.DiscardInBuffer();   特别是用上了这个。。。
串口发送过来的数据,有时还在缓存区,如果没达到一定的长度是不会触发DataRevive事件 此时你把他清空了,就造成你上面说的200个数据出错。那是因为它也像TCPIP通信一样,在接收的缓存区 粘包。串口数据接收到的数据,下位机有时发送6个字符过来。你的上位机在DataRecive时不一定就是6个字符,有可能是分成两次接收,先接收到4个字符,第二次是2个字符。 这是时有发生的,也就是发生了你上面的问题了,你做这个,应写一个接收字节缓冲区,专门接收字节,也不用Sleep()

看一下这个吧,http://blog.csdn.net/wyd1520/article/details/23822313
这个也是为论坛另一网友跟你提的一样的问题写的。

这是当时他提的原贴子
http://bbs.csdn.net/topics/390316188
  相关解决方案