本帖最后由 chenfanghua539 于 2020-2-26 20:42 编辑
五、强制类型转换:
将指定表达式的值转换为指定类型.形式:(类型名)(表达式) 例如:(S16)(a+b)
说明: 1)表达式应用括号括起。 例如:(S16)(x+y); (S16)(x)+y; 2)在强制类型转换时,得到一个所需类型的中间变量, 原来变量类型未发生变化。 例如: FP32 x=8.6; int y; y=(S16)(x);
右侧为将一个32位浮点数取整转换成16位整数,执行结果会把浮点数 小数点后的值丢弃转换成整数。如果要四舍五入,if(b>0) c=(S16)(b+0.5) else c=(S16)(b-0.5)即可以得到。
voidCF_2(FP32 data_b, S16 *data_c ) { S16 temp; if(data_b>0) { temp=(S16)(data_b+0.5); } else { temp=(S16)(data_b-0.5); } setS16(data_c,temp);
}
六、大小端转换问题:
由于STL系统的数据使用的是大端模式,而C语言系列使用的是小端模式,因此直接操 作指针赋值会有字节序混乱的问题,因此我们通过提供了一组通过指针从STL取值和将值写回 STL的函数,函数的具体形式在MagicWork安装目录\ccompile\include\plc300.h里头。 大端模式,是指数据的高字节保存在内存的低地址中,而数据的低字节保存在内存的高地址 中,这样的存储模式有点儿类似于把数据当作字符串顺序处理:地址由小向大增加,而数据从 高位往低位放;这和我们的阅读习惯一致。
小端模式,是指数据的高字节保存在内存的高地址中,而数据的低字节保存在内存的低地址 中,这种存储模式将地址的高低和数据位权有效地结合起来,高地址部分权值高,低地址部分权值低。
举例:参数通过指针在C系列和STL进行传递时, 由于C系统使用的是小端模式,而STL系统使用是 的大端模式,所以需要调用大小端转换接口。 voidCF_1( S16 int1, S16 int2, S16 *int3 , S16 *int4 ) { S16 int4_t; int4_t=*int3=int1+int2;
setS16(int4,int4_t);
在状态表中查看执行结果,显示成16进制,VW104没有进行大小端转换,其结果是不正确的,执行完才正常。
七、STL系统与C语言系统的数据转换操作函数: 在上述操作步骤中,已强调过输入输出和输出参数,会变成相应类型的指针,通过指针在C函数里头将结果 写回STL系统。即C函数无返回值,返回值只能通过指针传回。 加之大小端转换问题,8位、16位、32位数都需要做好转换大小端,故所有的输入输出或者输出参数都执行以 下指令把C语言的执行结果赋值到STL环境中。 void setU8( , ); //将一个U8数据,从C语言写回STL系统 void setS8( , ); //将一个S8数据,从C语言写回STL系统 void setU16( , ); //将一个U16数据,从C语言写回STL系统 void setS16( , ); //将一个S16数据,从C语言写回STL系统 void setU32( , ); //将一个U32数据,从C语言写回STL系统 void setS32( , ); //将一个S32数据,从C语言写回STL系统
void setFP32( , ); //将一个FP32数据,从C语言写回STL系统 (暂时不支持BOOL型,后续将增加,未增加之前可使用上述例程*heat=1,操作输出指针的方法!) 例如,我们要用C函数输出求出结果int4,建议先在C函数中建一个int4的中间值int4_t,待int4_t的值求出以后, 再执行setS16(int4,int4_t)输出结果到STL。 同样的,如果需要在C函数中直接调用PLC的V区、M区等寄存器,可以将PLC寄存器的指针输入给C函数,C函数块 可以通过取指针值的方式获取到PLC的内存区。 更重要的,如果输入的参数个数很多,也同可以通过指针的方式获取到。 getU8(U8 *p);从 p地址 取得一个C语言系统可用的U8数据 getS8(S8 *p);从 p地址 取得一个C语言系统可用的S8数据 getU16(U16 *p);从 p地址 取得一个C语言系统可用的U16数据 getS16(S16 *p);从 p地址 取得一个C语言系统可用的S16数据 getU32(U32* p);从 p地址 取得一个C语言系统可用的U32数据 getS32(S32* p);从 p地址 取得一个C语言系统可用的S32数据 getFP32(FP32* p);从 p地址 取得一个C语言系统可用的FP32数据
|