我正在做时间考勤系统,我的物理文件(PF)有这些字段:
User ID(key field),Date,Time In,Time Out
......
问题是,我尝试选择特定的用户ID和日期以及当天的最高超时值。并将Time Out值移动到我程序中的变量。
如何将RPGLE源看起来像?
答案 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优化器发挥作用,找到最快的方式来获取数据。