【问题标题】:Cobol, Code 65 File LockedCobol,代码 65 文件已锁定
【发布时间】:2015-03-18 23:16:10
【问题描述】:

我正在尝试访问同一个文件来执行两项特定任务。第一个任务是更新、添加和删除记录。访问必须是随机的。第二个任务是在控制台上显示所有记录。访问必须是顺序的。我从 COBOL 收到code 65 File locked,因为程序试图同时访问同一个文件两次。有没有办法解决这个错误?还是有其他方法可以做到这一点?还是我必须编写一个单独的程序才能在控制台上显示记录?我被卡住了!

   ENVIRONMENT DIVISION.

   INPUT-OUTPUT SECTION.
   FILE-CONTROL.
       SELECT MAST-FILE ASSIGN TO 'G:\CPSC315-COBOL\COBOLAssignments\P15-5\SALES.IND.TXT'
           ORGANIZATION IS INDEXED
           ACCESS IS RANDOM
           RECORD KEY M-SALESPERSON-NUM.

       SELECT MAST2-FILE ASSIGN TO 'G:\CPSC315-COBOL\COBOLAssignments\P15-5\SALES.IND.TXT'
           ORGANIZATION IS INDEXED
           ACCESS IS SEQUENTIAL
           RECORD KEY M2-SALESPERSON-NUM.

   DATA DIVISION.
   FILE SECTION.
   FD MAST-FILE
       LABEL RECORDS ARE STANDARD.
   01 MAST-RECORD.
       05 M-SALESPERSON-NUM  PIC XXX.
       05 M-CUSTOMER-NAME    PIC X(15).
       05 M-TOTAL-SALES      PIC 9(5)V99.
       05 M-COST-OF-SALES    PIC 9(4)V99.

   FD MAST2-FILE
       LABEL RECORDS ARE STANDARD.
   01 MAST2-RECORD.
       05 M2-SALESPERSON-NUM     PIC X(3).
       05 M2-SALESPERSON-NAME    PIC X(15).
       05 M2-TOTAL-SALES         PIC 9(5)V99.
       05 M2-COST-OF-SALES       PIC 9(4)V99.

   WORKING-STORAGE SECTION.
   01 SALES-DATA.
       05 SALESPERSON-NUM     PIC X(3).
       05 SALESPERSON-NAME    PIC X(15).
       05 TOTAL-SALES         PIC 9(5)V99.
       05 COST-OF-SALES       PIC 9(4)V99.

   01 OUTPUT-RECORD.
       05                      PIC X(1) VALUE SPACES.
       05 O-SALESPERSON-NUM    PIC X(3).
       05                      PIC X(3) VALUE SPACES.
       05 O-SALESPERSON-NAME   PIC X(3).
       05                      PIC X(3) VALUE SPACES.
       05 O-TOTAL-SALES        PIC 9(5)V99.
       05                      PIC X(3) VALUE SPACES.
       05 O-COST-OF-SALES      PIC 9(4)V99.

   01 PROGRAM-DATA-ITEMS.
       05 I-SALESPERSON-NUM       PIC XXX.
       05 WAIT-OK                 PIC X.
       05 CHOICE                  PIC 9 VALUE 0.
       05 READ-OK                 PIC X.
       05 REWRITE-OK              PIC X.
       05 DELETE-OK               PIC X.

   PROCEDURE DIVISION.
   10-MAINLINE.
       OPEN I-O MAST-FILE
       OPEN INPUT MAST2-FILE
       PERFORM 20-PROCESS-LOOP
       CLOSE MAST-FILE
           MAST2-FILE
       STOP RUN.

   20-PROCESS-LOOP.
       PERFORM UNTIL CHOICE = 5
           PERFORM 30-DISPLAY-MENU
           EVALUATE CHOICE
               WHEN 1  
                   PERFORM 40-UPD-SALES
               WHEN 2
                   PERFORM 90-ADD-SALES
               WHEN 3
                   PERFORM 110-DELETE-SALES
               WHEN 4
                   PERFORM 120-DISPLAY-SALES
            END-EVALUATE
        END-PERFORM.

   30-DISPLAY-MENU.
       DISPLAY 'SALES MAINTENANCE SYSTEM'
       DISPLAY ' '
       DISPLAY ' SELECT ONE:'
       DISPLAY ' '
       DISPLAY '   1. UPDATE SALES RECORD'
       DISPLAY '   2. ADD SALES RECORD'
       DISPLAY '   3. DELETE SALES RECORD'
       DISPLAY '   4. DISPLAY SALES RECORD'
       DISPLAY '   5. QUIT'
       DISPLAY ' '
       DISPLAY 'ENTER CHOICE (1 - 5): ' WITH NO ADVANCING
       ACCEPT CHOICE
       PERFORM UNTIL CHOICE >= 1 AND <= 5
           DISPLAY ' '
           DISPLAY 'ERROR: ENTER CHOICE (1 - 5): ' WITH NO ADVANCING
           ACCEPT CHOICE
       END-PERFORM.

   40-UPD-SALES.
       DISPLAY 'UPDATE SALES: ENTER SALESPERSON NUMBER: ' WITH NO ADVANCING
       ACCEPT SALESPERSON-NUM
       MOVE SALESPERSON-NUM TO M-SALESPERSON-NUM
       PERFORM 50-READ-RECORD
       IF READ-OK = 'N'
           DISPLAY 'RECORD DOES NOT EXIST - PRESS ENTER'
           ACCEPT WAIT-OK
       ELSE
           DISPLAY SALES-DATA
           PERFORM 100-INPUT-NEW-RECORD
           PERFORM 60-REWRITE-RECORD
       END-IF.

   50-READ-RECORD.
       MOVE 'Y' TO READ-OK
       READ MAST-FILE INTO SALES-DATA
           INVALID KEY
               MOVE 'N' TO READ-OK
       END-READ.

   60-REWRITE-RECORD.
       REWRITE MAST-RECORD FROM SALES-DATA
           INVALID KEY
               DISPLAY 'REWRITE ERROR: SALESPERSON NUMBER ' SALESPERSON-NUM
               DISPLAY 'PRESS ENTER TO CONTINUE'
               ACCEPT WAIT-OK
       END-REWRITE.

   70-WRITE-RECORD.
       MOVE 'Y' TO REWRITE-OK
       WRITE MAST-RECORD FROM SALES-DATA
           INVALID KEY
               MOVE 'N' TO REWRITE-OK
       END-WRITE
       IF REWRITE-OK = 'N'
           DISPLAY 'WRITE ERROR: SALESPERSON NUMBER ' SALESPERSON-NUM
           DISPLAY 'PRESS ENTER TO CONTINUE'
           ACCEPT WAIT-OK
       END-IF.

   80-DELETE-RECORD.
       MOVE 'Y' TO DELETE-OK
       DELETE MAST-FILE
           INVALID KEY 
               MOVE 'N' TO DELETE-OK
       END-DELETE
       IF REWRITE-OK = 'N'
           DISPLAY 'WRITE ERROR: SALESPERSON NUMBER ' SALESPERSON-NUM
           DISPLAY 'PRESS ENTER TO CONTINUE'
           ACCEPT WAIT-OK
       END-IF.

   90-ADD-SALES.
       DISPLAY 'ADD SALES RECORD: ENTER SALESPERSON NUMBER: ' WITH NO ADVANCING
       ACCEPT SALESPERSON-NUM
       MOVE SALESPERSON-NUM TO M-SALESPERSON-NUM
       PERFORM 50-READ-RECORD
       IF READ-OK = 'Y'
           DISPLAY 'RECORD ALREADY EXISTS - PRESS ENTER'
           ACCEPT WAIT-OK
       ELSE
           PERFORM 100-INPUT-NEW-RECORD
           PERFORM 70-WRITE-RECORD
           IF REWRITE-OK = 'Y'
               DISPLAY 'RECORD ' SALESPERSON-NUM ' ADDED TO FILE'
               DISPLAY 'PRESS ENTER TO CONTINUE'
               ACCEPT WAIT-OK
           END-IF
       END-IF.

   100-INPUT-NEW-RECORD.
       MOVE SALESPERSON-NUM TO M-SALESPERSON-NUM
       DISPLAY '       ENTER SALESPERSON NAME: ' WITH NO ADVANCING
       ACCEPT SALESPERSON-NAME
       DISPLAY '           ENTER TOTAL SALES: ' WITH NO ADVANCING
       ACCEPT TOTAL-SALES
       DISPLAY '               ENTER COST OF SALES: ' WITH NO ADVANCING
       ACCEPT COST-OF-SALES.

   110-DELETE-SALES.
       DISPLAY 'DELETE SALES RECORD: ENTER SALESPERSON NUMBER: ' WITH NO ADVANCING
       ACCEPT SALESPERSON-NUM
       MOVE SALESPERSON-NUM TO M-SALESPERSON-NUM
       PERFORM 50-READ-RECORD
       IF READ-OK = 'N'
           DISPLAY 'RECORD DOES NOT EXIST - PRESS ENTER'
           ACCEPT WAIT-OK
       ELSE
           PERFORM 80-DELETE-RECORD
           IF DELETE-OK = 'Y'
               DISPLAY 'RECORD DELETED - PRESS ENTER'
               ACCEPT WAIT-OK
           END-IF
       END-IF.

   120-DISPLAY-SALES.
       MOVE SALESPERSON-NUM TO M2-SALESPERSON-NUM
       MOVE SALESPERSON-NAME TO M2-SALESPERSON-NAME
       MOVE TOTAL-SALES TO M2-TOTAL-SALES
       MOVE COST-OF-SALES TO M2-COST-OF-SALES
       READ MAST2-FILE
           AT END MOVE HIGH-VALUES TO M2-SALESPERSON-NUM
       END-READ
       PERFORM UNTIL M2-SALESPERSON-NUM = HIGH-VALUES
           MOVE M2-SALESPERSON-NUM TO O-SALESPERSON-NUM
           MOVE M2-SALESPERSON-NAME TO O-SALESPERSON-NAME
           MOVE M2-TOTAL-SALES TO O-TOTAL-SALES
           MOVE M2-COST-OF-SALES TO O-COST-OF-SALES
           DISPLAY OUTPUT-RECORD
           READ MAST2-FILE
               AT END MOVE HIGH-VALUES TO M2-SALESPERSON-NUM
           END-READ
       END-PERFORM.

   end program Program1.

