找回密码
 开放注册
搜索
查看: 488|回复: 10

万能的避难所啊!

[复制链接]
发表于 2011-7-3 09:55:49 | 显示全部楼层 |阅读模式
难民我再次请求援助:

是关于编程的。

一个工控机上有4个通道,分别为通道1,2,3,4,这4个通道有可能是4个都在工作,也有可能只有通道4工作,也有可能1,2,3,也有可能2,4,等等,虽然说可以一一列举(用if 或者 case)并编写各种情况,但过程繁琐,请问有什么更好的方式来判断4个通道的工作情况吗?
发表于 2011-7-3 10:47:10 | 显示全部楼层
语言很久没碰了,都忘了差不多了。是不是可以把每个通道自己判断是否工作,然后统一汇总呢。这样就不需要那么麻烦了。
发表于 2011-7-3 11:11:33 | 显示全部楼层
太简单了,用switch...case(我说的是JAVA,不过任何语言应该都有类似语句块,只是语法略有不同)
具体的语法我也忘了,好久不碰,但思路是:
用逻辑判断语句块(像一个等式,很短的那个)判断每个机器是否工作,然后取特定的数字,4个数字相加,根据和的不同来判断工作情况
写法为:
(判断1号是否工作,是则为1,否则为0)+(判断2号是否工作,是则为3,否则为0)+(判断2号是否工作,是则为6,否则为0)+(判断2号是否工作,是则为11,否则为0)=最后的和
和=0 则4台都没工作
和=1+3+6+11=21 则4台皆工作
和=7 则1、3号工作
和=14 则2、4号工作
等等,依次类推,根据和的不同而不同,你要做的只是加减乘除而已
这个思路的关键是括号中判断语句块的取值,不能取相加会重复的数,比如设为1、3、6、10的话,那么1、2、3号都工作和只有4号工作的情况将无法辨别(因为最后和都等于10)
发表于 2011-7-3 12:53:43 | 显示全部楼层
位运算
用二进制后4位表示4个通道的工作情况
即 (1)2 (10)2  (100)2  (1000)2
对应于10进制,即为  (1)10  (2)10 (4)10 (8)10
取根据工作状态取其和相加得到A

以第三个通道为例(  (100)2 == (4)10 )任何时候
1)   A & 4 !=0 即表示通道开启
2)  A=A-A&4 无论通道状态如何,关闭通道
3)   A=A | 4 无论通道状态如何,开启通道


最后未必是2进制,如果一个通道有N个状态,就使用N进制就好了


接上,豆子的最后一句话的意思是要选取表示这4个通道状态的一组基,某这个方法无非是要求求一组正交基,取正交基的好处就是可以很方便的对一个坐标轴分量进行分离而不必影响其他坐标轴分量而已- -
在计算机中的好处,嗯,能用位运算提升运算速度罢了= =
发表于 2011-7-3 13:07:56 | 显示全部楼层
豆子的思路很好, 不过仅限于类似4个数位组合的情况, 一旦数位增多, 姜饼小人怀疑数学上是否可行, 毕竟要找到那么多特征数字.

还有一种方法就是用矩阵:

比如说你有三种情况要执行命令A:
1001
0100
0110

首先将所有情况做成一个矩阵:
| 100 |
| 011 | = M
| 001 |
| 100 |

然后对于任意输入, 例如 I = 1000
先取反:  0111
然后和矩阵cross product:

{0111} X  | 100 |
                 | 011 |
                 | 001 |
                 | 100 |

然后写一个简单方程:
  1. int Test ( array X)
  2. {
  3.      int count=0;
  4.      int n=-1;
  5.      for(i=0, i<=size(X); i++)
  6.           {
  7.                 if (X[i]==0)
  8.                        count++;
  9.                        n=i;
  10.           };
  11.       if (count == 1)
  12.           return (n);
  13.       else
  14.           return(-1);
  15. }
复制代码



之前的cross运算结果是一个3位的array, 这个test方程只返回运算结果有且只有一个0那一位的序号, 如果是条件内的数列, 比如说1001, 结果是{012}, 那么方程返回 1.

结果只有一个0, 说明输入值与一种条件1的位置一致, 比如如果返回{012}, 说明输入是1XX1, 之后我们只需利用n的值(1), 来确认其他数位即可, M( * , n) 就是对应 0 的那个数列, 只要判断条件 M(*,n) (dot product) M(*,n) == I (dot product) I, 即1001 dot 1001 == 1XX1 dot 1XX1, 如果点乘结果相同说明输入值与1001有相同数量的1, 1XX1 -> 1001, 确认符合条件, 如果不相等, 说明1的数量不相等, 比如 1101或 1011.

这个算法可以避开繁琐的if判断, 便于修改维护(只需修改每个条件集的矩阵), 并且不限制输入数位的长度, 即使是100位的01序列也是一样的, 另外最好每种操作对应一个比较大的条件集, 如果每种组合对应一种操作, 其实跟用if写也没什么区别....

 楼主| 发表于 2011-7-3 22:37:52 | 显示全部楼层
所以我说万能的避难所

深藏不露的高手都是。。。

谢啦
发表于 2011-7-4 01:23:02 | 显示全部楼层
死宅理科男
发表于 2011-7-5 05:38:34 | 显示全部楼层
所里藏龙卧虎,不是干这个的,表示看不懂
发表于 2011-7-5 08:06:42 | 显示全部楼层
- -编程最后还是放弃了,好枯燥啊~还是关心我的面团去。。。
发表于 2011-7-5 13:54:05 | 显示全部楼层
老牛觉得自己变成了文盲..
发表于 2011-7-6 02:05:37 | 显示全部楼层
昨天晚上做梦发现我上面的算法有个TMD漏洞, 有奖竞答, 瓶盖100.
您需要登录后才可以回帖 登录 | 开放注册

本版积分规则

Archiver|手机版|小黑屋|13号避难所-旧人类论坛

GMT+8, 2026-6-8 16:28 , Processed in 0.079116 second(s), 15 queries .

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表