神要保佑善良的人
有些话,适合烂在心里;有些痛苦,适合无声无息的忘记
关于policyActivity这篇文章,是基于

http://www.microsoft.com/china/MSDN/library/Windev/WindowsVista/intWF_FndRlsEng.mspx?mfr=true

写的,对其示范的例子进行了一些改动和完善。

 开发人员使用规则条件 (Rule Condition) 取代代码条件 (Code Condition) 的主要原因是,规则条件成为模型的组成部分并且可在运行时在正在执行的工作流实例上动态更新。规则条件的第二个优势是,作为模型的组成部分,更复杂的工具可构建到模型的顶层,从而提供额外的创作体验、依赖性管理、交叉条件分析等。

 PolicyActivity

策略活动封装 RuleSet 的定义和执行。RuleSet 是一个带有一组执行语义的规则集合。而规则是对工作流成员进行操作的 If-Then-Else 表达式。实际操作如图 2 所示,类似于规则条件中所示。

 添加PolicyActivity

要为策略活动配置一个规则集,请执行以下步骤:

?

将策略活动从工具箱拖到工作流设计器上。

?

在 RuleSetReference 中,为 RuleSet 指定一个名称。

?

选择椭圆形中的 RuleSet Definition 字段,启动 Rule Set Editor。

?

该编辑器在列表框中显示规则的集合。

?

选择一个给定的规则可以显示其 Condition、Then 操作、Else 操作以及一组其他属性。

?

和 Rule Condition Editor 中一样,Condition、Then 操作和 Else 操作均以文本方式输入,然后解析为相关联的对象模型表示形式;根据工作流上的成员生成规则。

?

选择 OK,你会发现工作流又多了个文件,workflow3.rules,这个文件就是将 RuleSet 序列化得到的

注意,选择椭圆形中的 RuleSetReference 属性将启动编辑器,从而使用户能选择一个现有的 RuleSet 或添加/重命名/删除 RuleSet,如图 3 所示。

 PolicyActivity的规则计算

RuleSet 中的每个规则都有一个优先级值,默认值为 0。可将 RuleSet 中的规则看作一个按优先级值排列的有序集合。WF 规则计算器分别计算规则,根据规则的条件计算结果执行规则的操作。

计算机制在概念上可以用以下过程描述:

?

首先,列出活动的规则。

?

找到优先级最高的规则。

?

计算规则并根据需要执行其 Then/Else 操作。

?

如果一个规则的操作更新了列表中前面的某条规则(该规则具有较高的优先级)使用的字段/属性,则重新计算前面这条规则并根据需要执行其操作。注意,只有那些具有特定依赖性的规则才需要重新计算。

?

继续该过程,直至 RuleSet 中的所有规则均已计算完毕。

我们来看一个简单的示例。假定有以下 RuleSet,其中 A、B 等代表工作流上的数据。

Rule4 (Priority = 4)

IF A = 15 THEN B = 5

Rule3 (P=3)

IF C = 5THEN B = 10

Rule2 (P=2)

IF D = 2 THEN A = 15

Rule1 (P=1)

IF B = 5 THEN E = 7

假定有以下输入数据:

?

A = 0  B=0 C=5 D=2 E=0

计算将按以下方式进行:

?

计算 Rule4;其计算结果为 false,由于 Rule4 没有 Else 操作,因此不执行任何操作。

?

Rule3 的计算结果为 true,执行其操作,设置 B = 10。Rule4 不依赖于 B 的值,因此进行 Rule2 的计算。

?

Rule2 的计算结果为 true,执行其操作,设置 A = 15。

?

由于 Rule4 在其条件中使用 A 的值,因此要重新计算 Rule4。Rule4 的计算结果为 true,执行其操作,设置 B = 5;由于 Rule3 和 Rule2 的条件不依赖 A 的值,因此它们不用重新计算。由于前面的值都不依赖于 B 的值,因此进行 Rule1 的计算。

?

Rule1 的计算结果为 true,执行其操作,设置 E = 7。

结果数据集应该如下所示:

?

A = 15 B=5 C=5 D=2 E=7

 

 

在这里,我们做一个这样的例子,来理解一个关于policy更多的东西。

 运用policy设计一个工作流,实现一个这样的例子,在购物的过程中,如果金额大于1000,就打半折,如果这个客户还是老客户,那么在这个基础上再打半折,最后算出最后应付的金额。



流程设计很简单:一个policyActivity 和一个codeActivity来输出结果。

这里我们还要设计一个界面来输入金额和客户类别,并将这两个参数传入工作流中。

首先,我们定义一个实体类:Order来对这支交易时行描述:

 

 public class Order

    {

       

/// <summary>

        ///打折度

        /// </summary>

    private double discount;

        public double Discount

        {

            get { return discount; }

            set { discount = ; }

        }

   /// <summary>

        ///客户类型

        /// </summary>

        private string customerType;

        public string CustomerType

        {

            get { return customerType; }

            set { customerType = ; }

        }

    }

而在workflow中,我们要定义以下变量

      /// <summary>

        /// 消费总数

        /// </summary>

        private double subtotal;

        public double Subtotal

        {

            get { return subtotal; }

            set { subtotal = ; }

        }

 

        /// <summary>

        /// 消费者分类

        /// </summary>

        private string customerType;

        public string CustomerType

        {

            get { return this.disCountOrder.CustomerType; }

            set { this.disCountOrder.CustomerType = ; }

        }

 

        /// <summary>

        /// 最后应付金额

        /// </summary>

        private double total;

 

重要的是在工作流我们定义这个规则:

Rule1中,我们将优先级设为2(最高,首先执行),conditiion设为:this.subtotal > 1000,检测金额是否超过了1000,action中我们设置折扣:this.discountOrder.Discount = 0.5,

 

