回复:出个题 活跃一下

t1122

  • 帖子

    73
  • 精华

    1
  • 被关注

    5

论坛等级:游士

注册时间:2011-04-14

普通 普通 如何晋级?

发布于 2011-07-21 01:17:38

49楼

这个帖子我跟着看来几天。
不得不说,识人长,方能知己短。
n次看你的背影 、老学童、伊默 、无名、火麒麟(这里排名不分先后)等都给出了具体的写法。回头再看我写的,实在汗颜。连循环都用不好,该用while的用for,水平很有限。
伊默写的超经典,即使这样还自己提出有改进的地方。无名的思路天马行空一般,还在考虑是不是可以减少循环。火麒麟指令运用的那么恰当用,可见对指令有多熟悉,可还是认真的模拟,求证。还有背影(简称了)用指针,反复改进,老学童也在小心求证。真是八仙过海各显其能啊。让我这个凡人,看到好多程序之外的东西,该学习的不仅仅是程序。
我觉得我也应该勤快一把,不能随手就写了一个循环应付了事。所以就有了这个哗众取宠的算法,不用循环,不用累加,不用条件分支,不用判断,只用逻辑运算。
在粘贴上程序之前,请允许我再犯一次懒。我这个哗众取宠的新手,真应该认真的学习西门子的库。系统自带的好多东西,我都没有学会。姑苏城外的一句话,一个系统库函数就能解决这个问题,我觉得这是一种态度。西门子本身提供了丰富的库,里面有很多方便我们写程序的sfc、sfb,学会它,掌握他才是用好西门子plc的根本。
我的这段就当一种娱乐吧,用我们自己的语言娱乐。说一下这个方法来源,时间久了,记不太清楚,好像跟某个比赛的题目类似,还有一些类似求32位左边连续0的个数等等的题目。我记得是当时临位相加来解这道题的,想了一天,才想起来。拟真已经通过,所有的情况都测试过,结果还是正确的。其实可以用stl写,不过我这水平就不献丑了。这个是用scl写的,原理都一样,就当学习scl了。

FUNCTION FC600 : INT
(*
相邻取和,结果是10进制个数。位数=位数/2。以此类推。
应该可以减少运算次数,32-16-8-4-2共5次(位数除2)。
理论上是对的。就实际情况而言,也是个哗众取宠的活。
不用循环,不用判断,不用累加,纯逻辑运算,直接得到结果。

步骤 二进制变量/16进制变量 右移位数
一 2#0101_0101_0101_0101_0101_0101_0101_0101/DW#16#55555555 shr 1
二 2#0011_0011_0011_0011_0011_0011_0011_0011/DW#16#33333333 shr 2
三 2#0000_1111_0000_1111_0000_1111_0000_1111/DW#16#F0F0F0F shr 4
四 2#0000_0000_1111_1111_0000_0000_1111_1111/DW#16#FF00FF shr 8
五 2#0000_0000_0000_0000_0000_0000_1111_1111/DW#16#FF shr 16
最后就可以直接转换为int了。
*)
VAR_INPUT
IDWord:DWORD;//输入的32位
END_VAR

VAR_IN_OUT
END_VAR

VAR_OUTPUT
END_VAR

VAR_TEMP
x:DWORD;//临时32位变量
y:DWORD;//用来简化语句的临时变量
END_VAR
x:=idword;
x:=DINT_TO_DWORD(DWORD_TO_DINT(x AND DW#16#55555555)+DWORD_TO_DINT(SHR (IN:=x, N:=1 ) AND DW#16#55555555));
x:=DINT_TO_DWORD(DWORD_TO_DINT(x AND DW#16#33333333)+DWORD_TO_DINT(SHR (IN:=x, N:=2 ) AND DW#16#33333333));
x:=DINT_TO_DWORD(DWORD_TO_DINT(x AND DW#16#F0F0F0F )+DWORD_TO_DINT(SHR (IN:=x, N:=4 ) AND DW#16#F0F0F0F ));
x:=DINT_TO_DWORD(DWORD_TO_DINT(x AND DW#16#FF00FF )+DWORD_TO_DINT(SHR (IN:=x, N:=8 ) AND DW#16#FF00FF ));
x:=DINT_TO_DWORD(DWORD_TO_DINT(x AND DW#16#FF )+DWORD_TO_DINT(SHR (IN:=x, N:=16) AND DW#16#FF ));
FC600 := DINT_TO_INT(DWORD_TO_DINT(x));

(*
scl对数据类型要求严格,来回转换好麻烦!
stl对数据类型要求不严格,应该用stl来写。
虽然不严格的东西不好读,但是好像比scl省事。
直接用stl写好了……
*)
END_FUNCTION

调用是梯形图,我不会发图,转换stl贴上来吧a

A I 4.0
JNB _004
CALL FC 600
IDWord :=MD0
RET_VAL:=MW4
_004: NOP 0
就像找找偷懒的诀窍
评论
编辑推荐: 关闭

请填写推广理由:

本版热门话题

SIMATIC S7-300/400

共有54622条技术帖

相关推荐

热门标签

相关帖子推荐

guzhang

恭喜,你发布的帖子

评为精华帖!

快扫描右侧二维码晒一晒吧!

再发帖或跟帖交流2条,就能晋升VIP啦!开启更多专属权限!

  • 分享

  • 只看
    楼主

top
您收到0封站内信:
×
×
信息提示
很抱歉!您所访问的页面不存在,或网址发生了变化,请稍后再试。