【问题讨论】:

  • 将它们作为两个单独的通道进行,并在通道之间根据需要关闭和打开文件?
  • 是的,先生! Mast 文件是随机访问的,因此打开 i-o 并关闭,mast2 文件是顺序的,因此打开输入以读取然后关闭。 2 遍的相同文件 ==> 代码 65 错误
  • 请使用您拥有的“两次通过”版本代码的代码更新您的 10-MAINLINE 段落。它应该类似于:OPEN I-O MAST-FILE。执行 20 个随机过程循环,关闭 MAST 文件。打开输入 MAST2 文件。执行 21 顺序过程循环。关闭 MAST2 文件。
  • 瑞恩!它仍然导致代码 65 文件被锁定。我想是因为我同时访问同一个文件。有什么办法可以解锁文件吗?
  • 很高兴知道您如何处理其他问题。

标签: cobol


【解决方案1】:

当你打开一个文件 I-O 时,这意味着你打开它是为了输入和输出。删除你的第二个文件。

要定位文件以显示数据,您可以使用 KEY 读取,然后使用 READ ... NEXT ...,或者您可以使用 START ... 然后使用 READ ... NEXT。

始终在 ASSIGN 中使用 FILE STATUS。然后使用您告诉 COBOL 将文件状态放入的文件状态字段来检查之前的 IO。将其用于文件结尾(值为“10”)。使用88s。然后,您不需要 INVALID KEY 和 AT END 以及与 IO 关联的所有 END- 语句都可以执行,因为您没有 IO 的内置条件。这将简化事情。

