2015-02-24 71 views
1

我已經看到了很多的例子在COBOL讀取順序文件看起來是這樣的:模式用於讀取順序輸入文件

FD File-Record 
01 Input-Record. 
    88 End-Of-File  VALUE HIGH-VALUES. 
    05 ... 

... 

    READ File-Record 
     AT END SET End-Of-File TO TRUE 
    END-READ 

    PERFORM UNTIL End-Of-File 
     PERFORM Process-Record 
     READ File-Record 
      AT END SET End-Of-File TO TRUE 
     END-READ 
    END-PERFORM 

的一個問題是,這將是一樣好於處理它如下?

PERFORM UNTIL End-Of-File 
     READ File-Record 
      AT END SET End-Of-File TO TRUE 
      NOT AT END PERFORM Process-Record 
     END-READ 
    END-PERFORM 

我還沒有普遍看到第二種模式,但它似乎更簡潔,沒有多餘的我。與第一個相比,它有問題嗎?我並不是指上述主題的變體(它們可以根據你如何定義你所定義的內容而進行不同的分組),但我指的是第一條記錄的預讀模式的概念,這似乎是在我見過的各種例子中受到青睞。

+1

比爾伍德回答了這個問題。在READ之外的啓動讀取和PERFORM普遍存在的原因是,它是在NOT AT END被添加到READ語法之前很久才完成的。 – 2015-02-24 19:12:34

+0

@GilbertLeBlanc謝謝,這很有趣(+1)。你碰巧知道什麼時候引入了NOT AT END? – lurker 2015-02-24 19:39:11

+0

Cobol 85標準X3.23-1985在互聯網上不可用。它可以購買。我的回憶是在1985年標準中的NOT AT END子句被添加到Cobol READ語句中。 – 2015-02-24 20:06:38

回答

3

第一個被稱爲「啓動讀取」。使用這意味着總是有一個可用的記錄進入處理循環。

第二個被稱爲...好吧,不知道這是否有一個名稱。在處理循環中,必須測試記錄的可用性。

一些事情。使用AT END/NOT AT END/END-READ本身有點笨拙(意見)。有一個更清潔的方式(它是更清潔的兩個原因)。

在您的文件的SELECT語句中(您應該對所有文件執行此操作)定義一個FILE STATUS字段,單個文件。

每次文件訪問之後,測試該文件的文件狀態字段,並確保訪問得到預期的結果。

使用此方法時,到達文件結尾時,文件狀態字段將自動設置爲10。所以,你移動88文件狀態字段,並更改VALUE至10

01 INPUT-FILE-STATUS    PIC XX. 
    88 INPUT-FILE-OK    VALUE ZERO "10". 
    88 INPUT-FILE-EOF    VALUE "10". 

PERFORM      PRIMING-READ 
PERFORM UNTIL End-Of-File 
    PERFORM     Process-Record 
    PERFORM     READ-A-RECORD05 is optional file not present, 23 is record not found. 
END-PERFORM 

... 
PRIMING-READ. 
    PERFORM     READ-A-RECORD 
    IF INPUT-FILE-EOF 
     [cancel with end-of-file on first read message] 
    END-IF 
    . 

READ-A-RECORD. 
    READ File-Record 
    IF NOT INPUT-FILE-OK 
     [code here to check file-status field and crash if bad] 
    END-IF 
    . 

我強烈贊成啓動讀取。 「空白」文件可能表明存在問題。現在您可以測試(在讀取引導之後),而不必混亂主邏輯。您不必在文件結束時「退出循環」,因爲循環只能輸入當前記錄。

傳統上文件將包含「標題」(和「拖車」)。標題將包含日期,邏輯文件名等。標題將被讀取和驗證,以知道正在處理正確的文件。然後你需要檢查有沒有兩個標題(因爲如果你不這樣做,有一天會有)。雖然你已經做到了,但你已經有了第一筆數據記錄。

你不想在一些「商業」邏輯中做所有事情,或混淆邏輯流程。

在輸入記錄上的88上,請注意,這是不可跨其他COBOL傳輸的。例如,在IBM大型機上,除非您的輸入是可變長度記錄,並且您只使用APPLY WRITE(明確地或由可怕的編譯器選項AWO隱式地),然後在文件打開之前在FD下訪問數據,關閉後,或在文件結束後會導致崩潰(ABEND)。

+0

謝謝比爾。你回答了我關於'88'EOF狀態的問題。我把這個機制扔到了幾個地方,作爲一種「聰明」的方式來處理這個選項。在這種情況下,我個人會認爲便攜性比較聰明。因此,使用文件狀態可以避免使用「EOF」標誌? – lurker 2015-02-24 19:30:15

+1

根本不需要使用AT END/NOT END/END-READ。與INVALID KEY/NOT INVALID KEY相同。沒有END-WRITEs。除了示例,我認爲我沒有編碼過它們。在FILE STATUS字段中爲88,00爲AOK,10爲EOF。還有其他的值,它們是標準的,儘管編譯器實現者已經知道它們的擴展。 – 2015-02-24 20:11:56

+1

是的,文件狀態字段*變成*文件結束標誌(以及無效的鍵控讀取/鍵控寫入等)。通過IO代碼自動設置,所以您知道錯誤時它是錯誤的(除非您打錯了88個VALUE)。 – 2015-02-24 20:18:30

0

主要問題是您只撥打PERFORM Process-Record一次,所以在這方面沒有第二種模式的改進。

然後你在Cobol工作,但擔心模式的企業。我寧願擔心Cobol與較高/較新的語言工作。大約25年前,我用Protos作爲一層來隱藏未加工的Cobol。 。 。

+0

你是否暗示第二種方法與第一種方法沒有什麼功能上的錯誤? (有關COBOL相關性的意見等討論不屬於我的問題。) – lurker 2015-02-24 16:27:16

+1

「PERFORM Process-Record」只在源代碼中出現一次,但每次成功讀取時都會執行該操作。不明白你的意思。也許你太多地隱藏了你的COBOL。 – 2015-02-24 16:46:57

+0

如果記錄中的「Perform」實際上存在多行代碼,那麼最好不要重複該代碼。只是爲了複製'read'命令不會讓你的代碼變得非常混亂。 – Roland 2015-02-24 17:34:50