如何为具有条件的字段选择最高值?

时间:2012-07-11 03:46:04

标签: ibm-midrange rpgle rpg

我正在做时间考勤系统,我的物理文件(PF)有这些字段:

User ID(key field),Date,Time In,Time Out
......

问题是,我尝试选择特定的用户ID和日期以及当天的最高超时值。并将Time Out值移动到我程序中的变量。

如何将RPGLE源看起来像?

3 个答案:

答案 0 :(得分:3)

传统方法是使用用户ID,日期和超时作为键构建逻辑文件,日期和时间输出降序。然后我认为只使用用户ID链接到逻辑,今天的日期作为部分密钥将为您提供最新记录。

答案 1 :(得分:2)

嵌入式SQL也可以运行:

SELECT MAX(timeout) 
INTO :outTime  
FROM PF 
WHERE userid = :selected_user_id
AND date = :selected_date`

答案 2 :(得分:2)

假设您有一个员工档案和一个时间工作文件,例如您所描述的。并且您想报告每个员工在某一天的最早入住时间和最近超时时间。

所以你可能有一个循环读取员工文件,并且在那个循环中,你可以链接到@Martin所描述的逻辑以获得最后一次超时,另一个逻辑键入上升时间输入以获得那里价值最低。

使用SQL,您可以在一次读取(SQL中的提取)中获取员工文件信息,以及最早的进入时间和最近的超时时间。它简化了循环内部的代码,不是吗?

所以这是伪代码的基本流程:

Declare a cursor with your SQL statement
Open the cursor
Fetch a row from the cursor
DoWhile status is ok
    Process your data
    Fetch the next record
EndDo
Close the cursor

看起来不太可怕,是吗?那么让我们看看代码可能是什么样子。当然,在SQL中有多种方法可以做,但让我们从一个SQL Select语句开始。在SQL中使用RPG变量时,用冒号(':')作为前缀。

    WITH h as
    ( SELECT empID, min(timein) as firstin, max(timeout) as lastout
        FROM workhours
        WHERE workdate = :myvariable
        GROUP BY empID
    )
    SELECT e.lastname, e.firstname, e.empnbr, h.firstin, h.lastout
      FROM h
      JOIN employees as e   on h.empID = e.empnbr
      ORDER BY e.lastname, e.firstname, e.empnbr;

嗯,那是一个非常的SELECT语句,是吗?很多事情都在继续。

但它分为两部分。第一部分是一个名为h的表表达式,我们在该日期为每个员工获取时间。第二部分列出了我们想要的所有结果字段,这些字段取自表表达式h和employees文件,只要我们可以匹配两个文件中的员工编号。这些行将按姓氏,名字和员工编号分类给我们。

所以我们把它放在RPG中。

EXEC-SQL  DECLARE CURSOR C1 AS
              WITH h as
              ( SELECT empID, min(timein) as firstin, max(timeout) as lastout
                  FROM workhours
                  WHERE workdate = :myvariable
                  GROUP BY empID
              )
              SELECT e.lastname, e.firstname, e.empnbr, h.firstin, h.lastout
                FROM h
                JOIN employees as e   on h.empID = e.empnbr
                ORDER BY e.lastname, e.firstname, e.empnbr
                FOR READ ONLY;
EXEC-SQL  OPEN C1;
EXEC-SQL  FETCH FROM C1
            INTO :lname, :fname, :emp, :firsttime, :lasttime;
DoW &subst(SQLState,1,2) = '00';
    //
    // perform processing here
    //
    EXEC-SQL  FETCH FROM C1
                INTO :lname, :fname, :emp, :firsttime, :lasttime;
enddo;
EXEC-SQL  CLOSE C1;

现在您可能首先对光标中SELECT语句正在完成的工作犹豫不决。但是通过这一切,你已经简化了I / O,让SQL优化器发挥作用,找到最快的方式来获取数据。