- 浏览: 220284 次
- 性别:
- 来自: 北京
-
最新评论
-
LinApex:
请使用js好吗?
利用开发框架中的标签库集成报表工具 -
qiu768:
博主你们是直接用jquerymobile+phonegap实现 ...
工作流软件管理系统移动客户端的开发 -
shige19:
流程与业务表单的关联:流程->任务->表单
aspx页面集成工作流引擎api -
shige19:
工作流中集成页面:1 流程环节绑定页面url;2 页面处理中调 ...
工作流集成第三方aspx页面 -
shige19:
流程关联多单据:1 多单据只是针对主从表情况;2 单据与流程的 ...
工作流集成表单之多张单据和一张单据
工作流系统的自由流实现了不按照流程预定义的轨迹流转,即需要在节点之间任意的跳转。上一篇自由流的实现主要说明了跳转规律,如果是单节点间的跳转,只要有当前的节点,以及跳转到的节点,就ok了。但是当当前节点和任意跳转到的节点之间有分支并发线路后,就不是简单的跳转了,当分支套分支,分支主干等之间的跳转就更复杂了。
如果是这种串行路由,就很简单了。
但是这样的多路分支,分支嵌套分支的,就很复杂了。
因此在实现的时候,必需找出,当前节点到跳转到的节点之间的轨迹线路。又因为分支之间是可以嵌套的,所以必需用递归来遍历这之间的轨迹。
由当前节点开始,查找这个节点的动作结果节点是否为跳转到的节点,如果是,则找到之间的轨迹,返回。
如果不是,则将当前这个节点的动作结果节点作为当前节点,继续调用这个函数,查找,直到找到后退出。
因为流程定义的轨迹,可以是循环的轨迹,即一个节点的动作结果可以返回到前面的节点,如:
当返回到前面的节点时,用递归调用的话,就永远也退不出循环了。因此,将处理过的节点放到traceNodeList中,每次调用递归函数前,均判断一下,此节点是否在traceNodeList中,如果在,就不用处理了。不在的继续处理。
eworkflow自定义工作流系统有.net版和java版,两个版本的实现过程完全一样,只是一个是c#语言的一个是java语言的。
c#的递归函数:
private ArrayList getJoinsAndSplitsBwteenStep(WorkflowDescriptor wd,IDictionary orgNodeMap,ResultDescriptor theResult,ArrayList traceNodeList)
{
ArrayList tagList = new ArrayList();
string nodeType =(System.String)orgNodeMap["node_type"];
AbstractDescriptor node = (AbstractDescriptor)orgNodeMap["node"];
ArrayList results = new ArrayList();
if (nodeType.Equals("join"))
{
JoinDescriptor join = (JoinDescriptor)node;
results.Add(join.Result);
}
if (nodeType.Equals("split"))
{
SplitDescriptor split = (SplitDescriptor)node;
results.AddRange(split.Results);
}
if (nodeType.Equals("subflow"))
{
SubflowDescriptor subflow = (SubflowDescriptor)node;
results.Add(subflow.unconditionalResult);
results.AddRange(subflow.conditionalResults);
}
if (nodeType.Equals("step"))
{
StepDescriptor step = (StepDescriptor)node;
ArrayList actions = step.actions;
for (IEnumerator iter = actions.GetEnumerator();iter.MoveNext();)
{
ActionDescriptor action =(ActionDescriptor)iter.Current;
ResultDescriptor result = action.UnconditionalResult;
results.Add(result);
results.AddRange(action.ConditionalResults);
}
}
bool bFind=false;
for (IEnumerator it = results.GetEnumerator();it.MoveNext();)
{
ResultDescriptor result = (ResultDescriptor)it.Current;
if (result.Id==theResult.Id)
{//找到跳转到的节点,退出
bFind = true;
break;
}
}
if (bFind) return tagList;
//将当前处理节点 存入traceNodeList中
traceNodeList.Add(node);
for (IEnumerator iterator = results.GetEnumerator();iterator.MoveNext();)
{
ResultDescriptor resultDesc = (ResultDescriptor)iterator.Current;
int joinid = resultDesc.join;
int splitid = resultDesc.Split;
int stepid = resultDesc.Step;
int subflowid = resultDesc.subflow;
int traceid = 0;
IDictionary orgMap = new Hashtable();//记录节点信息
if (joinid>0)
{
IDictionary m = new Hashtable();
m["join"] = joinid;//new Integer(joinid);
tagList.Add(m);
JoinDescriptor join = wd.getJoin(joinid);
orgMap["node_type"] = "join";
orgMap["node"] = join;
traceid = joinid;
}
if (splitid>0)
{
SplitDescriptor split = wd.getSplit(splitid);
orgMap["node_type"] = "split";
orgMap["node"] = split;
IDictionary m = new Hashtable();
m["split"] = splitid;// new Integer(splitid));
for (int i=0;i<split.Results.Count;i++)
{
tagList.Add(m);
}
traceid = splitid;
}
if (stepid>0)
{
StepDescriptor step = wd.getStep(stepid);
orgMap["node_type"] = "step";
orgMap["node"] = step;
traceid = stepid;
}
if (subflowid>0)
{
SubflowDescriptor subflow = wd.getSubflow(subflowid);
orgMap["node_type"] = "subflow";
orgMap["node"] = subflow;
traceid = subflowid;
}
//判断 关联到的节点 是否处理过
bool inTrace = false;
for (IEnumerator itrace=traceNodeList.GetEnumerator();itrace.MoveNext();)
{
AbstractDescriptor trace = (AbstractDescriptor)itrace.Current;
if (trace.Id==traceid)
{//已经处理过的了
inTrace = true;
break;
}
}
if (!inTrace)
tagList.AddRange(getJoinsAndSplitsBwteenStep(wd,orgMap,theResult,traceNodeList));
}
return tagList;
java的递归函数:
private List getJoinsAndSplitsBwteenStep(WorkflowDescriptor wd,Map orgNodeMap,ResultDescriptor theResult,List traceNodeList) throws WorkflowException{
List tagList =new ArrayList();
String nodeType =(String)orgNodeMap.get("node_type");
AbstractDescriptor node = (AbstractDescriptor)orgNodeMap.get("node");
List results = new ArrayList();
if (nodeType.equals("join")){
JoinDescriptor join = (JoinDescriptor)node;
results.add(join.getResult());
}
if (nodeType.equals("split")){
SplitDescriptor split = (SplitDescriptor)node;
results.addAll(split.getResults());
}
if (nodeType.equals("subflow")){
SubflowDescriptor subflow = (SubflowDescriptor)node;
results.add(subflow.getUnconditionalResult());
results.addAll(subflow.getConditionalResults());
}
if (nodeType.equals("step")){
StepDescriptor step = (StepDescriptor)node;
List actions = step.getActions();
for (Iterator iter = actions.iterator();iter.hasNext();){
ActionDescriptor action =(ActionDescriptor)iter.next();
ResultDescriptor result = action.getUnconditionalResult();
results.add(result);
results.addAll(action.getConditionalResults());
}
}
boolean bFind=false;
for (Iterator it = results.iterator();it.hasNext();){
ResultDescriptor result = (ResultDescriptor)it.next();
if (result.getId()==theResult.getId()){//找到跳转到的节点,退出
bFind = true;
break;
//return tagList;
}
}
if (bFind) return tagList;
//将当前处理节点 存入traceNodeList中
traceNodeList.add(node);
for (Iterator iterator = results.iterator();iterator.hasNext();){
ResultDescriptor resultDesc = (ResultDescriptor)iterator.next();
int joinid = resultDesc.getJoin();
int splitid = resultDesc.getSplit();
int stepid = resultDesc.getStep();
int subflowid = resultDesc.getSubflow();
int traceid = 0;
Map orgMap = new HashMap();//记录节点信息
if (joinid>0){
Map m = new HashMap();
m.put("join", new Integer(joinid));
tagList.add(m);
JoinDescriptor join = wd.getJoin(joinid);
orgMap.put("node_type", "join");
orgMap.put("node", join);
traceid = joinid;
}
if (splitid>0){
SplitDescriptor split = wd.getSplit(splitid);
orgMap.put("node_type", "split");
orgMap.put("node", split);
Map m = new HashMap();
m.put("split", new Integer(splitid));
//tagList.add(m);
for (int i=0;i<split.getResults().size();i++){
tagList.add(m);
}
traceid = splitid;
}
if (stepid>0){
StepDescriptor step = wd.getStep(stepid);
orgMap.put("node_type", "step");
orgMap.put("node", step);
traceid = stepid;
}
if (subflowid>0){
SubflowDescriptor subflow = wd.getSubflow(subflowid);
orgMap.put("node_type", "subflow");
orgMap.put("node", subflow);
traceid = subflowid;
}
//判断 关联到的节点 是否处理过
boolean inTrace = false;
for (Iterator itrace=traceNodeList.iterator();itrace.hasNext();){
AbstractDescriptor trace = (AbstractDescriptor)itrace.next();
if (trace.getId()==traceid){//已经处理过的了
inTrace = true;
break;
}
}
if (!inTrace)
tagList.addAll(getJoinsAndSplitsBwteenStep(wd,orgMap,theResult,traceNodeList));
}
return tagList;
}
欢迎大家多提改进意见,或者有更好的解决方案共享 ^_^
<script type="text/javascript"></script>
发表评论
-
工作流之设置表访问权限
2015-01-19 20:34 1909在工作流管理系统中,工作流引擎负责流程的流转。首先梳理业务, ... -
工作流之设置表访问权限
2015-01-19 20:34 988在工作流管理系统中,工作流引擎负责流程的流转。首先梳理业务, ... -
利用工作流返回达到无限次重复办理业务的过程
2015-01-04 14:21 1224在和客户的交流中,有客户提出有这样的业务流程: 申 ... -
eworkflow工作流系统在iis中发布
2014-12-22 14:40 956eworkflow工作流系统在iis中发布 win7下面 ... -
IE8用ajax访问不能每次都刷新的问题
2014-07-10 18:36 616最近发现,用ajax访问后台,用ie8访问,第一次可以正常返 ... -
视频演示(动态指定执行人+指定申请人的上级)
2014-07-10 12:05 1405视频演示下载地址 获取申请人的上级: http://p ... -
eworkflow集成定制aspx页面的过程
2014-07-09 16:23 1112eworkflow自定义工作流系统,集成eform自定义表 ... -
java项目开发框架
2014-07-07 11:37 712做项目的时候,最需要快速开发框架来辅助。好的快速安全的开发 ... -
利用开发框架中的标签库集成报表工具
2014-06-22 10:22 1415在项目开发中,完成数据录入后,统计分析报表是必定要出的,后 ... -
流程设计器之标签工具
2014-06-20 11:17 1561流程设计器之标签工具 工作流系统中,各种路由节点,顺序流 ... -
简单设置eworkflow条件的方式
2014-01-03 11:46 1204在eworkflow自定义工作流产品中,设置条件节点,是在 ... -
流程多节点调用同一张业务表单的锚点问题
2013-11-19 19:56 1211在工作流的实施中,经常会有客户提出,一个业务流程中,同一张业 ... -
java工作流软件发送邮件的方案
2013-11-01 17:03 1283利用javamail的功能将发送邮件的功能集成到java工作 ... -
工作流软件是未来web的支柱
2013-10-30 17:13 946Web 3.0正在敲门,但是 ... -
自定义表单中多附件上传控件的实现方案
2013-10-25 11:53 1434多附件上传的功能,在我们开发系统的时候经常会需要,客户的需求 ... -
流程节点中发送邮件的解决方案
2013-10-15 18:14 1024在流程引擎中,需要 ... -
财务报销流程
2013-09-11 12:33 1862给客户做的财务报销流程示例说明文档: 业务介绍 ... -
tomcat6配置jndi连接数据库的方式
2013-08-26 10:31 801eworkflow工作流+eform表单+ebiao报表集 ... -
动态获取当前执行人或指定步骤执行人的上级
2013-08-14 10:27 1339流程在一个业务节点办理完成后,到达下一个节点,产生下一个节 ... -
流程节点多场景多表单
2013-07-27 13:51 981工作流的流转,每一个办理过程就是一个流程节点,实际办理业务 ...
相关推荐
对于开发者而言,掌握NetBpm的源代码意味着可以更自由地定制工作流功能,例如,添加新的流程节点类型,改进现有的任务分配算法,或者增强系统的监控和报告功能。通过这种方式,开发者可以打造出更加贴近实际业务场景...
开源工作流系统 JWFD 是一个基于开放源代码的流程自动化工具,旨在帮助企业或组织实现高效、灵活的工作流程管理。在本文中,我们将深入探讨 JWFD 的核心特性、工作原理、优势以及如何使用它来优化业务流程。 一、...
Java工作流定义(JWFD)是一个开源的工作流管理系统,专门设计用于在Java环境中实现灵活、可扩展和高效的工作流程自动化。该系统的核心理念是提供一个强大而易用的框架,帮助开发者快速构建符合业务需求的工作流程...
在实际应用中,"基于工作流网的过程挖掘算法.nh"这个文件可能包含了具体实现这些算法的代码、数据结构、实验结果和案例分析等。深入理解和掌握这些内容,对于从事工作流管理、业务流程优化或相关IT领域的专业人士来...
### jBPM详解_工作流管理系统详细文档 #### 一、jBPM入门简介与重要性 ##### 1.1 概述 jBPM,全称为Java Business Process Management(业务流程管理),是一款开放源码的业务流程管理、工作流管理和服务协作领域...
3. **工作流执行**:生成的Java代码可以直接运行,实现设计的工作流。Flow4j支持动态执行和调试,使得测试和优化流程变得更加便捷。 4. **可扩展性**:Flow4j具有良好的扩展性,允许开发者添加自定义的活动节点,以...
这个工具的独特之处在于它提供了一个管理器和设计器,使得工作流的创建、管理和监控变得更加直观和便捷。在.NET开发领域,工作流引擎常用于构建复杂的业务流程,将一系列任务按特定顺序组织起来,实现自动化处理。 ...
《Anderson CFD 代码 MATLAB》是一份专注于计算流体力学(CFD)的资源,它包含基于MATLAB语言实现的代码示例。这些代码源于Anderson的知名书籍,为读者提供了深入理解和应用CFD理论的实际操作平台。MATLAB作为一种...
3. **工作流引擎**:OA的核心组件之一是工作流引擎,它负责定义、执行和监控业务流程,自动化审批流程。 4. **文档管理**:强大的文档管理系统是OA的重要组成部分,它应支持多种格式的文件存储、版本控制、预览和...
通过Apache许可证v.2.0,Docflow遵循开源原则,允许自由使用、修改和分发源代码,鼓励社区参与开发和改进。 综上所述,Docflow是一个使用C#和Windows Workflow Foundation构建的简单工作流系统,旨在简化组织内部的...
2. 工作流引擎:工作流引擎是一种软件系统,它负责执行定义好的工作流程,包括任务分配、状态转移和审批流程等。FlowDesigner的工作流引擎允许用户以可视化的方式设计这些流程,然后将它们转换为可执行的逻辑。 3. ...
6. **流程审批**:BMS支持自定义工作流,用户可以根据业务需求创建和配置审批流程,如请假申请、报销审批等,自动化处理日常事务,减少人为错误。 7. **数据管理**:系统需要具备强大的数据管理能力,包括数据存储...
【标题】"JWFD开源工作流"涉及的是一个最新的实时编译器,该编译器具有对三角函数的支持。这表明它可能是一个专为处理数学计算和算法优化的编程工具,尤其适合需要进行大量科学计算或者图形处理的场景。在IT领域,...
经过对60个节点和105个连接的流程图test119的矩阵数据的测试,发现,目前这个算法还存在问题,还需要改进和升级,暂时修改一下计划在JG的设计器的基础上,把矩阵引擎这块继续完善下去,不着急做自己的设计器,把引擎...
雷神的H.264码流分析器是一款开源软件,这意味着其源代码对公众开放,用户可以自由查看、学习和改进。开源软件的一大优势在于促进技术交流与创新,用户可以根据自己的需求对其进行定制,或者参考其设计思路解决类似...
数据库则用于存储系统数据,如用户信息、工作流、文档等。 在功能方面,信呼OA系统涵盖了企业日常办公的多个关键模块。例如,它提供了人事管理,包括员工档案、考勤记录、薪资福利等功能,帮助企业管理员工信息;...
同时,它支持与数据库、Web服务和其他系统集成,实现了工作流与其他业务系统的协同工作,进一步提升了工作效率。 标签"C#FlowAddFlow"表明这个压缩包包含了与C#语言、工作流(Flow)和Lassalle AddFlow相关的资源。...
Notepad++是一款非常受欢迎的免费源代码编辑器,尤其在编程社区中被广泛使用。它基于Windows操作系统,支持多种编程语言,并且具有丰富的自定义功能。2017年3月25日的Notepad++源代码更新是该软件发展历史上的一个...
该系统架构通常由七个子系统构成,包括用户管理子系统、文件管理子系统、邮件管理子系统、日程安排子系统、通讯录管理子系统、会议管理子系统和信息发布子系统等,每个子系统都具有不同的功能和作用。例如,用户管理...
"全新开源版本二开IPTV管理系统源码" 文件名直接对应了整个项目的源代码,包含了系统的核心逻辑和结构,开发者可以通过阅读和修改这些代码来理解系统的工作原理,实现定制化需求。 **详细知识点** 1. **IPTV技术**...