Rule2中,我们将优先级设为1(其次),conditiion设为:this.disCountOrder.Discount > 0,检测是否打了折扣,action中我们计算第一次结果:this.total = (1 - this.disCountOrder.Discount) * this.subtotal

 

Rule3中,我们将优先级设为0(其次),conditiion设为:this.disCountOrder.CustomerType == "laoguke",检测客户类别,action中我们计算最后结果:this.total = (1 - this.disCountOrder.Discount) * this.subtotal * 0.5

 

可以看出:

引擎将计算规则,识别 Rule 1是否满足条件,Rule 2 在 Rule 1 上有一个依赖项;结果是引擎将确保每次 Rule 1 执行其 Then 操作时,都会对 Rule 2 进行计算/重新计算。

然而,Rule 3 在 Rule 1 和 Rule 2 上没有依赖项,因此它不更新 CustomerType 属性。换言之,依赖项在 CustomerType 属性级别进行识别,而不是由 Order 对象本身识别

 

最后执行结果:

 

 

在查资料的时候他是这种说的

 

链接基于规则中已识别的依赖项;更具体地说,就是一个规则的操作和其他规则的条件之间的依赖项。这些依赖项可通过以下方式识别或声明:隐式、基于属性、显式。

 

隐式

隐式依赖项由引擎自动识别。第一次执行某个 RuleSet 时,分析每个规则以评估它读入条件中并写入操作中的字段/属性。逐步执行条件中的表达式以及操作中的语句,即可完成该操作。例如,假定以下规则。

通过隐式链接,WF 为用户提供大多数必要的链接,因此用户不必显式对更新进行建模,实际上在大多数实例中,用户可以不必了解链接或对链接的需求。我们希望这将使大多数用户更直观地了解复杂 RuleSet 的建模,让链接的概念成为一种强大的(但主要是隐含的)引擎功能。然而,其他两种驱动链接的机制(基于属性和显式)是为更复杂、更特定的方案而提供的。(前面的例子就是这种情况)

 

基于属性

对于规则中的方法调用,明确地计算发生的读/写操作变得更难了。为了解决该问题,WF 提供了三个可应用于方法以指示其操作的属性:RuleRead RuleWrite RuleInvoke

 

显式

最后一种指示字段/属性依赖项的机制是使用 Update 语句。Update 语句的参数为字符串(表示到字段或属性的路径)或表达式(表示字段/属性访问)。例如,可在 RuleSet 编辑器中键入以下任一语句在工作流上的 Customer 实例的 Name 属性上创建一条 Update 语句。

 

对于上面说的理解不到,所以也没做例子,留着这个问题,下一次为这个专门发一篇,希望高手指点.这是资料

http://www.microsoft.com/china/MSDN/library/Windev/WindowsVista/intWF_FndRlsEng.mspx?mfr=true

 

然而,在某些情况下,规则书写器也许希望能够对链接行为进行更多的控制,特别是希望能限制链接发生的行为。这使规则模块能够:

 1限制规则的重复执行,这可能会导致错误的结果。

 2提高性能。

  3 预防失控的循环。

 

[对于上面的说的,提到正向链接控件这个概念:

正向链接是一个非常强大的概念,它使原子则规则可以组装到 RuleSet,而无需定义甚至无需了解规则中依赖项的概念。]

 

通过以下两个属性,有助于在 WF 规则中使用该级别的控件:

    RuleSet 上的Chaining Behavior 属性。

    每个规则上的 Reevaluation Behavior 属性。


Always 是默认选项,它提供前面讨论过的行为,即将始终根据因其他规则的操作导致的链接对规则进行重新计算。顾名思义,Never 关闭该重新计算。该规则将计算一次,但如果它以前未执行任何操作,则不进行重新计算。换言之,如果RuleSet 上的 Chaining Behavior 属性有三个可能的值:
Full Chaining、 Explicit Chaining、 Sequential

Full Chaining 是默认选项,它提供目前为止所描述的行为。Explicit Chaining 选项关闭隐式链接和基于属性的链接,指示链接仅对显式的 Update 语句发生。这使规则书写器能完全控制哪些规则导致重新计算。通常,该选项用于以下两种情况:避免循环依赖项(导致过多的甚至失控的规则重新执行),或提高性能(通过消除提供 RuleSet 的功能完整性所不需要的多余的规则重新计算来实现)。

最后一个选项是 Sequential。该选项将导致引擎以严格的线性方式计算规则。每个规则都将按优先级顺序计算一次仅一次。优先级较高的规则可以影响优先级较低的规则,由于没有链接,因此优先级较低的规则不会影响优先级较高的规则。因此,该选项可以与显式优先级分配一起使用,除非规则中不存在依赖项。

Reevaluation Behavior 属性

规则上的 Reevaluation Behavior 有两个可能的值:
Always、 Never

Always 是默认选项,它提供前面讨论过的行为,即将始终根据因其他规则的操作导致的链接对规则进行重新计算。顾名思义,Never 关闭该重新计算。该规则将计算一次,但如果它以前未执行任何操作,则不进行重新计算。换言之,如果规则之前已进行过计算,结果执行了其 Then 或 Else 操作,则不对它进行重新计算。然而,执行 Then 或 Else 操作中的空操作集合不会将一个规则标记为已执行。

通常,该属性将在规则级别使用,以防止因规则在它自己的操作上或其他规则上具有依赖项而导致的无限循环。例如,下面的规则会创建自己的无限循环,无需重新计算来实现规则的功能需求。

IF this.shippingCharge < 2.5 AND this.orderValue > 100
THEN this.shippingCharge = 0
posted on 2007-04-05 16:49  GoodQ  阅读(654)  评论(0编辑  收藏  举报