使用 Microsoft COBOL编译器2.2版,我的代码完全正常。
IDENTIFICATION DIVISION.
PROGRAM-ID. COCENTRY.
ENVIRONMENT DIVISION.
INPUT-OUTPUT SECTION.
FILE-CONTROL.
SELECT COC-FILE
ASSIGN TO DISK
ORGANIZATION IS INDEXED
ACCESS MODE IS RANDOM
RECORD KEY IS COCNO
FILE STATUS IS FILE-STATUS.
DATA DIVISION.
FILE SECTION.
FD COC-FILE LABEL RECORD IS STANDARD
VALUE OF FILE-ID IS "COC.DAT".
01 COC-RECORD.
03 COCNO PIC 9(5).
03 COCDESC PIC X(40).
WORKING-STORAGE SECTION.
01 FILE-STATUS PIC XX.
01 ESC-CODE PIC 99 VALUE 0.
88 ESC-KEY VALUE 1.
88 F2 VALUE 3.
88 F10 VALUE 11.
01 ERRMSG PIC X(70) VALUE SPACES.
01 ERR PIC 9 VALUE 0.
SCREEN SECTION.
01 FORM1.
03 BLANK SCREEN BACKGROUND-COLOR 1.
03 LINE 1 COLUMN 1 'COCNO'.
03 LINE 2 COLUMN 1 'COCDESC'.
03 LINE 24 COLUMN 1 "Esc=Exit F2=Save F10=Cancel".
03 LINE 25 COLUMN 1 PIC X(70) FROM ERRMSG HIGHLIGHT.
01 FORM2.
03 LINE 1 COLUMN 14 PIC 9(5)
USING COCNO REVERSE-VIDEO.
03 LINE 2 COLUMN 14 PIC X(40)
USING COCDESC REVERSE-VIDEO.
03 LINE 24 COLUMN 1 PIC 99
USING ESC-CODE.
PROCEDURE DIVISION.
MAIN.
OPEN I-O COC-FILE.
IF FILE-STATUS NOT = '00'
OPEN OUTPUT COC-FILE
CLOSE COC-FILE
OPEN I-O COC-FILE.
PERFORM ENTRY1 THRU ENTRYX UNTIL ESC-KEY.
CLOSE COC-FILE.
STOP RUN.
ENTRY1.
MOVE SPACES TO COC-RECORD.
MOVE ZEROES TO COCNO.
ENTRY2.
DISPLAY FORM1 FORM2.
ACCEPT FORM2.
ACCEPT ESC-CODE FROM ESCAPE KEY.
IF F10
MOVE 'Entries canceled...' TO ERRMSG
GO ENTRY1
ELSE IF F2
GO ENTRY3
ELSE IF ESC-KEY
GO ENTRYX
ELSE
GO ENTRY2.
ENTRY3.
MOVE 0 TO ERR.
WRITE COC-RECORD INVALID KEY MOVE 1 TO ERR.
IF ERR = 1
MOVE 'Duplicate key not allowed...' TO ERRMSG
GO ENTRY2
ELSE
MOVE 'Entries recorded...' TO ERRMSG
GO ENTRY1.
ENTRYX.
EXIT.
现在我正在使用具有GNUCobol版本1.1.0的OpenCobol IDE 4.3.0 ,我被提示使用这行
syntax error, unexpected "Literal", expecting LEADING or TRAILING
03 LINE 1 COLUMN 1 'COCNO'.
03 LINE 2 COLUMN 1 'COCDESC'.
03 LINE 24 COLUMN 1 "Esc=Exit F2=Save F10=Cancel".
所以我通过添加 VALUE 关键字来修复它们:
03 LINE 1 COLUMN 1 VALUE 'COCNO'.
03 LINE 2 COLUMN 1 VALUE 'COCDESC'.
03 LINE 24 COLUMN 1 VALUE "Esc=Exit F2=Save F10=Cancel".
但是一旦我这样做,我得到另一个提示
'ACCEPT .. FROM ESCAPE KEY' not implemented
在这一行
ACCEPT ESC-CODE FROM ESCAPE KEY.
可能的原因是什么?什么可以解决这个问题?
答案 0 :(得分:4)
你的实际答案就在这里,https://sourceforge.net/p/open-cobol/discussion/help/thread/26a01c5f/,在SourceForge的GnuCOBOL部分。通过微小的更改,您的代码将完全正常工作"您已经做出的更改包括VALUE
子句,以及您是否使用GnuCOBOL编译器的2.0或更高版本。
您的代码可以完全正常工作"但它是意大利面条代码。
该术语来自过去,涉及在程序中使用许多分支,这是当时的常见做法,但是它试图遵循逻辑过程,例如尝试遵循一串煮熟的意大利面条。一堆熟意大利面的一部分。
如果你改变了这个:
PERFORM ENTRY1 THRU ENTRYX UNTIL ESC-KEY.
对此:
PERFORM ENTRY1 THRU ENTRYX.
您的计划仍然有效。困惑?是的,因为你有意大利面。您的程序流程只会转到ENTRYX一次。当它到达ENTRYX时的值是ESC-KEY,但这是多余的,因为当它是ESC-KEY时它只能到达那里一次。明确?没有?因为你有意大利面。
这是你的逻辑,重写:
PROCEDURE DIVISION.
OPEN I-O COC-FILE
IF FILE-STATUS NOT = '00'
[the following code is a horror. Deal with this outside the
program. Crash for an unexpected FILE STATUS on OPEN]
OPEN OUTPUT COC-FILE
CLOSE COC-FILE
OPEN I-O COC-FILE
END-IF
PERFORM PROCESS-USER-INPUT
UNTIL ESC-KEY
CLOSE COC-FILE
IF FILE-STATUS NOT = '00'
[something bad has happened, so don't go quietly]
END-IF
GOBACK
.
PROCESS-USER-INPUT.
PERFORM BLANK-OUTPUT-RECORD
PERFORM PROCESS-COC
UNTIL ESC-KEY
.
PROCESS-COC.
DISPLAY FORM1 FORM2
ACCEPT FORM2
ACCEPT ESC-CODE FROM ESCAPE KEY
EVALUATE TRUE
WHEN F10
MOVE 'Entries canceled...' TO ERRMSG
WHEN F2
PERFORM CREATE-OUTPUT
END-EVALUATE
.
CREATE-OUTPUT.
WRITE COC-RECORD
IF ATTEMPT-TO-WRITE-DUPLICATE [22 on the FILE STATUS field]
MOVE 'Duplicate key not allowed...' TO ERRMSG
ELSE
MOVE 'Entries recorded...' TO ERRMSG
PERFORM BLANK-OUTPUT-RECORD
END-IF
.
BLANK-OUTPUT-RECORD.
MOVE SPACES TO COC-RECORD
MOVE ZEROES TO COCNO
.
这会让您的程序看起来更简单吗?更容易理解,改变,理解当别人看到它时(或者你在两周内做的时候)它会做什么?
还有其他的东西,比如为什么将COC-RECORD设置为空格,然后将COCNO设置为零?将空格移动到COCDESC。
使您的数据/程序名称更好且更具描述性。文件状态具有良好的名称(不要将其称为FILE-STATUS),如果您有多个文件,则每个文件一个。仅在必要时使用完全停止/句点,并对您使用的所有条件结构使用范围分隔符。对所有IO使用FILE STATUS检查,不要在IO上使用曲折的AT。
如果您现在看起来程序中的第一个代码很长,只执行一次,并且(应该)与您的程序的业务功能无关。所以坚持段落中的所有内容,然后执行。收盘也一样。然后,您可以在启动和关闭时获得所需的代码,而不会使您的程序更难以遵循。
答案 1 :(得分:3)
屏幕和键盘I / O是MicroSoft Cobol特有的风格。您可能需要稍微调整一下才能使其与OpenCobol一起使用。
答案 2 :(得分:0)
PROCEDURE DIVISION.
SET ENVIRONMENT 'COB_SCREEN_EXCEPTIONS' TO 'Y'.
SET ENVIRONMENT 'COB_SCREEN_ESC' TO 'Y'.
IF cob-crt-status = 2005
...... IF cob-crt-status = 0
........ IF cob-crt-status = 1001
...... IF cob-crt-status = 1002
......