>>SOURCE FORMAT IS FREE *> cobol-reconcile-two-files.cob - match two sorted files record by record *> and report every reference as MATCHED, AMOUNT DIFFERS, BANK ONLY or *> BOOK ONLY, with counts and control totals at the end *> Dialect: GnuCOBOL 3.x, free format *> Status : desk-checked against the GnuCOBOL 3.2 Programmer's Guide; *> NOT compiled (no cobc on the authoring machine) *> Inputs : datasets/cobol-reconcile-two-files-bank.dat (what the bank says) *> datasets/cobol-reconcile-two-files.dat (what our books say) *> both LINE SEQUENTIAL, 47 bytes, sorted ascending by reference *> Output : recon.txt in the current folder; counts on standard output *> Return : 0 normally, 12 if a file will not open, 16 on a sequence error *> Build : cobc -x code/cobol-reconcile-two-files.cob *> Run : ./cobol-reconcile-two-files (from the site folder) IDENTIFICATION DIVISION. PROGRAM-ID. RECONCILE. ENVIRONMENT DIVISION. INPUT-OUTPUT SECTION. FILE-CONTROL. SELECT Bank-File ASSIGN TO "datasets/cobol-reconcile-two-files-bank.dat" ORGANIZATION IS LINE SEQUENTIAL FILE STATUS IS WS-Bank-Status. SELECT Book-File ASSIGN TO "datasets/cobol-reconcile-two-files.dat" ORGANIZATION IS LINE SEQUENTIAL FILE STATUS IS WS-Book-Status. SELECT Report-File ASSIGN TO "recon.txt" ORGANIZATION IS LINE SEQUENTIAL FILE STATUS IS WS-Rpt-Status. DATA DIVISION. FILE SECTION. FD Bank-File. 01 Bank-Rec. 05 Bank-Ref PIC X(8). 05 Bank-Date PIC 9(8). 05 Bank-Amount PIC 9(9)V99. 05 Bank-Desc PIC X(20). FD Book-File. 01 Book-Rec. 05 Book-Ref PIC X(8). 05 Book-Date PIC 9(8). 05 Book-Amount PIC 9(9)V99. 05 Book-Desc PIC X(20). FD Report-File. 01 Report-Line PIC X(80). WORKING-STORAGE SECTION. 01 WS-Bank-Status PIC XX. 01 WS-Book-Status PIC XX. 01 WS-Rpt-Status PIC XX. *> The two keys the match runs on. HIGH-VALUES in a key means that file is *> finished; it sorts above every real reference, so the loop drains the *> other file and stops when both keys are HIGH-VALUES. 01 WS-Bank-Key PIC X(8). 01 WS-Book-Key PIC X(8). 01 WS-Prev-Bank PIC X(8) VALUE LOW-VALUES. 01 WS-Prev-Book PIC X(8) VALUE LOW-VALUES. 01 WS-Diff PIC S9(9)V99. 01 WS-Counts. 05 WS-Matched PIC 9(5) VALUE ZERO. 05 WS-Differs PIC 9(5) VALUE ZERO. 05 WS-Bank-Only PIC 9(5) VALUE ZERO. 05 WS-Book-Only PIC 9(5) VALUE ZERO. 01 WS-Totals. 05 WS-Bank-Total PIC S9(11)V99 VALUE ZERO. 05 WS-Book-Total PIC S9(11)V99 VALUE ZERO. 05 WS-Net PIC S9(11)V99 VALUE ZERO. 01 WS-Heading-1 PIC X(80) VALUE "RECONCILIATION: BANK FILE AGAINST BOOK FILE". 01 WS-Heading-2. 05 FILLER PIC X(16) VALUE "STATUS". 05 FILLER PIC X(10) VALUE "REFERENCE". 05 FILLER PIC X(14) VALUE " BANK AMOUNT". 05 FILLER PIC X(2) VALUE SPACES. 05 FILLER PIC X(14) VALUE " BOOK AMOUNT". 05 FILLER PIC X(2) VALUE SPACES. 05 FILLER PIC X(16) VALUE " DIFFERENCE". 01 WS-Detail. 05 WS-D-Status PIC X(14). 05 FILLER PIC X(2) VALUE SPACES. 05 WS-D-Ref PIC X(8). 05 FILLER PIC X(2) VALUE SPACES. 05 WS-D-Bank PIC ZZZ,ZZZ,ZZ9.99 BLANK WHEN ZERO. 05 FILLER PIC X(2) VALUE SPACES. 05 WS-D-Book PIC ZZZ,ZZZ,ZZ9.99 BLANK WHEN ZERO. 05 FILLER PIC X(2) VALUE SPACES. 05 WS-D-Diff PIC -,---,---,--9.99 BLANK WHEN ZERO. 01 WS-Count-Line. 05 WS-C-Label PIC X(24). 05 WS-C-Value PIC ZZ,ZZ9. 01 WS-Money-Line. 05 WS-M-Label PIC X(24). 05 WS-M-Value PIC -,---,---,---,--9.99. PROCEDURE DIVISION. Main-Para. OPEN INPUT Bank-File Book-File OUTPUT Report-File IF WS-Bank-Status NOT = "00" OR WS-Book-Status NOT = "00" OR WS-Rpt-Status NOT = "00" DISPLAY "OPEN FAILED: BANK " WS-Bank-Status " BOOK " WS-Book-Status " REPORT " WS-Rpt-Status MOVE 12 TO RETURN-CODE STOP RUN END-IF WRITE Report-Line FROM WS-Heading-1 WRITE Report-Line FROM WS-Heading-2 PERFORM Read-Bank PERFORM Read-Book PERFORM UNTIL WS-Bank-Key = HIGH-VALUES AND WS-Book-Key = HIGH-VALUES EVALUATE TRUE WHEN WS-Bank-Key = WS-Book-Key PERFORM Same-Key PERFORM Read-Bank PERFORM Read-Book WHEN WS-Bank-Key < WS-Book-Key PERFORM Bank-Only PERFORM Read-Bank WHEN OTHER PERFORM Book-Only PERFORM Read-Book END-EVALUATE END-PERFORM PERFORM Write-Totals CLOSE Bank-File Book-File Report-File STOP RUN. *> Read the next bank record. At end of file the key becomes HIGH-VALUES. *> A reference that is not higher than the one before it is a sequence *> error: the match only works on sorted input, so the run stops. Read-Bank. READ Bank-File AT END MOVE HIGH-VALUES TO WS-Bank-Key NOT AT END IF Bank-Ref NOT > WS-Prev-Bank DISPLAY "SEQUENCE ERROR IN BANK FILE AT " Bank-Ref PERFORM Abort-Run END-IF MOVE Bank-Ref TO WS-Bank-Key WS-Prev-Bank ADD Bank-Amount TO WS-Bank-Total END-READ. Read-Book. READ Book-File AT END MOVE HIGH-VALUES TO WS-Book-Key NOT AT END IF Book-Ref NOT > WS-Prev-Book DISPLAY "SEQUENCE ERROR IN BOOK FILE AT " Book-Ref PERFORM Abort-Run END-IF MOVE Book-Ref TO WS-Book-Key WS-Prev-Book ADD Book-Amount TO WS-Book-Total END-READ. *> Both files hold this reference: compare the amounts. Same-Key. MOVE WS-Bank-Key TO WS-D-Ref MOVE Bank-Amount TO WS-D-Bank MOVE Book-Amount TO WS-D-Book COMPUTE WS-Diff = Bank-Amount - Book-Amount MOVE WS-Diff TO WS-D-Diff IF WS-Diff = ZERO MOVE "MATCHED" TO WS-D-Status ADD 1 TO WS-Matched ELSE MOVE "AMOUNT DIFFERS" TO WS-D-Status ADD 1 TO WS-Differs END-IF WRITE Report-Line FROM WS-Detail. *> Only the bank has it: a fee, interest, or a payment we never booked. Bank-Only. MOVE "BANK ONLY" TO WS-D-Status MOVE WS-Bank-Key TO WS-D-Ref MOVE Bank-Amount TO WS-D-Bank MOVE ZERO TO WS-D-Book MOVE Bank-Amount TO WS-Diff MOVE WS-Diff TO WS-D-Diff ADD 1 TO WS-Bank-Only WRITE Report-Line FROM WS-Detail. *> Only our books have it: usually a cheque that has not cleared yet. Book-Only. MOVE "BOOK ONLY" TO WS-D-Status MOVE WS-Book-Key TO WS-D-Ref MOVE ZERO TO WS-D-Bank MOVE Book-Amount TO WS-D-Book COMPUTE WS-Diff = 0 - Book-Amount MOVE WS-Diff TO WS-D-Diff ADD 1 TO WS-Book-Only WRITE Report-Line FROM WS-Detail. Write-Totals. MOVE SPACES TO Report-Line WRITE Report-Line MOVE "MATCHED" TO WS-C-Label MOVE WS-Matched TO WS-C-Value WRITE Report-Line FROM WS-Count-Line MOVE "AMOUNT DIFFERS" TO WS-C-Label MOVE WS-Differs TO WS-C-Value WRITE Report-Line FROM WS-Count-Line MOVE "BANK ONLY" TO WS-C-Label MOVE WS-Bank-Only TO WS-C-Value WRITE Report-Line FROM WS-Count-Line MOVE "BOOK ONLY" TO WS-C-Label MOVE WS-Book-Only TO WS-C-Value WRITE Report-Line FROM WS-Count-Line MOVE "BANK FILE TOTAL" TO WS-M-Label MOVE WS-Bank-Total TO WS-M-Value WRITE Report-Line FROM WS-Money-Line MOVE "BOOK FILE TOTAL" TO WS-M-Label MOVE WS-Book-Total TO WS-M-Value WRITE Report-Line FROM WS-Money-Line COMPUTE WS-Net = WS-Bank-Total - WS-Book-Total MOVE "NET DIFFERENCE" TO WS-M-Label MOVE WS-Net TO WS-M-Value WRITE Report-Line FROM WS-Money-Line DISPLAY "MATCHED " WS-Matched " DIFFERS " WS-Differs " BANK ONLY " WS-Bank-Only " BOOK ONLY " WS-Book-Only. Abort-Run. MOVE 16 TO RETURN-CODE CLOSE Bank-File Book-File Report-File STOP RUN.