您的结构非常适合初学者。令人耳目一新,看到没有 PERFORM ... THRU ....

我建议您尝试在第 12 列中单独使用一个句号/句点的效果。然后,您将能够从段落中移动最后一行代码,而无需考虑附加到它的句号/句点(因为它没有附加到它)。

使用更多的 PERFORM。 OPEN 和 CLOSE 对程序的逻辑并不重要。将它们隐藏在段落中,对它们进行文件状态检查。与您最终得到的 READ/WRITE/DELETE 和任何其他 IO 语句相同。将它们隐藏在您执行的命名程序中。

考虑一些 IF 的大小(行数)。将代码放在一个命名良好的过程中,代码可以被人类在高层次上“阅读”,只有在需要时才查看细节。

不要,不要,不要,搞乱两个文件。不要,不要,不要两次打开同一个文件(我曾经写过一些 COBOL 程序,而且我从来没有认为这是实现任何事情的合理方法,更不用说你的简单任务了)。

您可能需要考虑 DYNAMIC 而不是 RANDOM(这就是它的用途)。如果您进行随机访问,则使用 RANDOM。您实际上也想进行顺序访问(查找对跳过顺序访问的引用以进行进一步讨论)。

SELECT MAST-FILE ASSIGN TO 'G:\CPSC315-COBOL\COBOLAssignments\P15-5\SALES.IND.TXT'
       ORGANIZATION IS INDEXED
       ACCESS IS RANDOMREWRITE-OK = 'N'
       RECORD KEY M-SALESPERSON-NUM
       FILE STATUS IS W-MAST-FILE-STATUS.

