发表于:2019/10/10 23:10:02
#0楼
这两天论坛里和群里有朋友问了 程序 功能块 函数的各自的意思与区别
这里写一下我的理解.
程序好理解,就是程序嘛.要实现的工艺.逻辑关系.计算都可以在程序里面写
功能块..在之前回复的帖子里我写了
功能块 FB 可以看做"子程序"
你自己定义好的.外部输入变量..输出变量.在内部有一定的计算.逻辑关系..
能够反复调用...比如 somachine里面的那些MC_home_atv mc_pto 什么的.都属于功能块
相比较的话.和西门子200 200smart里面用的那个库 scaling 是一样的..
STEP里面是FC144 FC145那个吧.具体数我记不住了..就是比例关系..官方做好的库.直接拿来用就可以了
比如你有一个工程里面有20台水泵...
每台水泵的启停条件都一样.你就可以做一个FB
定义输入.启动.停止.高液位.低液位.手动自动.过载.
定义输出,泵启动. 泵故障
然后在FB里写逻辑关系..
然后你每次都调用这个块,把对应的输入输出写上就可以了
就不用每个泵都写一遍了
最后就是函数了
通过论坛里@weicy007 的解答...我了解到
这样我就想起之前给一个客户写过许多个功能块,其实是应该用函数来做的
应该可以节省很多内存
函数功能嘛.顾名思义.就是要用来写函数啊~~~
'****************功能函数部分***************************
'反余弦函数(参数为弧度)
Private Function ArcCos( bt : real;) : real;
ArcCos = Atn(-bt / Sqr(-bt * bt + 1)) + 2 * Atn(1)
End Function
'已知abc三边长,求a边对角角度,以弧度表示
Public Sub abc2A( a : real;, b : real;, c : real;, ByRef return_A : real;)
Dim tmpData : real;
tmpData = (b * b + c * c - a * a) / (2 * b * c)
return_A = ArcCos(tmpData)
End Sub
'获取与给定点指定距离和与X轴夹角的点
Public Sub PAD2P( X : real;, Y : real;, Angle : real;, disc : real;, ByRef returnX : real;, ByRef returnY : real;)
returnX = Cos(Angle) * disc + X
returnY = Sin(Angle) * disc + Y
End Sub
'两点间的距离
Public Sub PP2D( x1 : real;, y1 : real;, x2 : real;, y2 : real;, ByRef return_Disc : real;)
return_Disc = Sqr((x1 - x2) ^ 2 + (y1 - y2) ^ 2)
End Sub
'已知三角形顶点坐标x1,y1,x2,y2,x3,y3,求三角形外接圆半径R
Public Sub PPP2R( x1 : real; y1 : real;, x2 : real;, y2 : real;, x3 : real;, y3 : real;, ByRef Return_R : real;)
Dim a : real;, b : real;, c : real;, angA : real; '三角形三边abc和a边对角angA
Dim disc : real;
PP2D x1, y1, x2, y2, a '计算a边长
PP2D x2, y2, x3, y3, b '计算b边长
PP2D x3, y3, x1, y1, c '计算c边长
abc2A a, b, c, angA '计算A角
'计算外接圆半径
Return_R = a / Sin(angA) * 0.5
End Sub
'两点连线与X轴的夹角
Public Sub PP2A( x1 : real;, y1 : real;, x2 : real;, y2 : real;, ByRef return_Ang : real;)
Dim PI : real;
PI = Atn(1) * 4
If x1 < x2 And y1 < y2 Then '第一象限
return_Ang = Atn((y2 - y1) / (x2 - x1))
End If
If x1 = x2 And y1 < y2 Then '90度
return_Ang = 90 / 180 * PI
End If
If x1 > x2 And y1 < y2 Then '第二象限
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI
End If
If x1 > x2 And y1 = y2 Then '180度
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI
End If
If x1 > x2 And y1 > y2 Then '第三象限
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI
End If
If x1 = x2 And y1 > y2 Then '270度
return_Ang = 270 / 180 * PI
End If
If x1 < x2 And y1 > y2 Then '第四象限
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI * 2
End If
If x1 < x2 And Abs(y1 - y2) < 0.000001 Then '0度
return_Ang = Atn((y2 - y1) / (x2 - x1))
End If
End Sub
'求直线和圆的交点,Order参数为true则取的是逆时第一点坐标,Order参数为false则取的是逆时第二点坐标,以圆心为坐标系原点
Private Sub getCircleLineIntersect( CX : real;, CY : real;, r : real;, LX1 : real;, LY1 : real;, _
LX2 : real;, LY2 : real;, Order As Boolean, ByRef x_return : real;, ByRef y_return : real;)
Dim a : real;, b : real;, c : real;, D : real;, E : real;, F : real;, G : real;, H : real;, x1 : real;, y1 : real;, x2 : real;, y2 : real;
Dim ang1 : real;, ang2 : real;
If Abs(LX2 - LX1) < 0.000001 Then '直线为竖直时
x_return = LX1
y1 = (2 * CY + Sqr(4 * CY * CY - 4 * (CY * CY + (x_return - CX) * (x_return - CX) - r * r))) / 2
y2 = (2 * CY - Sqr(4 * CY * CY - 4 * (CY * CY + (x_return - CX) * (x_return - CX) - r * r))) / 2
PP2A CX, CY, x_return, y1, ang1
PP2A CX, CY, x_return, y2, ang2
If Order = True Then
If ang1 < ang2 Then
y_return = y1
Else
y_return = y2
End If
Else
If ang1 < ang2 Then
y_return = y2
Else
y_return = y1
End If
End If
Else '直线非竖直时
E = (LY2 - LY1) / (LX2 - LX1)
D = LY1 - E * LX1
F = 1 + E * E
G = 2 * CX - 2 * D * E + 2 * E * CY
H = CX * CX + D * D - 2 * CY * D + CY * CY - r * r
x1 = (G + Sqr(G * G - 4 * F * H)) / (2 * F)
x2 = (G - Sqr(G * G - 4 * F * H)) / (2 * F)
y1 = D + E * x1
y2 = D + E * x2
PP2A CX, CY, x1, y1, ang1
PP2A CX, CY, x2, y2, ang2
If Order = True Then
If ang1 < ang2 Then
x_return = x1
y_return = y1
Else
x_return = x2
y_return = y2
End If
Else
If ang1 < ang2 Then
x_return = x2
y_return = y2
Else
x_return = x1
y_return = y1
End If
End If
End If
上面这些是客户给我的函数..
我都给做到FB里面了..其实是应该做到函数里面去
调用起来更好一些.
这里写一下我的理解.
程序好理解,就是程序嘛.要实现的工艺.逻辑关系.计算都可以在程序里面写
功能块..在之前回复的帖子里我写了
功能块 FB 可以看做"子程序"
你自己定义好的.外部输入变量..输出变量.在内部有一定的计算.逻辑关系..
能够反复调用...比如 somachine里面的那些MC_home_atv mc_pto 什么的.都属于功能块
相比较的话.和西门子200 200smart里面用的那个库 scaling 是一样的..
STEP里面是FC144 FC145那个吧.具体数我记不住了..就是比例关系..官方做好的库.直接拿来用就可以了
比如你有一个工程里面有20台水泵...
每台水泵的启停条件都一样.你就可以做一个FB
定义输入.启动.停止.高液位.低液位.手动自动.过载.
定义输出,泵启动. 泵故障
然后在FB里写逻辑关系..
然后你每次都调用这个块,把对应的输入输出写上就可以了
就不用每个泵都写一遍了
最后就是函数了
通过论坛里@weicy007 的解答...我了解到
这样我就想起之前给一个客户写过许多个功能块,其实是应该用函数来做的
应该可以节省很多内存
函数功能嘛.顾名思义.就是要用来写函数啊~~~
'****************功能函数部分***************************
'反余弦函数(参数为弧度)
Private Function ArcCos( bt : real;) : real;
ArcCos = Atn(-bt / Sqr(-bt * bt + 1)) + 2 * Atn(1)
End Function
'已知abc三边长,求a边对角角度,以弧度表示
Public Sub abc2A( a : real;, b : real;, c : real;, ByRef return_A : real;)
Dim tmpData : real;
tmpData = (b * b + c * c - a * a) / (2 * b * c)
return_A = ArcCos(tmpData)
End Sub
'获取与给定点指定距离和与X轴夹角的点
Public Sub PAD2P( X : real;, Y : real;, Angle : real;, disc : real;, ByRef returnX : real;, ByRef returnY : real;)
returnX = Cos(Angle) * disc + X
returnY = Sin(Angle) * disc + Y
End Sub
'两点间的距离
Public Sub PP2D( x1 : real;, y1 : real;, x2 : real;, y2 : real;, ByRef return_Disc : real;)
return_Disc = Sqr((x1 - x2) ^ 2 + (y1 - y2) ^ 2)
End Sub
'已知三角形顶点坐标x1,y1,x2,y2,x3,y3,求三角形外接圆半径R
Public Sub PPP2R( x1 : real; y1 : real;, x2 : real;, y2 : real;, x3 : real;, y3 : real;, ByRef Return_R : real;)
Dim a : real;, b : real;, c : real;, angA : real; '三角形三边abc和a边对角angA
Dim disc : real;
PP2D x1, y1, x2, y2, a '计算a边长
PP2D x2, y2, x3, y3, b '计算b边长
PP2D x3, y3, x1, y1, c '计算c边长
abc2A a, b, c, angA '计算A角
'计算外接圆半径
Return_R = a / Sin(angA) * 0.5
End Sub
'两点连线与X轴的夹角
Public Sub PP2A( x1 : real;, y1 : real;, x2 : real;, y2 : real;, ByRef return_Ang : real;)
Dim PI : real;
PI = Atn(1) * 4
If x1 < x2 And y1 < y2 Then '第一象限
return_Ang = Atn((y2 - y1) / (x2 - x1))
End If
If x1 = x2 And y1 < y2 Then '90度
return_Ang = 90 / 180 * PI
End If
If x1 > x2 And y1 < y2 Then '第二象限
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI
End If
If x1 > x2 And y1 = y2 Then '180度
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI
End If
If x1 > x2 And y1 > y2 Then '第三象限
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI
End If
If x1 = x2 And y1 > y2 Then '270度
return_Ang = 270 / 180 * PI
End If
If x1 < x2 And y1 > y2 Then '第四象限
return_Ang = Atn((y2 - y1) / (x2 - x1)) + PI * 2
End If
If x1 < x2 And Abs(y1 - y2) < 0.000001 Then '0度
return_Ang = Atn((y2 - y1) / (x2 - x1))
End If
End Sub
'求直线和圆的交点,Order参数为true则取的是逆时第一点坐标,Order参数为false则取的是逆时第二点坐标,以圆心为坐标系原点
Private Sub getCircleLineIntersect( CX : real;, CY : real;, r : real;, LX1 : real;, LY1 : real;, _
LX2 : real;, LY2 : real;, Order As Boolean, ByRef x_return : real;, ByRef y_return : real;)
Dim a : real;, b : real;, c : real;, D : real;, E : real;, F : real;, G : real;, H : real;, x1 : real;, y1 : real;, x2 : real;, y2 : real;
Dim ang1 : real;, ang2 : real;
If Abs(LX2 - LX1) < 0.000001 Then '直线为竖直时
x_return = LX1
y1 = (2 * CY + Sqr(4 * CY * CY - 4 * (CY * CY + (x_return - CX) * (x_return - CX) - r * r))) / 2
y2 = (2 * CY - Sqr(4 * CY * CY - 4 * (CY * CY + (x_return - CX) * (x_return - CX) - r * r))) / 2
PP2A CX, CY, x_return, y1, ang1
PP2A CX, CY, x_return, y2, ang2
If Order = True Then
If ang1 < ang2 Then
y_return = y1
Else
y_return = y2
End If
Else
If ang1 < ang2 Then
y_return = y2
Else
y_return = y1
End If
End If
Else '直线非竖直时
E = (LY2 - LY1) / (LX2 - LX1)
D = LY1 - E * LX1
F = 1 + E * E
G = 2 * CX - 2 * D * E + 2 * E * CY
H = CX * CX + D * D - 2 * CY * D + CY * CY - r * r
x1 = (G + Sqr(G * G - 4 * F * H)) / (2 * F)
x2 = (G - Sqr(G * G - 4 * F * H)) / (2 * F)
y1 = D + E * x1
y2 = D + E * x2
PP2A CX, CY, x1, y1, ang1
PP2A CX, CY, x2, y2, ang2
If Order = True Then
If ang1 < ang2 Then
x_return = x1
y_return = y1
Else
x_return = x2
y_return = y2
End If
Else
If ang1 < ang2 Then
x_return = x2
y_return = y2
Else
x_return = x1
y_return = y1
End If
End If
End If
上面这些是客户给我的函数..
我都给做到FB里面了..其实是应该做到函数里面去
调用起来更好一些.
[此贴子已经被作者于2019/10/10 23:11:10编辑过]
水平一般,能力有限.如有错误之处.欢迎并感谢指出.我一定认真学习积极改正.请勿DISS.