Mutual conversion between float and byte between c# and microcontroller

This chapter serves as a supplement to the serial port debugging assistant and the sending and receiving of structures . It is mainly used for sending and receiving negative numbers, floating point numbers, etc. in custom protocols (the floating point numbers we used before were directly used to send and receive strings. From the string For analysis, here we mainly use hexadecimal to analyze its sending and receiving principles and usage operations).

Virtual serial port debugging assistant

Generally speaking, computer external devices can be connected to the computer through various ports. Common ones include USB, VGA, DVI, etc. In the industrial field or software development field, we often need to use a simple, low-cost and fast way to complete the connection between computers and equipment. Then the serial port is a very good choice

In the development stage, the device may not be ready yet. The PC software needs to be developed first, and then we can virtualize a serial port through the software. The entity used to replace the device. for learning use

Insert image description here
Insert image description here
One uses COM1 and the other uses COM2 to communicate.

Bytes and data conversion

c# implementation

using System.Runtime.CompilerServices;

namespace ConsoleApp1
{
    
    
    internal class Program
    {
    
    
        static void Main(string[] args)
        {
    
    

            byte[] dataByte = new byte[120];
            int count = 0;
            //将double型数据存入databyte中。
            double data1 = -123.125;
            //C# BitConverter 类用来字节数组转换 可以转换成字节 也可以字节转换成int、double等
            byte[] buf = BitConverter.GetBytes((double)data1);//单精度浮点型用 BitConverter.ToSingle
            Console.WriteLine(BitConverter.ToDouble(buf));
        }
    }
}

Insert image description here

c implementation

#include <stdio.h>


/*
*function:ftoc(float fvalue,unsigned char*arr)
*decription:  浮点数转化成四个字节
*input: 浮点数 
*output: 4个字节的字节数组
*/
//例如12.5--0x41 48 00 00;转换完之后,arr[0]-00,arr[1]-00,arr[2]-48,arr[3]-41
void ftoc(float fvalue,unsigned char*arr) 
{
    
    
    unsigned char  *pf;
    unsigned char *px;
    unsigned char i;   //计数器 
    pf =(unsigned char *)&fvalue;            /*unsigned char型指针取得浮点数的首地址*/  
    px = arr;                               /*字符数组arr准备存储浮点数的四个字节,px指针指向字节数组arr*/

    for(i=0;i<4;i++)
    {
    
    
        *(px+i)=*(pf+i);     /*使用unsigned char型指针从低地址一个字节一个字节取出*/
    }
}

/* 
*function:float ByteToFloat(unsigned char* byteArray) 
*decription:  将字节型转化成32bits浮点型 
*input:       长度为4的字节数组 
*output: 
*/  
float ByteToFloat(unsigned char* byteArray)  
{
    
      
    return *((float*)byteArray);  //强制类型转换 然后取值 
}  

int main(int argc, char *argv[])
{
    
    

    int i;
    unsigned char byteArray[4];
    ftoc(-12.5,byteArray);//浮点数转化成四个字节 

    for(i=0;i<4;i++)
        printf("%x  ",byteArray[i]);//%x即按十六进制输出,英文字母小写,右对齐

    float x=0;
    x = ByteToFloat(byteArray);
    printf("\n%f  ",x);
    return 0;
}

Insert image description here

practice

With serial port debugging assistant

The first two bytes, the last one byte, and the intermediate data are 4 bytes. The single-precision 4 bytes converted from the C language can be seen in the C implementation above.
Insert image description here

        public static int cnt = 0;
        private void serialPort1_DataReceived2(object sender, System.IO.Ports.SerialDataReceivedEventArgs e)
        {
    
    
            cnt++;
            this.Invoke((EventHandler)delegate
            {
    
    
                uiRichTextBox1.AppendText("\r\n" + "cnt:" + cnt);
            });
            Thread.Sleep(40);

            int len = serialPort1.BytesToRead;//一共接收到多少数据
            Byte[] readBuffer = new Byte[100];
            serialPort1.Read(readBuffer, 0, len);

            //2+4+1  80 81  0 0 48 c1 ff   就是-12.5
            //获得一帧掐头去尾的数据
            for (int ptr = 0; ptr < len; ptr++)
            {
    
    
                if ((readBuffer[ptr] == HEAD1) && (readBuffer[ptr + 1] == HEAD2))
                {
    
    
                    if (readBuffer[ptr + 6] == 0xff)
                    {
    
    
                        int index = ptr + 2;
                        byte[] fdata = new byte[4];
                        for (int i = 0; i < 4; i++)//这样就把尾巴给去掉了
                        {
    
    
                            fdata[i] = readBuffer[index + i];
                        }
                        this.Invoke((EventHandler)delegate
                        {
    
    
                            uiRichTextBox1.AppendText("\r\n" + "接收数据值:" + BitConverter.ToSingle(fdata,0).ToString());
                        });

                    }

                }
            }
        }

c# receives floating point data

Insert image description here
What is received is two bytes ushort

//直接调用ReadDate函数,接收到的数据会自动保存入 ushort[] value1 中
//一个ushort占用两个字节,一共接收到2个ushort,共四个字节
//调用GetFloat即可实现转换
        public static void ReadDate()
        {
    
    
                ushort startAddress = 0x0066;
                ushort numberOfPoints = 2;
                ushort[] value1 = master.ReadHoldingRegisters(1, startAddress, numberOfPoints);
                log.SaveLog("value1字节数:"+value1.Length.ToString());

                float valuefloat;
                valuefloat = GetFloat(value1[0], value1[1]);

                log.SaveLog("流量" + valuefloat);
            
        }
        
        public static float GetFloat(ushort P1, ushort P2)
        {
    
    
            int intSign, intSignRest, intExponent, intExponentRest;
            float faResult, faDigit;
            intSign = P1 / 32768;
            intSignRest = P1 % 32768;
            intExponent = intSignRest / 128;
            intExponentRest = intSignRest % 128;
            faDigit = (float)(intExponentRest * 65536 + P2) / 8388608;
            faResult = (float)Math.Pow(-1, intSign) * (float)Math.Pow(2, intExponent - 127) * (faDigit + 1);
            return faResult;
        }

Insert image description here

Guess you like

Origin blog.csdn.net/chengcao123/article/details/131513755