...

01  W-MAST-FILE-STATUS                    PIC XX.
    88  W-MAST-FILE-LAST-IO-OK            VALUE "00".
    88  W-MAST-FILE-EOF                   VALUE "10".
    88  W-MAST-FILE-REC-NOT-FOUND         VALUE "23".
    88  W-MAST-FILE-OR-OR-NOT-FOUND       VALUE "00" "23".

...

50-READ-RECORD.
    MOVE 'Y' TO READ-OK
    READ MAST-FILE INTO SALES-DATA
        INVALID KEY
            MOVE 'N' TO READ-OK
    END-READ.

变成:

50-READ-RECORD.
    READ MAST-FILE KEY key-name INTO SALES-DATA
    IF NOT ( W-MAST-FILE-OR-OR-NOT-FOUND ) 
        some code to deal with the pickle, which is nothing to do with 
        business-logic, so hide it away
    END-IF
    .

80-DELETE-RECORD.
    MOVE 'Y' TO DELETE-OK
    DELETE MAST-FILE
        INVALID KEY 
            MOVE 'N' TO DELETE-OK
    END-DELETE
    IF REWRITE-OK = 'N'
        DISPLAY 'WRITE ERROR: SALESPERSON NUMBER ' SALESPERSON-NUM
        DISPLAY 'PRESS ENTER TO CONTINUE'
        ACCEPT WAIT-OK
    END-IF.

变成:

80-DELETE-RECORD.
    DELETE MAST-FILE
    IF NOT W-MAST-FILE-LAST-IO-OK
        DISPLAY 'WRITE ERROR: SALESPERSON NUMBER ' SALESPERSON-NUM
        DISPLAY 'PRESS ENTER TO CONTINUE'
        ACCEPT WAIT-OK
    END-IF
    .

每个 IO 段落都变得自包含、自验证,而 FILE STATUS 字段自然只有在您的业务逻辑中才具有良好的条件。您在这些段落中处理的“不可能发生”(但总有一天会发生)。

您在其他地方编写的代码可以简化。您的“标志”数量减少了(FILE STATUS 字段的值取代了对标志的需求)您的 IO 没有条件部分,因此不需要 END-scope 分隔符。

关于给段落编号的提示。在您对逻辑结构进行充分测试以使您满意之前,请不要这样做。一旦您对此感到满意,请重新排列段落,以便该段落始终在物理上它的 PERFORM 之后。然后把数字放在上面。然后,代码的物理布局就代表了程序逻辑的结构。

如果你先编号,你最终会遇到这样的情况——你有编号,但它们什么也不能推断。 “重新编号”段落比在没有段落编号的地方添加段落编号要繁琐得多(使用您可用的编辑器/实用程序来进行编号)。

【讨论】:

  • 根据所提供的代码提供代码示例作为您的意思的“好示例”是否有用?即显示您希望他们使用的“真实”代码?你提到他们有一个“合理的”程序结构。它应该是什么样子?发布好的代码示例?这是最好的学习方式;通过查看好的代码。
  • @RyanVincent 我已经做了一些。简化,重新排序。这就是它所需要的,再加上对 I-O 使用相同的文件,I-O 没有问题,这只是摆脱第二个文件以支持使用第一个文件的情况。现代谚语:为男人提供大学水平的教育,所以他决定是否一生都在钓鱼,或者做一些能让他买鱼、肉、电脑、名牌衣服、住的地方、股票和股票的事情节假日等
  • 感谢您的回复比尔,这很有意义。
猜你喜欢
  • 2020-12-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-04-08
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多