1. 導入:なぜTYPE IS DETAILが重要なのか
COBOLのレポートライター機能(Report Writer)において、最も頻繁に制御することになるのが「明細行(DETAIL)」です。システム開発の現場では、帳票のヘッダーやフッターは自動で出力されても、肝心のデータ明細が「改ページと連動して正しく出力されない」「集計とズレる」といったトラブルが後を絶ちません。TYPE IS DETAILを正しく理解し、GENERATE文で制御することは、帳票プログラムの品質を左右する非常に重要なスキルです。
2. 基礎知識:REPORT SECTIONにおける明細行の役割
Report Writerは、REPORT SECTIONで帳票のレイアウトを定義し、手続き部(PROCEDURE DIVISION)で明細を生成する仕組みです。その中でTYPE IS DETAILは、入力レコードを1件ずつ編集して出力するための「テンプレート」となります。
最大の特徴は、手続き部からGENERATE文によって明示的に呼び出される点です。他のTYPE(REPORT HEADINGやPAGE HEADINGなど)はシステムが自動判定して出力しますが、DETAIL行だけは「今、このデータを出力せよ」とプログラマが指示を出す必要があります。
3. 実装・解決策:GENERATE文による制御
明細行を出力するには、以下の手順を踏みます。
1. REPORT SECTIONでTYPE IS DETAILを指定したデータ項目を定義する。
2. 手続き部で、対象のレポート名を指定してGENERATE文を実行する。
この際、GENERATE文が実行されるたびに、レポートライターは自動的に「行数カウンター」をチェックし、ページ溢れが発生していれば自動的に改ページとページヘッダーの出力を行ってくれます。
4. サンプルプログラム
以下に、実務でよく見かける顧客リストの明細出力例を示します。
01 REPORT SECTION.
01 LIST-REPORT REPORT IS CUSTOMER-LIST.
02 TYPE IS DETAIL.
03 COLUMN 5 PIC X(10) SOURCE CUST-ID. > 顧客IDを出力
03 COLUMN 20 PIC X(20) SOURCE CUST-NAME. > 顧客名を出力
03 COLUMN 45 PIC Z(8)9 SOURCE SALES-AMT. > 売上額を出力
PROCEDURE DIVISION.
…
PERFORM UNTIL END-OF-FILE
READ INPUT-FILE INTO WS-CUST-RECORD
AT END SET END-OF-FILE TO TRUE
NOT AT END
> ここでDETAIL行を出力する
GENERATE LIST-REPORT
END-READ
END-PERFORM.
…
5. 応用・注意点:現場で役立つデバッグのコツ
現場でよくある失敗として、「明細行のデータが更新されていない」というケースがあります。これは、GENERATEを実行する前にソースとなるデータ項目(この例ではWS-CUST-RECORD内の項目)を適切に更新し忘れていることが原因です。
また、DETAIL行にサマリ機能(SUM句)を組み合わせる場合、GENERATEが実行された瞬間に合計値が加算される点に注意してください。もし、条件によって「出力はするが合計には含めたくない」といった複雑な要件がある場合は、SUM句ではなく、自前で作業用変数を定義して手続き部で加算し、最終的にCOMPUTEした結果をDETAIL行に出力する手法の方が、バグの温床を減らすことができます。
基本を忠実に守り、GENERATEのタイミングをしっかり制御することで、メンテナンス性の高い帳票プログラムを作成しましょう。

コメント