发布于 2011-07-01 15:27:56
69楼
稍作改进,就可以实现任意位的移位(取决于背景数据块设置的大小和CPU处理能力)
有效位可以是I/Q/M/DBX.
以下程序最大处理4000个位,用CPU317-2PN测试扫描周期占用5毫秒,应该可以接受.有低端CPU的坛友可以测试一下.
FUNCTION_BLOCK "ShiftAnyBit"
TITLE =
AUTHOR : SXG
FAMILY : Shift
NAME : AnyShift
VERSION : 1.1
VAR_INPUT
X_StartBit : POINTER ; //My.z,Iy.z,Qy.z,DBx.DBXy.z and pointer can be accepted.
X_Lenght : INT ; //2 <= X_Lenght <= number of Y_Result bits
X_ShiftNumber : INT ; //0 <= X_ShiftNumber < X_Lenght
V_LeftOrRight : BOOL ; //Set it ture if Left Shift otherwise set it false
END_VAR
VAR_OUTPUT
Y_Result : ARRAY [1 .. 4000 ] OF BOOL ;
END_VAR
VAR_TEMP
L_DB_Number : WORD ; //DB number if input bit is data block bit
L_GreatestResultAddress : DINT ;
L_ShiftNumberDINT : DINT ;
L_OutputAddress : DINT ;
L_ResultAddressOffset : DINT ;
END_VAR
BEGIN
NETWORK
TITLE =
L DILG; //Get IDB's length.
SLD 3; //Convet to bits' length.
L P##Y_Result;
-I ; //Get variable Y_Result's length.
L #X_Lenght;
JC err;
L 2;
JC err;
TAK ;
L #X_ShiftNumber;
<=I ;
JC err;
L P##Y_Result;
SLD 8;
SRD 8;
T #L_ResultAddressOffset;
L #X_Lenght;
ITD ;
+D ;
T #L_GreatestResultAddress; //Greatest result address
L #X_ShiftNumber;
A #V_LeftOrRight;
JC LorR;
L #X_Lenght;
TAK ;
-I ;
LorR: ITD ;
T #L_ShiftNumberDINT;
L #L_ResultAddressOffset;
L #L_ShiftNumberDINT;
+D ;
T #L_OutputAddress;
L P##X_StartBit;
LAR1 ;
L W [AR1,P#0.0];
T #L_DB_Number;
OPN DB [#L_DB_Number];
L D [AR1,P#2.0];
LAR1 ;
L #X_Lenght;
shif: T #X_Lenght;
L #L_OutputAddress;
L #L_GreatestResultAddress;
JC m000;
L #L_OutputAddress;
L #L_GreatestResultAddress;
-D ;
L #L_ResultAddressOffset;
+D ;
T #L_OutputAddress;
m000: A [AR1,P#0.0];
= DIX [#L_OutputAddress];
L #L_OutputAddress;
L L#1;
+D ;
T #L_OutputAddress;
+AR1 P#0.1; //Next bit
L #X_Lenght;
LOOP shif;
SET ;
SAVE ;
BE ;
err: CLR ;
SAVE ;
END_FUNCTION_BLOCK
07/20/2011更新版本1.1
添加左移右移选项
与人规矩,不与人巧!