开始 ... END 语句
BEGIN ... END 语句为 BEGIN 和 END 关键字中定义的语句提供了单个语句的状态。
- 可以成为函数或过程的主体
- 能够让处理程序处理自己的异常
- 能够用 LEAVE 语句中断自己的执行
语法
只有存在第一个 Label,第二个 Label 才能存在。 而且如果两个 Label 都存在,它们必须相等。 同一级别的两个或更多有标签语句可以有相同的标签,但这样会部分抵消使用第二个标签带来的好处。 此处所说的好处是指标签可以明白、准确地与每个 END 及其 BEGIN 进行匹配。 但是,上述语句中嵌套的有标签语句不能有相同的标签,因为这样会使 ITERATE 和 LEAVE 语句的行为不明确。
变量的作用域
DECLARE Variable1 CHAR 'Existing variable';
-- A reference to Variable1 here returns 'Existing variable'
BEGIN
-- A reference to Variable1 here returns 'Existing variable'
DECLARE Variable1 CHAR 'Local variable'; -- Perfectly legal even though
the name is the same
-- A reference to Variable1 here returns 'Local variable'
END;ATOMIC
如果指定了 ATOMIC,那么在任何时候,只允许消息流的一个实例(即,一个线程)执行特定 BEGIN ATOMIC... END 语句(由其模式和标签标识)。 如果没有标签,那么其行为与指定长度为零的标签相似。
CREATE PROCEDURE WriteSharedVariable1(IN NewValue CHARACTER)
SharedVariableMutex1 : BEGIN ATOMIC
-- Set new value into shared variable
END;
CREATE FUNCTION ReadSharedVariable1() RETURNS CHARACTER
SharedVariableMutex1 : BEGIN ATOMIC
DECLARE Value CHARACTER;
-- Get value from shared variable
RETURN Value;
END;
WriteSharedVariable1 和函数 ReadSharedVariable1 在同一模式中,并且被同一个流中的节点使用。 但是,过程和函数是否包含在模块中或是否在相同节点中使用并不重要。 集成节点会确保在任何特定时刻都只有一个线程在执行 Atomic 节中的语句。 例如,这样可以确保两个并行写操作或并行写、读操作有序执行。 注意:- 此序列只限于流。 使用 BEGIN ATOMIC... END 语句且具有相同模式和标签的两个流可以同时执行。 在这方面,流中的多个实例和流的多个副本是不相同的。
- 此序列只限于模式和标签。 在不同模式中指定且具有不同标签的 Atomic BEGIN ... END 语句不会相互交互。
请勿直接或间接嵌套 BEGIN ATOMIC... END 语句,因为这可能导致死锁
。 因此,请勿使用 Atomic 块中的 PROPAGATE 语句。
在从不部署一个以上实例(但如果让这种情况发生是不明智的)的流中没有必要使用 BEGIN ATOMIC 构造。 读、写共享变量时也没有必要使用 BEGIN ATOMIC 构造。 集成节点始终向共享变量安全地读、写新值。 仅当应用程序需要查看中间结果时,才需要使用 ATOMIC。
DECLARE LastOrderDate SHARED DATE;
...
SET LastOrderDate = CURRENT_DATE;
...
SET OutputRoot.XMLNSC.Data.Orders.Order[1].Date = LastOrderDate;
在本例中,我们假设一个线程定期更新 LastOrderDate,另一个线程定期读取它。 由于第二个 SET 语句始终读取有效值,因此不需要使用 ATOMIC。 如果更新和读取之间的时间间隔非常短,是读取旧值还是新值并不确定,但始终不是新值就是旧值。 结果总是有用的。DECLARE Count SHARED INT;
...
SET Count = Count + 1;在本例中,我们假设多个线程定期执行 SET 语句。 在这种情况下,您不需要使用 ATOMIC,因为两个线程可能几乎在同一时刻读取 Count,并获得相同的值。 这两个线程都执行添加并回存相同的值。 因此最终结果是 N+1,而不是 N+2。集成节点不会自动提供比这更高级别的锁定(例如,锁定覆盖整个 SET 语句),因为此类锁定容易导致死锁
。
提示
可以将 BEGIN ... END 语句视为一个循环构造,它总是只循环一次。 嵌套在 BEGIN ... END 语句中的 ITERATE 或 LEAVE 语句的效果与您预期的一样:将控制转移到 END 之后的语句。 在 BEGIN ... END 语句中使用 ITERATE 或 LEAV 对于存在需要放弃的一系列计算的情况很有用,因为已实现了一定结果,或者是因为发生了错误。
